From 354c0475d65f0382e6c52b86b98f5c9f3b1a5e74 Mon Sep 17 00:00:00 2001 From: Igor Foltin Date: Wed, 5 Oct 2016 09:00:07 +0200 Subject: [PATCH] Bug 6771: Problem with typedefs nested in augment When a typedef is nested in a container that is in an augment, the YANG parser produces an error. This is due to fact, that typedef statements nested in augments are ignored in statement definition phase, because AugmentStatement is supported only in full definition phase. The same issue occurs also for Choice and Case statements. This patch provides fix of these bugs. This patch is a manual cherry-pick of the following patch: git.opendaylight.org/gerrit/#/c/46223/ Change-Id: I345fd50e7d9810bbedcc873241338fbdb3186b74 Signed-off-by: Peter Kajsa Signed-off-by: Igor Foltin --- .../stmt/rfc6020/TypedefStatementImpl.java | 17 ++-- .../yangtools/yang/stmt/Bug6771Test.java | 80 +++++++++++++++++++ .../bugs/bug6771/augment/typedef-bug.yang | 26 ++++++ .../bugs/bug6771/choice-case/typedef-bug.yang | 45 +++++++++++ .../bugs/bug6771/grouping/typedef-bug.yang | 21 +++++ 5 files changed, 178 insertions(+), 11 deletions(-) create mode 100644 yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/stmt/Bug6771Test.java create mode 100644 yang/yang-parser-impl/src/test/resources/bugs/bug6771/augment/typedef-bug.yang create mode 100644 yang/yang-parser-impl/src/test/resources/bugs/bug6771/choice-case/typedef-bug.yang create mode 100644 yang/yang-parser-impl/src/test/resources/bugs/bug6771/grouping/typedef-bug.yang diff --git a/yang/yang-parser-impl/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/rfc6020/TypedefStatementImpl.java b/yang/yang-parser-impl/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/rfc6020/TypedefStatementImpl.java index b96a2708e4..0d845ca773 100644 --- a/yang/yang-parser-impl/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/rfc6020/TypedefStatementImpl.java +++ b/yang/yang-parser-impl/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/rfc6020/TypedefStatementImpl.java @@ -65,24 +65,19 @@ public class TypedefStatementImpl extends AbstractDeclaredStatement imple } @Override - public void onStatementDefinitionDeclared( - final StmtContext.Mutable> stmt) { + public void onFullDefinitionDeclared(final StmtContext.Mutable> stmt) { + super.onFullDefinitionDeclared(stmt); + SUBSTATEMENT_VALIDATOR.validate(stmt); if (stmt != null && stmt.getParentContext() != null) { - final StmtContext existing = - stmt.getParentContext().getFromNamespace(TypeNamespace.class, stmt.getStatementArgument()); + final StmtContext existing = stmt.getParentContext() + .getFromNamespace(TypeNamespace.class, stmt.getStatementArgument()); SourceException.throwIf(existing != null, stmt.getStatementSourceReference(), "Duplicate name for typedef %s", stmt.getStatementArgument()); stmt.getParentContext().addContext(TypeNamespace.class, stmt.getStatementArgument(), stmt); } } - - @Override - public void onFullDefinitionDeclared(final StmtContext.Mutable> stmt) throws SourceException { - super.onFullDefinitionDeclared(stmt); - SUBSTATEMENT_VALIDATOR.validate(stmt); - } } @Nullable diff --git a/yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/stmt/Bug6771Test.java b/yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/stmt/Bug6771Test.java new file mode 100644 index 0000000000..3c636f090b --- /dev/null +++ b/yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/stmt/Bug6771Test.java @@ -0,0 +1,80 @@ +/* + * Copyright (c) 2016 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.yangtools.yang.stmt; + +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertTrue; + +import java.io.FileNotFoundException; +import java.net.URISyntaxException; +import org.junit.Test; +import org.opendaylight.yangtools.yang.common.QName; +import org.opendaylight.yangtools.yang.model.api.LeafSchemaNode; +import org.opendaylight.yangtools.yang.model.api.SchemaContext; +import org.opendaylight.yangtools.yang.model.api.SchemaNode; +import org.opendaylight.yangtools.yang.model.api.SchemaPath; +import org.opendaylight.yangtools.yang.model.api.type.UnsignedIntegerTypeDefinition; +import org.opendaylight.yangtools.yang.model.util.SchemaContextUtil; +import org.opendaylight.yangtools.yang.parser.spi.meta.ReactorException; +import org.opendaylight.yangtools.yang.parser.spi.source.SourceException; +import org.opendaylight.yangtools.yang.stmt.test.StmtTestUtils; + +public class Bug6771Test { + private static final String NS = "http://www.example.com/typedef-bug"; + private static final String REV = "1970-01-01"; + private static final QName ROOT = QName.create(NS, REV, "root"); + private static final QName CONT_B = QName.create(NS, REV, "container-b"); + private static final QName LEAF_CONT_B = QName.create(NS, REV, "leaf-container-b"); + private static final QName INNER_CONTAINER = QName.create(NS, REV, "inner-container"); + + @Test + public void augmentTest() throws SourceException, FileNotFoundException, ReactorException, URISyntaxException { + final SchemaContext context = StmtTestUtils.parseYangSources("/bugs/bug6771/augment"); + assertNotNull(context); + + verifyLeafType(SchemaContextUtil + .findDataSchemaNode(context, SchemaPath.create(true, ROOT, CONT_B, LEAF_CONT_B))); + verifyLeafType(SchemaContextUtil.findDataSchemaNode(context, + SchemaPath.create(true, ROOT, CONT_B, INNER_CONTAINER, LEAF_CONT_B))); + } + + @Test + public void choiceCaseTest() throws SourceException, FileNotFoundException, ReactorException, URISyntaxException { + final SchemaContext context = StmtTestUtils.parseYangSources("/bugs/bug6771/choice-case"); + assertNotNull(context); + + final QName myChoice = QName.create(NS, REV, "my-choice"); + final QName caseOne = QName.create(NS, REV, "one"); + final QName caseTwo = QName.create(NS, REV, "two"); + final QName caseThree = QName.create(NS, REV, "three"); + final QName containerOne = QName.create(NS, REV, "container-one"); + final QName containerTwo = QName.create(NS, REV, "container-two"); + final QName containerThree = QName.create(NS, REV, "container-three"); + + verifyLeafType(SchemaContextUtil.findDataSchemaNode(context, + SchemaPath.create(true, ROOT, myChoice, caseOne, containerOne, LEAF_CONT_B))); + verifyLeafType(SchemaContextUtil.findDataSchemaNode(context, + SchemaPath.create(true, ROOT, myChoice, caseTwo, containerTwo, LEAF_CONT_B))); + verifyLeafType(SchemaContextUtil.findDataSchemaNode(context, + SchemaPath.create(true, ROOT, myChoice, caseThree, containerThree, INNER_CONTAINER, LEAF_CONT_B))); + } + + @Test + public void groupingTest() throws SourceException, FileNotFoundException, ReactorException, URISyntaxException { + final SchemaContext context = StmtTestUtils.parseYangSources("/bugs/bug6771/grouping"); + assertNotNull(context); + verifyLeafType(SchemaContextUtil + .findDataSchemaNode(context, SchemaPath.create(true, ROOT, CONT_B, LEAF_CONT_B))); + } + + private static void verifyLeafType(final SchemaNode schemaNode) { + assertTrue(schemaNode instanceof LeafSchemaNode); + assertTrue(((LeafSchemaNode) schemaNode).getType() instanceof UnsignedIntegerTypeDefinition); + } + +} diff --git a/yang/yang-parser-impl/src/test/resources/bugs/bug6771/augment/typedef-bug.yang b/yang/yang-parser-impl/src/test/resources/bugs/bug6771/augment/typedef-bug.yang new file mode 100644 index 0000000000..d006c70f58 --- /dev/null +++ b/yang/yang-parser-impl/src/test/resources/bugs/bug6771/augment/typedef-bug.yang @@ -0,0 +1,26 @@ +module typedef-bug { + namespace "http://www.example.com/typedef-bug"; + prefix tdb; + + container root { + } + + augment "/root" { + container container-b { + + leaf leaf-container-b { + type type-container-b; + } + + typedef type-container-b { + type uint32; + } + + container inner-container { + leaf leaf-container-b { + type type-container-b; + } + } + } + } +} diff --git a/yang/yang-parser-impl/src/test/resources/bugs/bug6771/choice-case/typedef-bug.yang b/yang/yang-parser-impl/src/test/resources/bugs/bug6771/choice-case/typedef-bug.yang new file mode 100644 index 0000000000..4d1e0d288b --- /dev/null +++ b/yang/yang-parser-impl/src/test/resources/bugs/bug6771/choice-case/typedef-bug.yang @@ -0,0 +1,45 @@ +module typedef-bug { + namespace "http://www.example.com/typedef-bug"; + prefix tdb; + + container root { + choice my-choice { + case one { + container container-one { + + typedef type-container-b { + type uint32; + } + + leaf leaf-container-b { + type type-container-b; + } + } + } + case two { + container container-two { + + leaf leaf-container-b { + type type-container-b; + } + + typedef type-container-b { + type uint32; + } + } + } + case three { + container container-three { + container inner-container { + leaf leaf-container-b { + type type-container-b; + } + } + typedef type-container-b { + type uint32; + } + } + } + } + } +} diff --git a/yang/yang-parser-impl/src/test/resources/bugs/bug6771/grouping/typedef-bug.yang b/yang/yang-parser-impl/src/test/resources/bugs/bug6771/grouping/typedef-bug.yang new file mode 100644 index 0000000000..51037a6bdb --- /dev/null +++ b/yang/yang-parser-impl/src/test/resources/bugs/bug6771/grouping/typedef-bug.yang @@ -0,0 +1,21 @@ +module typedef-bug { + namespace "http://www.example.com/typedef-bug"; + prefix tdb; + + container root { + uses grp; + } + + grouping grp { + container container-b { + + typedef type-container-b { + type uint32; + } + + leaf leaf-container-b { + type type-container-b; + } + } + } +} -- 2.36.6