For most configuration objects, the order in which the object or its children are created is not significant, because the JUNOS configuration management software stores and displays configuration objects in predetermined positions in the configuration hierarchy. However, some configuration objects—such as routing policies and firewall filters—consist of elements that must be processed and analyzed sequentially in order to produce the intended routing behavior.
This example ensures that a Border Gateway Protocol (BGP) global import policy is applied to all your BGP imports before any other import policies are applied.
This example automatically prepends the bgp_global_import policy in front of any other BGP import policies. If the bgp_global_import policy statement is not included in the configuration, an error message is emitted, and the commit operation fails.
Otherwise, the commit script uses the insert="before" JUNOScript attribute and the position() XSLT function to control the position of the global BGP policy in relation to any other applied policies. The insert="before" attribute inserts the bgp_global_import policy in front of the first preexisting BGP import policy.
If there is no preexisting default BGP import policy, the global policy is included in the configuration.
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:if test="not(policy-options/policy-statement[name='bgp_global_import'])">
<xnm:error>
<message>Policy error: Policy bgp_global_import required</message>
</xnm:error>
</xsl:if>
<xsl:for-each select="protocols/bgp | protocols/bgp/group | protocols/bgp/group/neighbor">
<xsl:variable name="first" select="import[position() = 1]"/>
<xsl:if test="$first">
<xsl:call-template name="jcs:emit-change">
<xsl:with-param name="tag" select="'transient-change'"/>
<xsl:with-param name="content">
<import insert="before" name="{$first}">bgp_global_import</import>
</xsl:with-param>
</xsl:call-template>
</xsl:if>
</xsl:for-each>
<xsl:for-each select="protocols/bgp">
<xsl:if test="not(import)">
<xsl:call-template name="jcs:emit-change">
<xsl:with-param name="tag" select="'transient-change'"/>
<xsl:with-param name="content">
<import>bgp_global_import</import>
</xsl:with-param>
</xsl:call-template>
</xsl:if>
</xsl:for-each>
</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 {
if (not(policy-options/policy-statement[name='bgp_global_import'])) {
<xnm:error> {
<message> "Policy error: Policy bgp_global_import required";
}
}
for-each (protocols/bgp | protocols/bgp/group | protocols/bgp/group/neighbor) {
var $first = import[position() = 1];
if ($first) {
call jcs:emit-change($tag = 'transient-change') {
with $content = {
<import insert="before" name="{$first}"> "bgp_global_import";
}
}
}
}
for-each (protocols/bgp) {
if (not(import)) {
call jcs:emit-change($tag = 'transient-change') {
with $content = {
<import> "bgp_global_import";
}
}
}
}
}
To test the example in this section, perform the following steps:
system {
scripts {
commit {
allow-transients;
file ex-bgp-global-import.xsl;
}
}
}
interfaces {
fe-0/0/0 {
unit 0 {
family inet {
address 192.168.16.2/24;
}
family inet6 {
address 2002:18a5:e996:beef::2/64;
}
}
}
}
routing-options {
autonomous-system 65400;
}
protocols {
bgp {
group fish {
neighbor 192.168.16.4 {
import [ blue green ];
peer-as 65401;
}
neighbor 192.168.16.6 {
peer-as 65402;
}
}
}
}
policy-options {
policy-statement blue {
from protocol bgp;
then accept;
}
policy-statement green {
then accept;
}
policy-statement bgp_global_import {
then accept;
}
}
- [edit]
- user@host# load merge terminal
- [Type ^D at a new line to end input]
- > Paste the contents of the clipboard here<
- [edit]
- user@host# commit
show protocols
When you issue the show protocols configuration mode command, the bgp_global_import import policy is not displayed because it is added as a transient change:
user@host# show protocols
bgp {
group fish {
neighbor 192.168.16.4 {
import [ blue green ];
peer-as 65401;
}
neighbor 192.168.16.6 {
peer-as 65402;
}
}
}
show protocols | display commit-scripts
The commit script adds the import bgp_global_import statement at the [edit protocols bgp] hierarchy level and prepends the bgp_global_import policy to the 192.168.16.4 neighbor policy chain:
user@host# show protocols | display commit-scripts
bgp {
import bgp_global_import;
group fish {
neighbor 192.168.16.4 {
import [ bgp_global_import blue green ];
peer-as 65401;
}
neighbor 192.168.16.6 {
peer-as 65402;
}
}
}
show protocols | display commit-scripts
After you add a policy to the 192.168.16.6 neighbor, which previously had no policies applied, the bgp_global_import policy is prepended:
user@host# set protocols bgp group fish neighbor 192.168.16.6 import green
user@host# show protocols | display commit-scripts
bgp {
import bgp_global_import;
group fish {
neighbor 192.168.16.4 {
import [ bgp_global_import blue green ];
peer-as 65401;
}
neighbor 192.168.16.6 {
import [ bgp_global_import green ];
peer-as 65402;
}
}
}