Schema Data

The schemadata module implements the following classes:

Doctest snippets for this module use the data model from Example 3.

>>> dm = DataModel.from_file("yang-library-ex3.json",
... [".", "../../../yang-modules/ietf"])
class yangson.schemadata.IdentityAdjacency

Objects of this class hold information about adjacencies of an identity, i.e. (i) its base identities and (ii) identities that are directly derived from it.

These objects are intended to be used only as values of the SchemaData.identity_adjs – each describes adjacencies of the identity appearing in the corresponding key (henceforth denoted as the “key identity”).

Instance Attributes

bases

Mutable set of qualified names of identities that are defined as bases of the key identity.

derivs

Mutable set of qualified names of identities that are directly derived from the key identity.

class yangson.schemadata.SchemaContext(schema_data: SchemaData, default_ns: YangIdentifier, text_mid: ModuleId)

An object of this class contains the current schema context that is passed along during the processing of YANG modules. Its instance attributes are initialized from constructor arguments of the same name.

Instance Attributes

schema_data

An object of the SchemaData class.

default_ns

Current default namespace (module name) that is assigned to unprefixed node identifiers. This attribute may differ from the namespace of the module identified by text_mid inside a grouping or typedef definition that is used in another module (see [RFC7950], sec. 6.4.1).

text_mid

Identifier of the current YANG module that defines the context for resolving namespace prefixes.

class yangson.schemadata.ModuleData(main_module: YangIdentifier)

An object of this class contains data related to a single module or submodule that is a part of the data model. Such objects are values of the dictionary SchemaData.modules.

The constructor argument main_module contains the value for main_module instance attribute.

Instance Attributes

features

Set of features defined in the receiver module that are supported by the data model.

main_module

This attribute contains the module identifier of the main module corresponding to the receiver.

prefix_map

Dictionary that maps prefixes declared in the receiver module to module identifiers.

statement

The module or submodule statement corresponding to the receiver. It is the entry point to the hierarchy of the (sub)module statements.

submodules

Set of submodules of the receiver module. If the receiver is a submodule, then this set is by definition empty.

class yangson.schemadata.Annotation(type: DataType, description: str)

An object of this class describes a metadata annotation [RFC7952].

Instance Attributes

type

Type of the annotation’s value.

description

Description string of the annotation.

class yangson.schemadata.SchemaData(yang_lib: Dict[str, Any], mod_path: List[str])

This class serves as a global for various data structures related to the schema that are extracted from YANG modules, and provides a number of methods for retrieving and processing this data.

The yang_lib constructor argument contains a dictionary with YANG library data [RFC7895] that is typically parsed from JSON text using the functions json.load() or json.loads(). The second constructor argument, mod_path, initializes the instance attribute module_search_path.

Instance Attributes

identity_adjs

Dictionary containing adjacency data of all identities defined by the data model.

The keys are qualified names of identities, and each value is an object of the IdentityAdjacency class.

>>> sorted(dm.schema_data.identity_adjs[('idZ', 'example-3-b')].bases)
[('idX', 'example-3-a'), ('idY', 'example-3-b')]
>>> dm.schema_data.identity_adjs[('idX', 'example-3-a')].derivs
{('idZ', 'example-3-b')}
implement

Dictionary of implemented modules. They correspond to YANG library entries that have conformance type implement. For each module, only one revision can be implemented – other revisions may be present but only with conformance type import.

The keys of this dictionary are module names, and the values are revision dates.

>>> dm.schema_data.implement['example-3-b']
'2016-08-22'
module_search_path

List of directories where to look for YANG modules.

All YANG modules and submodules listed in YANG library data have to be located in one of these directories.

>>> dm.schema_data.module_search_path
['.', '../../../yang-modules/ietf']
modules

Dictionary of modules and submodules comprising the data model.

The keys are module identifiers, and the values are objects of the ModuleData class.

>>> len(dm.schema_data.modules)
7
>>> dm.schema_data.modules[('example-3-a', '2017-08-01')].main_module
('example-3-a', '2017-08-01')
>>> dm.schema_data.modules[('example-3-suba', '2017-08-01')].main_module
('example-3-a', '2017-08-01')
>>> dm.schema_data.modules[('example-3-suba', '2017-08-01')].prefix_map['inet']
('ietf-inet-types', '2013-07-15')
>>> sorted(dm.schema_data.modules[('example-3-a', '2017-08-01')].features)
['fea1', 'fea2']
annotations

Dictionary of annotations that are defined in the modules comprising the data model. The keys are qualified names, of the annotations, and the values are objects of the Annotation class.

>>> list(dm.schema_data.annotations.keys())
[('last-modified', 'example-3-a')]
>>> str(dm.schema_data.annotations[('last-modified', 'example-3-a')].type)
'date-and-time(string)'

Public Methods

namespace(mid: ModuleId) → YangIdentifier

Return the namespace corresponding to a module or submodule. The argument mid is the module identifier of the (sub)module.

Note that Yangson uses main module module names rather than URIs as namespace identifiers.

This method raises ModuleNotRegistered if the (sub)module identified by mid is not part of the data model.

>>> dm.schema_data.namespace(('example-3-suba', '2017-08-01'))
'example-3-a'
last_revision(name: YangIdentifier) → ModuleId

Return module identifier of the most recent revision of a module or submodule name.

The method raises ModuleNotRegistered if no (sub)module of that name is part of the data model.

>>> dm.schema_data.last_revision('ietf-inet-types')
('ietf-inet-types', '2013-07-15')
prefix2ns(prefix: YangIdentifier, mid: ModuleId) → YangIdentifier

Return namespace identifier corresponding to prefix. The module or submodule context, in which the prefix is resolved, is specified by the mid argument.

This method raises ModuleNotRegistered if the (sub)module identified by mid is not part of the data model, and UnknownPrefix if prefix is not declared in that (sub)module.

>>> dm.schema_data.prefix2ns('oin', ('example-3-b', '2016-08-22'))
'ietf-inet-types'
resolve_pname(pname: PrefName, mid: ModuleId) → Tuple[YangIdentifier, ModuleId]

Resolve prefixed name pname and return a tuple consisting of an unprefixed name and a module identifier of the (sub)module in which that name is defined. The argument mid specifies the (sub)module in which pname is to be resolved. If pname has no prefix, mid is used as the second component of the result.

This method raises ModuleNotRegistered if the (sub)module identified by mid is not part of the data model, and UnknownPrefix if the prefix specified in pname is not declared in that (sub)module.

>>> dm.schema_data.resolve_pname('oin:port-number', ('example-3-b', '2016-08-22'))
('port-number', ('ietf-inet-types', '2010-09-24'))
translate_pname(pname: PrefName, mid: ModuleId) → QualName

Translate prefixed name pname to a qualified name. The argument mid specifies the (sub)module in which pname is to be resolved. If pname has no prefix, the namespace of the module identified by mid is assigned by default.

This method raises ModuleNotRegistered if the (sub)module identified by mid is not part of the data model, and UnknownPrefix if the prefix specified in pname is not declared in that (sub)module.

>>> dm.schema_data.translate_pname('oin:port-number', ('example-3-b', '2016-08-22'))
('port-number', 'ietf-inet-types')
translate_node_id(ni: PrefName, sctx:SchemaContext) → QualName

Translate node identifier ni to a qualified name. The argument sctx contains a SchemaContext in which ni is resolved.

This method raises ModuleNotRegistered if the (sub)module identified by the text_mid attribute of sctx is not part of the data model, and UnknownPrefix if the prefix specified in ni is not declared in that (sub)module.

>>> sctx1 = SchemaContext(dm.schema_data, 'example-3-b', ('example-3-a', '2017-08-01'))
>>> dm.schema_data.translate_node_id('bar', sctx1)
('bar', 'example-3-b')
prefix(imod: YangIdentifier, mid: ModuleId) → YangIdentifier

Return namespace prefix declared for implemented module imod in the module or submodule whose module identifier is mid.

This method may raise the following exceptions:

>>> dm.schema_data.prefix("example-3-a", ("example-3-b", "2016-08-22"))
'ex3a'
sni2route(sni: SchemaNodeId, sctx: SchemaContext) → SchemaRoute

Translate schema node identifier sni to a schema route. The argument sctx specifies the schema context in which sni is to be resolved.

This method raises ModuleNotRegistered if the (sub)module identified by mid is not part of the data model, and UnknownPrefix if a prefix specified in sni is not declared in that (sub)module.

>>> sctx2 = SchemaContext(dm.schema_data, 'example-3-b', ('example-3-b', '2016-08-22'))
>>> dm.schema_data.sni2route('/ex3a:top/ex3a:bar', sctx2)
[('top', 'example-3-a'), ('bar', 'example-3-a')]
static path2route(path: SchemaPath) → SchemaRoute

Translate schema path or data path in the path argument to a schema route or data route, respectively.

This method raises BadPath if path is not a valid schema or data path.

>>> dm.schema_data.path2route('/example-3-a:top/bar')
[('top', 'example-3-a'), ('bar', 'example-3-a')]
get_definition(stmt: Statement, sctx: SchemaContext) → Tuple[Statement, SchemaContext]

Find the grouping or typedef statement to which the statement in the stmt argument refers. The argument sctx specifies the schema context in which the name of the grouping or type is to be resolved. The returned value is a tuple consisting of the definition statement and a new SchemaContext in which the definition appears.

This method may raise the following exceptions:

  • ValueError – if the stmt statement is neither uses nor type statement.
  • ModuleNotRegistered – if the (sub)module identified by mid is not part of the data model.
  • UnknownPrefix – if the prefix specified in the argument of the stmt statement is not declared in the mid (sub)module.
  • DefinitionNotFound – if the corresponding definition statement is not found.
>>> bmod = dm.schema_data.modules[('example-3-b', '2016-08-22')].statement
>>> baztype = bmod.find1("augment").find1("leaf").find1("type")
>>> pn = dm.schema_data.get_definition(baztype, sctx2)
>>> pn[0].keyword
'typedef'
>>> pn[0].argument
'port-number'
>>> pn[1].text_mid
('ietf-inet-types', '2010-09-24')
is_derived_from(identity: QualName, base: QualName) → bool

Return True if the identity specified in the identity argument is derived (directly or transitively) from the identity base, otherwise return False.

>>> dm.schema_data.is_derived_from(('idZ', 'example-3-b'), ('idX', 'example-3-a'))
True
derived_from(identity: QualName) → MutableSet[QualName]

Return the set of qualified names of identities that are transitively derived from identity.

>>> dm.schema_data.derived_from(('idX', 'example-3-a'))
{('idZ', 'example-3-b')}
derived_from_all(identities: List[QualName]) → MutableSet[QualName]

Return the set of qualified names of identities that are transitively derived from all identities contained in the identities list.

>>> dm.schema_data.derived_from_all([('idX', 'example-3-a'), ('idY', 'example-3-b')])
{('idZ', 'example-3-b')}
>>> dm.schema_data.derived_from_all([('idX', 'example-3-a'), ('idZ', 'example-3-b')])
set()
if_features(stmt: Statement, mid: ModuleId) → bool

Evaluate all if-feature statements that are substatements of stmt. Return False if any of them is false, otherwise return True. If the statement stmt has no if-feature substatements, True is returned. The argument mid specifies the (sub)module in which features names are to be resolved.

This method may raise the following exceptions:

  • InvalidFeatureExpression – if the argument of an if-feature statement is not syntactically correct.
  • ModuleNotRegistered – if the (sub)module identified by mid is not part of the data model.
  • UnknownPrefix – if a prefix of a feature name is not declared in the mid (sub)module.
>>> amod = dm.schema_data.modules[('example-3-a', '2017-08-01')].statement
>>> foo = amod.find1("container").find1("leaf")
>>> dm.schema_data.if_features(foo, ('example-3-a', '2017-08-01'))
True
class yangson.schemadata.FeatureExprParser(text: str, schema_data: SchemaData, mid: ModuleId)

This class implements a parser and evaluator of expressions appearing in the argument of if-feature statements. It is a subclass of Parser.

The arguments of the class constructor are:

  • text – feature expression text to parse,
  • schema_data -
  • mid – value for mid attribute.

The constructor may raise ModuleNotRedistered if the (sub)module identified by mid is not part of the data model.

Instance Attributes

mid

This attribute is a module identifier of the (sub)module that provides context for parsing and evaluating the feature expression.

schema_data

This attribute contains a SchemaData object describing the current schema for which the feature expression is to be evaluated.

Two other instance attributes (input and offset) are inherited from the Parser class.

Public Methods

parse() → bool

Parse and evaluate a feature expression, and return the result.

This method may raise the following exceptions:

>>> from yangson.schemadata import FeatureExprParser
>>> FeatureExprParser('ex3a:fea1 and not (ex3a:fea1 or ex3a:fea2)',
... dm.schema_data, ('example-3-a', '2017-08-01')).parse()
False