Source code for jnpr.junos.jxml

from ncclient import manager
from ncclient.xml_ import NCElement
from lxml import etree
import six

  These are Junos XML 'helper' definitions use for generic XML processing

  .DEL to delete an item
  .REN to rename an item, requires the use of NAME()

  .INSERT(<'before'|'after'>) to reorder an item, requires the use of NAME()
  .BEFORE to reorder an item before another, requires the use of NAME()
  .AFTER to reorder an item after another, requires the use of NAME()

  .NAME(name) to assign the name attribute


DEL = {"delete": "delete"}  # Junos XML resource delete
REN = {"rename": "rename"}  # Junos XML resource rename
ACTIVATE = {"active": "active"}  # activate resource
DEACTIVATE = {"inactive": "inactive"}  # deactivate resource
REPLACE = {"replace": "replace"}  # replace elements

[docs]def NAME(name): return {"name": name}
[docs]def INSERT(cmd): return {"insert": cmd}
BEFORE = {"insert": "before"} AFTER = {"insert": "after"} # used with <get-configuration> to load only the object identifiers and # not all the subsequent configuration NAMES_ONLY = {"recurse": "false"} # for <get-configuration>, attributes to retrieve from apply-groups INHERIT = {"inherit": "inherit"} INHERIT_GROUPS = {"inherit": "inherit", "groups": "groups"} INHERIT_DEFAULTS = {"inherit": "defaults", "groups": "groups"} # XSLT for on-box commit script conf_xslt = """\ <xsl:stylesheet xmlns:xsl="" version="1.0"> <xsl:output method="xml" indent="yes"/> <xsl:strip-space elements="*"/> <xsl:param name="subSelectionXPath" /> <xsl:template match="/"> <xsl:apply-templates select="$subSelectionXPath/ancestor::*[position()=last()]"/> </xsl:template> <xsl:template match="*"> <xsl:choose> <xsl:when test="$subSelectionXPath/ancestor::* [generate-id() = generate-id(current())]"> <xsl:copy> <xsl:copy-of select="@*"/> <xsl:choose> <xsl:when test="generate-id(.)= generate-id($subSelectionXPath/ancestor::*[1])"> <xsl:copy-of select="$subSelectionXPath"/> </xsl:when> <xsl:otherwise> <xsl:apply-templates select="*"/> </xsl:otherwise> </xsl:choose> </xsl:copy> </xsl:when> <xsl:otherwise/> </xsl:choose> </xsl:template> </xsl:stylesheet>""" conf_xslt_root = etree.XML(conf_xslt) conf_transform = etree.XSLT(conf_xslt_root) normalize_xslt = """\ <xsl:stylesheet version="1.0" xmlns:xsl=""> <xsl:output method="xml" indent="no"/> <xsl:template match="/*[local-name()='rpc-reply']/*[local-name()='output']"> <xsl:copy-of select="."/> </xsl:template> <xsl:template match="/|comment()|processing-instruction()"> <xsl:copy> <xsl:apply-templates/> </xsl:copy> </xsl:template> <xsl:template match="*"> <xsl:element name="{local-name()}"> <xsl:apply-templates select="@*|node()"/> </xsl:element> </xsl:template> <xsl:template match="@*"> <xsl:attribute name="{local-name()}"> <xsl:value-of select="."/> </xsl:attribute> </xsl:template> <xsl:template match="text()"> <xsl:value-of select="normalize-space(.)"/> </xsl:template> </xsl:stylesheet>""" # XSLT to strip comments strip_comments_xslt = """\ <xsl:stylesheet version="1.0" xmlns:xsl=""> <xsl:output omit-xml-declaration="yes" indent="yes"/> <xsl:strip-space elements="*"/> <xsl:template match="node()|@*" name="identity"> <xsl:copy> <xsl:apply-templates select="node()|@*"/> </xsl:copy> </xsl:template> <xsl:template match="comment()"/> </xsl:stylesheet>""" strip_xslt_root = etree.XML(strip_comments_xslt) strip_comments_transform = etree.XSLT(strip_xslt_root) # XSLT to strip <rpc-error> elements strip_rpc_error_xslt = """ <xsl:stylesheet version="1.0" xmlns:xsl=""> <xsl:output omit-xml-declaration="yes" indent="yes"/> <xsl:strip-space elements="*"/> <xsl:template match="node()|@*"> <xsl:copy> <xsl:apply-templates select="node()|@*"/> </xsl:copy> </xsl:template> <xsl:template match="rpc-error"/> </xsl:stylesheet> """ strip_rpc_error_root = etree.XML(strip_rpc_error_xslt) strip_rpc_error_transform = etree.XSLT(strip_rpc_error_root)
[docs]def remove_namespaces(xml): for elem in xml.getiterator(): if elem.tag is etree.Comment: continue i = elem.tag.find("}") if i > 0: elem.tag = elem.tag[i + 1 :] return xml
[docs]def remove_namespaces_and_spaces(xml): for elem in xml.getiterator(): if elem.tag is etree.Comment: continue # Remove namespace from attributes for k, v in elem.attrib.items(): i = k.find("}") if i >= 0: del elem.attrib[k] k = k[i + 1 :] elem.set(k, v) # Remove namespace from tags i = elem.tag.find("}") if i >= 0: elem.tag = elem.tag[i + 1 :] # remove white spaces from text if elem.text: elem.text = elem.text.strip() return xml
[docs]def rpc_error(rpc_xml): """ extract the various bits from an <rpc-error> element into a dictionary """ remove_namespaces(rpc_xml) if "rpc-reply" == rpc_xml.tag: rpc_xml = rpc_xml[0] def find_strip(x): ele = rpc_xml.find(x) return ele.text.strip() if ele is not None and ele.text is not None else None this_err = {} this_err["severity"] = find_strip("error-severity") this_err["source"] = find_strip("source-daemon") this_err["edit_path"] = find_strip("error-path") this_err["bad_element"] = find_strip("error-info/bad-element") this_err["message"] = find_strip("error-message") return this_err
[docs]def cscript_conf(reply): try: device_params = {"name": "junos"} device_handler = manager.make_device_handler(device_params) transform_reply = device_handler.transform_reply() return NCElement(reply, transform_reply)._NCElement__doc except: return None
# xslt to remove prefix like junos:ns strip_namespaces_prefix = six.b( """<?xml version="1.0" encoding="UTF-8" ?> <xsl:stylesheet version="1.0" xmlns:xsl=""> <xsl:output method="xml" indent="no" omit-xml-declaration="no" /> <xsl:template match="/ |comment() |processing-instruction()"> <xsl:copy> <xsl:apply-templates select="/*" /> </xsl:copy> </xsl:template> <xsl:template match="*"> <xsl:element name="{local-name()}" namespace="{namespace-uri()}"> <xsl:apply-templates select="@*|node()" /> </xsl:element> </xsl:template> <xsl:template match="@*"> <xsl:attribute name="{local-name()}"> <xsl:value-of select="." /> </xsl:attribute> </xsl:template> </xsl:stylesheet>""" )