Skip to content
Snippets Groups Projects
Commit 68c8d986 authored by Ladislav Lhotka's avatar Ladislav Lhotka
Browse files

Consolidate tests and examples.

parent 30694f5b
Branches
Tags
No related merge requests found
......@@ -42,7 +42,7 @@ __ http://www.sphinx-doc.org/en/stable/ext/doctest.html
.. doctest::
>>> dm = DataModel.from_file("yang-library-ex3.json",
... [".", "../../../examples/ietf"])
... [".", "../../../yang-modules/ietf"])
.. class:: ModuleData(main_module: YangIdentifier)
......@@ -141,7 +141,7 @@ __ http://www.sphinx-doc.org/en/stable/ext/doctest.html
.. doctest::
>>> Context.module_search_path
['.', '../../../examples/ietf']
['.', '../../../yang-modules/ietf']
.. attribute:: modules
......
......@@ -54,7 +54,7 @@ __ http://www.sphinx-doc.org/en/stable/ext/doctest.html
.. doctest::
>>> dm = DataModel.from_file('yang-library-ex5.json',
... mod_path=[".", "../../../examples/ietf"])
... mod_path=[".", "../../../yang-modules/ietf"])
>>> binary_t = dm.get_data_node('/example-5-a:binary-leaf').type
>>> bits_t = dm.get_data_node('/example-5-a:bits-leaf').type
>>> boolean_t = dm.get_data_node('/example-5-a:boolean-leaf').type
......
*/Makefile
*.dsdl
*.rng
*.rnc
*.xml
*.xsl
*.yin
model.tree
test.py
# This Makefile is designed to be run from a subdirectory of examples/docs
yams = $(patsubst %.yin,%.yang,$(wildcard *.yin))
EXAMPLE_BASE = example
EXAMPLE_TARGET = data
PYANG_OPTS =
IETF_DIR = ../../../examples/ietf
baty = $(EXAMPLE_BASE)-$(EXAMPLE_TARGET)
export YANG_MODPATH ?= .:$(IETF_DIR)
xsldir = ../../../tools/xslt
schemas = $(baty).rng $(baty).sch $(baty).dsrl
y2dopts = -t $(EXAMPLE_TARGET) -b $(EXAMPLE_BASE)
ylfile = yang-library-$(lastword $(subst /, ,$(abspath .))).json
rngparms = --stringparam target $(EXAMPLE_TARGET) \
--stringparam basename $(EXAMPLE_BASE) \
--stringparam schema-dir $(PYANG_RNG_LIBDIR) \
$(PYANG_XSLT_DIR)/gen-relaxng.xsl
.PHONY: all clean commit json rnc skel yang
all: $(ylfile) $(baty).json
yang: $(yams)
json: $(baty).json
schema: $(schemas)
rnc: $(baty).rnc
hello.xml: $(yams)
@echo '<hello xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">' > $@
@echo '<capabilities>' >> $@
@echo '<capability>urn:ietf:params:netconf:base:1.1</capability>' >> $@
@for m in $(yams); do \
capa=$$(pyang $(PYANG_OPTS) -f capability --capability-entity $$m); \
if [ "$$capa" != "" ]; then \
echo "<capability>$$capa</capability>" >> $@; \
fi \
done
@echo '</capabilities>' >> $@
@echo '</hello>' >> $@
../yang-library.xsl: $(IETF_DIR)/ietf-yang-library@2016-06-21.yang
@pyang $(PYANG_OPTS) -f jsonxsl -o $@ $<
$(ylfile): hello.xml ../yang-library.xsl
@xsltproc $(xsldir)/hello2yanglib.xsl $< | \
xsltproc -o $@ ../yang-library.xsl -
%.yang: %.yin
@xsltproc --xinclude $(xsldir)/canonicalize.xsl $< | \
xsltproc --output $@ $(yypars) $(xsldir)/yin2yang.xsl -
$(baty).dsdl: hello.xml
@pyang $(PYANG_OPTS) -f dsdl -o $@ -L $<
$(baty).rng: $(baty).dsdl
@xsltproc --output $@ $(rngparms) $<
$(EXAMPLE_BASE)-gdefs.rng: $(baty).dsdl
@xsltproc --output $@ --stringparam gdefs-only 1 $(rngparms) $<
$(baty).rnc: $(baty).rng $(EXAMPLE_BASE)-gdefs.rng
@trang -I rng -O rnc $< $@
$(baty).json: model.xsl $(baty).xml
@xsltproc --output $@ $^
model.xsl: hello.xml
@pyang $(PYANG_OPTS) -o $@ -f jsonxsl -L $<
model.tree: hello.xml
@pyang $(PYANG_OPTS) -f tree -o $@ -L $<
skel: hello.xml
@pyang $(PYANG_OPTS) -f sample-xml-skeleton \
--sample-xml-skeleton-defaults -L $< | \
xmllint -o $(baty).xml --format -
commit: $(yams) $(baty).json $(ylfile)
@git add $^
@git commit
clean:
@rm -rf *.rng *.rnc *.dsdl *.xsl model.tree
<?xml version="1.0" encoding="utf-8"?>
<module name="example-n"
xmlns="urn:ietf:params:xml:ns:yang:yin:1">
<yang-version value="1.1"/>
<namespace uri="http://example.com/example-n"/>
<prefix value="exn"/>
</module>
......@@ -57,7 +57,7 @@ __ http://www.sphinx-doc.org/en/stable/ext/doctest.html
.. doctest::
>>> dm = DataModel.from_file('yang-library-ex4.json',
... mod_path=[".", "../../../examples/ietf"])
... mod_path=[".", "../../../yang-modules/ietf"])
>>> fsn = dm.get_schema_node("/example-4-a:bag/foo")
>>> rsn = dm.get_schema_node("/example-4-a:bag/opts/example-4-b:fooref/fooref")
>>> with open("example-data.json") as infile:
......
......@@ -28,7 +28,7 @@ __ http://www.sphinx-doc.org/en/stable/ext/doctest.html
.. doctest::
>>> dm = DataModel.from_file("yang-library-ex4.json",
... [".", "../../../examples/ietf"])
... [".", "../../../yang-modules/ietf"])
>>> with open("example-data.json") as infile:
... ri = json.load(infile)
>>> inst = dm.from_raw(ri)
......
......@@ -79,8 +79,8 @@ tree = """+--rw (test:choiA)?
@pytest.fixture
def data_model():
return DataModel.from_file("examples/test/yang-library-data.json",
["examples/test", "examples/ietf"])
return DataModel.from_file("yang-modules/test/yang-library-data.json",
["yang-modules/test", "yang-modules/ietf"])
@pytest.fixture
def instance(data_model):
......
import pytest
from yangson import DataModel
from yangson.schema import NonexistentSchemaNode
from yangson.context import Context, BadPath
@pytest.fixture
def data_model():
tpath = ["examples/turing/"]
with open("examples/turing/yang-library.json", encoding="utf-8") as ylfile:
ylib = ylfile.read()
return DataModel(ylib, tpath)
def test_schema_nodes(data_model):
top = data_model.get_data_node("/turing-machine:turing-machine")
assert top.instance_name() == "turing-machine:turing-machine"
assert top.config == True
assert len(top.state_roots()) == 5
nonex = top.get_child("NONEXISTENT")
assert nonex is None
with pytest.raises(NonexistentSchemaNode):
data_model.parse_instance_id("/turing-machine:turing-machine/ftate")
state = top.get_child("state")
assert state.config == False
assert state.state_roots() == [["turing-machine:turing-machine", "state"]]
with pytest.raises(BadPath):
Context.path2route("transition-function")
label = top.get_schema_descendant(Context.path2route(
"turing-machine:transition-function/delta/label"))
assert label.config == True
def test_feature_expr(data_model):
assert Context.feature_expr(
"head-stay or not tm:head-stay and not tm:head-stay",
("turing-machine", None)) == True
assert Context.feature_expr(
"(head-stay or not tm:head-stay) and not tm:head-stay",
("turing-machine", None)) == False
module second-tape {
namespace "http://example.net/turing-machine/tape-2";
prefix "t2";
import turing-machine {
prefix "tm";
}
augment "/tm:turing-machine" {
description
"State data for the second tape.";
leaf head-position-2 {
type tm:cell-index;
config "false";
description
"Head position of the second tape.";
}
container tape-2 {
config "false";
description
"Contents of the second tape.";
uses tm:tape-cells;
}
}
augment
"/tm:turing-machine/tm:transition-function/tm:delta/tm:input" {
description
"A new input parameter.";
leaf symbol-2 {
type tm:tape-symbol;
description
"Symbol read from the second tape.";
}
}
augment
"/tm:turing-machine/tm:transition-function/tm:delta/tm:output" {
description
"New output parameters.";
leaf symbol-2 {
type tm:tape-symbol;
description
"Symbol to be written to the second tape. If this leaf is not
present, the symbol doesn't change.";
}
leaf head-move-2 {
type tm:head-dir;
description
"Motion of the second tape's head.";
}
}
augment "/tm:initialize/tm:input" {
description
"A new RPC input parameter.";
leaf tape-content-2 {
type string;
description
"Initial content of the second tape.";
}
}
}
{
"turing-machine:turing-machine": {
"transition-function": {
"delta": [
{
"label": "both-a",
"input": {
"state": 0,
"symbol": "a",
"second-tape:symbol-2": "a"
}
},
{
"label": "both-b",
"input": {
"state": 0,
"symbol": "b",
"second-tape:symbol-2": "b"
}
},
{
"label": "end",
"input": {
"state": 0,
"symbol": "",
"second-tape:symbol-2": ""
},
"output": {
"state": 1
}
}
]
}
}
}
module turing-machine {
yang-version "1.1";
namespace "http://example.net/turing-machine";
prefix "tm";
description
"Data model for the Turing Machine.";
/* Features */
feature head-stay {
description
"This feature indicates support for the 'stay' option for
read-write head motion.";
}
/* Typedefs */
typedef tape-symbol {
type string {
length "0..1";
}
description
"Type of symbols appearing in tape cells.
A blank is represented as an empty string where necessary.";
}
typedef cell-index {
type int64;
description
"Type for indexing tape cells.";
}
typedef state-index {
type uint16;
description
"Type for indexing states of the control unit.";
}
typedef head-dir {
type enumeration {
enum left;
enum right;
enum stay {
if-feature "head-stay";
}
}
default "right";
description
"Possible directions for moving the read/write head, one cell
to the left or right (default).
Feature 'head-stay' adds the third option, 'stay', which means
that the head doesn't move.";
}
/* Groupings */
grouping tape-cells {
description
"The tape of the Turing Machine is represented as a sparse
array.";
list cell {
key "coord";
description
"List of non-blank cells.";
leaf coord {
type cell-index;
description
"Coordinate (index) of the tape cell.";
}
leaf symbol {
type tape-symbol {
length "1";
}
description
"Symbol appearing in the tape cell.
Blank (empty string) is not allowed here because the
'cell' list only contains non-blank cells.";
}
}
}
/* State data and Configuration */
container turing-machine {
description
"State data and configuration of a Turing Machine.";
leaf state {
type state-index;
config "false";
mandatory "true";
description
"Current state of the control unit.
The initial state is 0.";
}
leaf head-position {
type cell-index;
config "false";
mandatory "true";
description
"Position of tape read/write head.";
}
container tape {
config "false";
description
"The contents of the tape.";
uses tape-cells;
}
container transition-function {
description
"The Turing Machine is configured by specifying the
transition function.";
list delta {
key "label";
unique "input/state input/symbol";
description
"The list of transition rules.";
leaf label {
type string;
description
"An arbitrary label of the transition rule.";
}
container input {
description
"Input parameters (arguments) of the transition rule.";
leaf state {
type state-index;
mandatory "true";
description
"Current state of the control unit.";
}
leaf symbol {
type tape-symbol;
mandatory "true";
description
"Symbol read from the tape cell.";
}
}
container output {
description
"Output values of the transition rule.";
leaf state {
type state-index;
description
"New state of the control unit. If this leaf is not
present, the state doesn't change.";
}
leaf symbol {
type tape-symbol;
description
"Symbol to be written to the tape cell. If this leaf is
not present, the symbol doesn't change.";
}
leaf head-move {
type head-dir;
description
"Head motion.";
}
}
}
}
}
/* RPCs */
rpc initialize {
description
"Initialize the Turing Machine as follows:
1. Put the control unit into the initial state (0).
2. Move the read/write head to the tape cell with coordinate
zero.
3. Write the string from the 'tape-content' input parameter to
the tape, character by character, starting at cell 0. The
tape is othewise empty.";
input {
leaf tape-content {
type string;
default "";
description
"The string with which the tape shall be initialized. The
leftmost symbol will be at tape coordinate 0.";
}
}
}
rpc run {
description
"Start the Turing Machine operation.";
}
/* Notifications */
notification halted {
description
"The Turing Machine has halted. This means that there is no
transition rule for the current state and tape symbol.";
leaf state {
type state-index;
mandatory "true";
description
"The state of the control unit in which the machine has
halted.";
}
}
}
{
"ietf-yang-library:modules-state": {
"module-set-id": "",
"module": [
{
"name": "turing-machine",
"revision": "",
"namespace": "http://example.net/turing-machine",
"feature": ["head-stay"],
"conformance-type": "implement"
},
{
"name": "second-tape",
"revision": "",
"namespace": "http://example.net/turing-machine/tape-2",
"conformance-type": "implement"
}
]
}
}
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment