[Contents] [Prev] [Next] [Index] [Report an Error]

Automatically Configuring Logical Interfaces and IP Addresses

Every interface you configure requires at least one logical unit and one IP address. Asynchronous Transfer Mode (ATM) interfaces also require a virtual circuit identifier (VCI) for each logical interface. If you need to configure multiple logical units on an interface, you can use a commit script macro to complete the task quickly and with no errors.

This example expands an apply-macro statement that provides the name of a physical ATM interface, and a set of parameters that specify how to configure a number of logical units on the interface. The units and VCI numbers are numbered sequentially from the $unit variable to the $max variable, and are given IP addresses starting at the $address variable. To loop through the logical units, Extensible Stylesheet Language Transformations (XSLT) uses recursion, which is implemented in the <emit-interface> template. Calculation of the next address is performed in the <next-address> template.

XSLT Syntax

<?xml version="1.0" standalone="yes"?>
<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:junos="http://xml.juniper.net/junos/*/junos"
    xmlns:xnm="http://xml.juniper.net/xnm/1.1/xnm"
    xmlns:jcs="http://xml.juniper.net/junos/commit-scripts/1.0">

    <xsl:import href="../import/junos.xsl"/>

    <xsl:template match="configuration">
        <xsl:for-each select="interfaces/apply-macro">
            <xsl:variable name="device" select="name"/>
            <xsl:variable name="address" select="data[name='address']/value"/>
            <xsl:variable name="max" select="data[name='max']/value"/>
            <xsl:variable name="unit" select="data[name='unit']/value"/>

            <xsl:variable name="real-max">
                <xsl:choose>
                    <xsl:when test="string-length($max) &gt; 0">
                        <xsl:value-of select="$max"/>
                    </xsl:when>
                    <xsl:otherwise>0</xsl:otherwise>
                </xsl:choose>
            </xsl:variable>

            <xsl:variable name="real-unit">
                <xsl:choose>
                    <xsl:when test="string-length($unit) &gt; 0">
                        <xsl:value-of select="$unit"/>
                    </xsl:when>
                    <xsl:when test="contains($device, '.')">
                        <xsl:value-of select="substring-after($device, '.')"/>
                    </xsl:when>
                    <xsl:otherwise>0</xsl:otherwise>
                </xsl:choose>
            </xsl:variable>

            <xsl:variable name="real-device">
                <xsl:choose>
                    <xsl:when test="contains($device, '.')">
                        <xsl:value-of select="substring-before($device, '.')"/>
                    </xsl:when>
                    <xsl:otherwise><xsl:value-of select="$device"/></xsl:otherwise>
                </xsl:choose>
            </xsl:variable>

            <transient-change>
                <interfaces>
                    <interface>
                        <name><xsl:value-of select="$real-device"/></name>
                        <xsl:call-template name="emit-interface">
                            <xsl:with-param name="address" select="$address"/>
                            <xsl:with-param name="unit" select="$real-unit"/>
                            <xsl:with-param name="max" select="$real-max"/>
                        </xsl:call-template>
                    </interface>
                </interfaces>
            </transient-change>

        </xsl:for-each>
    </xsl:template>

    <xsl:template name="emit-interface">
        <xsl:param name="$max"/>
        <xsl:param name="$unit"/>
        <xsl:param name="$address"/>

        <unit>
            <name><xsl:value-of select="$unit"/></name>
            <vci><xsl:value-of select="$unit"/></vci>
            <family>
                <inet>
                    <address><xsl:value-of select="$address"/></address>
                </inet>
            </family>
        </unit>

        <xsl:if test="$max &gt; $unit">
            <xsl:call-template name="emit-interface">
                <xsl:with-param name="address">
                    <xsl:call-template name="next-address">
                        <xsl:with-param name="address" select="$address"/>
                    </xsl:call-template>
                </xsl:with-param>
                <xsl:with-param name="unit" select="$unit + 1"/>
                <xsl:with-param name="max" select="$max"/>
            </xsl:call-template>
        </xsl:if>
    </xsl:template>

    <xsl:template name="next-address">
        <xsl:param name="address"/>

        <xsl:variable name="arg-prefix" select="substring-after($address, '/')"/>
        <xsl:variable name="arg-addr" select="substring-before($address, '/')"/>
        <xsl:variable name="addr">
            <xsl:choose>
                <xsl:when test="string-length($arg-addr) &gt; 0">
                    <xsl:value-of select="$arg-addr"/>
                </xsl:when>
                <xsl:otherwise>
                    <xsl:value-of select="$address"/>
                </xsl:otherwise>
            </xsl:choose>
        </xsl:variable>

        <xsl:variable name="prefix">
            <xsl:choose>
                <xsl:when test="string-length($arg-prefix) &gt; 0">
                    <xsl:value-of select="$arg-prefix"/>
                </xsl:when>
                <xsl:otherwise>32</xsl:otherwise>
            </xsl:choose>
        </xsl:variable>

        <xsl:variable name="a1" select="substring-before($addr, '.')"/>
        <xsl:variable name="a234" select="substring-after($addr, '.')"/>
        <xsl:variable name="a2" select="substring-before($a234, '.')"/>
        <xsl:variable name="a34" select="substring-after($a234, '.')"/>
        <xsl:variable name="a3" select="substring-before($a34, '.')"/>
        <xsl:variable name="a4" select="substring-after($a34, '.')"/>

        <xsl:variable name="r3">
            <xsl:choose>
                <xsl:when test="$a4 &lt; 255">
                    <xsl:value-of select="$a3"/>
                </xsl:when>
                <xsl:otherwise>
                    <xsl:value-of select="$a3 + 1"/>
                </xsl:otherwise>
            </xsl:choose>
        </xsl:variable>

        <xsl:variable name="r4">
            <xsl:choose>
                <xsl:when test="$a4 &lt; 255">
                    <xsl:value-of select="$a4 + 1"/>
                </xsl:when>
                <xsl:otherwise>
                    <xsl:value-of select="0"/>
                </xsl:otherwise>
            </xsl:choose>
        </xsl:variable>

        <xsl:value-of select="$a1"/>
        <xsl:text>.</xsl:text>
        <xsl:value-of select="$a2"/>
        <xsl:text>.</xsl:text>
        <xsl:value-of select="$r3"/>
        <xsl:text>.</xsl:text>
        <xsl:value-of select="$r4"/>
        <xsl:text>/</xsl:text>
        <xsl:value-of select="$prefix"/>
    </xsl:template>

</xsl:stylesheet>

SLAX Syntax

version 1.0;

ns junos = "http://xml.juniper.net/junos/*/junos";
ns xnm = "http://xml.juniper.net/xnm/1.1/xnm";
ns jcs = "http://xml.juniper.net/junos/commit-scripts/1.0";

import "../import/junos.xsl";
match configuration {
    for-each (interfaces/apply-macro) {
        var $device = name;
        var $address = data[name='address']/value;
        var $max = data[name='max']/value;
        var $unit = data[name='unit']/value;
        var $real-max = {
            if (string-length($max) > 0) {
                expr $max;

            } else {
                expr "0";
            }
        }
        var $real-unit = {
            if (string-length($unit) > 0) {
                expr $unit;

            } else if (contains($device, '.')) {
                expr substring-after($device, '.');

            } else {
                expr "0";
            }
        }
        var $real-device = {
            if (contains($device, '.')) {
                expr substring-before($device, '.');

            } else {
                expr $device;
            }
        }
        <transient-change> {
            <interfaces> {
                <interface> {
                    <name> $real-device;
                    call emit-interface($address, $unit = $real-unit, $max = $real-max);
                }
            }
        }
    }
}
emit-interface ($max, $unit, $address) {
    <unit> {
        <name> $unit;
        <vci> $unit;
        <family> {
            <inet> {
                <address> $address;
            }
        }
    }
    if ($max > $unit) {
        call emit-interface($unit = $unit + 1, $max) {
            with $address = {
                call next-address($address);
            }
        }
    }
}
next-address ($address) {
    var $arg-prefix = substring-after($address, '/');
    var $arg-addr = substring-before($address, '/');
    var $addr = {
        if (string-length($arg-addr) > 0) {
            expr $arg-addr;

        } else {
            expr $address;
        }
    }
    var $prefix = {
        if (string-length($arg-prefix) > 0) {
            expr $arg-prefix;

        } else {
            expr "32";
        }
    }
    var $a1 = substring-before($addr, '.');
    var $a234 = substring-after($addr, '.');
    var $a2 = substring-before($a234, '.');
    var $a34 = substring-after($a234, '.');
    var $a3 = substring-before($a34, '.');
    var $a4 = substring-after($a34, '.');
    var $r3 = {
        if ($a4 < 255) {
            expr $a3;

        } else {
            expr $a3 + 1;
        }
    }
    var $r4 = {
        if ($a4 < 255) {
            expr $a4 + 1;

        } else {
            expr 0;
        }
    }

    expr $a1;
    expr ".";
    expr $a2;
    expr ".";
    expr $r3;
    expr ".";
    expr $r4;
    expr "/";
    expr $prefix;
}

[Contents] [Prev] [Next] [Index] [Report an Error]