Bug 9241: Action definition should implicitly define input/output 01/64301/2
authorIgor Foltin <igor.foltin@pantheon.tech>
Fri, 13 Oct 2017 10:02:58 +0000 (12:02 +0200)
committerRobert Varga <nite@hq.sk>
Tue, 17 Oct 2017 08:48:19 +0000 (08:48 +0000)
Empty input and output statements are now automatically added to
every action statement that does not declare them explicitly.

Change-Id: I41c037657e83b8e53d314d9b9c6c691ef99e993f
Signed-off-by: Igor Foltin <igor.foltin@pantheon.tech>
yang/yang-parser-impl/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/rfc7950/ActionStatementImpl.java
yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/parser/stmt/rfc7950/Bug9241Test.java [new file with mode: 0644]
yang/yang-parser-impl/src/test/resources/rfc7950/bug9241/foo.yang [new file with mode: 0644]

index 4ccef75a1bbdf4b13af3e6f759eb1507a5a30dcb..93b4b8eb0b469d9fa8547057568a6ee076b8baf8 100644 (file)
@@ -28,10 +28,14 @@ import org.opendaylight.yangtools.yang.model.api.stmt.StatusStatement;
 import org.opendaylight.yangtools.yang.model.api.stmt.TypedefStatement;
 import org.opendaylight.yangtools.yang.parser.spi.meta.AbstractDeclaredStatement;
 import org.opendaylight.yangtools.yang.parser.spi.meta.AbstractStatementSupport;
+import org.opendaylight.yangtools.yang.parser.spi.meta.StatementSupport;
 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContext;
 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContextUtils;
 import org.opendaylight.yangtools.yang.parser.spi.meta.SubstatementValidator;
+import org.opendaylight.yangtools.yang.parser.spi.source.ImplicitSubstatement;
 import org.opendaylight.yangtools.yang.parser.spi.source.SourceException;
+import org.opendaylight.yangtools.yang.parser.stmt.reactor.StatementContextBase;
+import org.opendaylight.yangtools.yang.parser.stmt.reactor.StatementDefinitionContext;
 import org.opendaylight.yangtools.yang.parser.stmt.rfc6020.ChildSchemaNodes;
 import org.opendaylight.yangtools.yang.parser.stmt.rfc7950.effective.ActionEffectiveStatementImpl;
 
@@ -57,6 +61,8 @@ public class ActionStatementImpl extends AbstractDeclaredStatement<QName> implem
 
         private static final Set<StatementDefinition> ILLEGAL_PARENTS = ImmutableSet.of(YangStmtMapping.NOTIFICATION,
                 YangStmtMapping.RPC, YangStmtMapping.ACTION);
+        private static final StatementSupport<?, ?, ?> IMPLICIT_INPUT = new InputStatementRfc7950Support();
+        private static final StatementSupport<?, ?, ?> IMPLICIT_OUTPUT = new OutputStatementRfc7950Support();
 
         public Definition() {
             super(YangStmtMapping.ACTION);
@@ -97,10 +103,32 @@ public class ActionStatementImpl extends AbstractDeclaredStatement<QName> implem
             return new ActionEffectiveStatementImpl(ctx);
         }
 
+        @Override
+        public void onFullDefinitionDeclared(final StmtContext.Mutable<QName, ActionStatement,
+                EffectiveStatement<QName, ActionStatement>> stmt) {
+            super.onFullDefinitionDeclared(stmt);
+
+            if (StmtContextUtils.findFirstDeclaredSubstatement(stmt, InputStatement.class) == null) {
+                addImplicitStatement((StatementContextBase<?, ?, ?>) stmt, IMPLICIT_INPUT);
+            }
+
+            if (StmtContextUtils.findFirstDeclaredSubstatement(stmt, OutputStatement.class) == null) {
+                addImplicitStatement((StatementContextBase<?, ?, ?>) stmt, IMPLICIT_OUTPUT);
+            }
+        }
+
         @Override
         protected SubstatementValidator getSubstatementValidator() {
             return SUBSTATEMENT_VALIDATOR;
         }
+
+        private static void addImplicitStatement(final StatementContextBase<?, ?, ?> parent,
+            final StatementSupport<?, ?, ?> statementToAdd) {
+            final StatementDefinitionContext<?, ?, ?> stmtDefCtx = new StatementDefinitionContext<>(statementToAdd);
+
+            parent.createSubstatement(parent.declaredSubstatements().size(), stmtDefCtx,
+                    ImplicitSubstatement.of(parent.getStatementSourceReference()), null);
+        }
     }
 
     @Override
diff --git a/yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/parser/stmt/rfc7950/Bug9241Test.java b/yang/yang-parser-impl/src/test/java/org/opendaylight/yangtools/yang/parser/stmt/rfc7950/Bug9241Test.java
new file mode 100644 (file)
index 0000000..2f44254
--- /dev/null
@@ -0,0 +1,54 @@
+/*
+ * Copyright (c) 2017 Pantheon Technologies s.r.o. 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.parser.stmt.rfc7950;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+import java.util.Date;
+import org.junit.Test;
+import org.opendaylight.yangtools.yang.common.QName;
+import org.opendaylight.yangtools.yang.common.SimpleDateFormatUtil;
+import org.opendaylight.yangtools.yang.model.api.ActionDefinition;
+import org.opendaylight.yangtools.yang.model.api.ContainerSchemaNode;
+import org.opendaylight.yangtools.yang.model.api.Module;
+import org.opendaylight.yangtools.yang.model.api.SchemaContext;
+import org.opendaylight.yangtools.yang.model.api.meta.EffectiveStatement;
+import org.opendaylight.yangtools.yang.model.api.meta.StatementSource;
+import org.opendaylight.yangtools.yang.stmt.StmtTestUtils;
+
+public class Bug9241Test {
+
+    @Test
+    public void testImplicitInputAndOutputInAction() throws Exception {
+        final SchemaContext schemaContext = StmtTestUtils.parseYangSource("/rfc7950/bug9241/foo.yang");
+        assertNotNull(schemaContext);
+
+        final Date revision = SimpleDateFormatUtil.getRevisionFormat().parse("2017-10-13");
+
+        final Module fooModule = schemaContext.findModuleByName("foo", revision);
+        assertNotNull(fooModule);
+
+        final ContainerSchemaNode actionCont = (ContainerSchemaNode) fooModule.getDataChildByName(QName.create(
+                fooModule.getQNameModule(), "action-cont"));
+        assertNotNull(actionCont);
+
+        final ActionDefinition actionInCont = actionCont.getActions().iterator().next();
+
+        final ContainerSchemaNode input = actionInCont.getInput();
+        assertNotNull(input);
+        assertEquals(1, input.getChildNodes().size());
+        assertEquals(StatementSource.CONTEXT, ((EffectiveStatement<?, ?>) input).getDeclared().getStatementSource());
+
+        final ContainerSchemaNode output = actionInCont.getOutput();
+        assertNotNull(output);
+        assertEquals(1, output.getChildNodes().size());
+        assertEquals(StatementSource.CONTEXT, ((EffectiveStatement<?, ?>) output).getDeclared().getStatementSource());
+    }
+}
diff --git a/yang/yang-parser-impl/src/test/resources/rfc7950/bug9241/foo.yang b/yang/yang-parser-impl/src/test/resources/rfc7950/bug9241/foo.yang
new file mode 100644 (file)
index 0000000..eba36f6
--- /dev/null
@@ -0,0 +1,25 @@
+module foo {
+    namespace foo;
+    prefix foo;
+    yang-version 1.1;
+
+    revision 2017-10-13;
+
+    container action-cont {
+        action action-in-cont {
+
+        }
+    }
+
+    augment "/action-cont/action-in-cont/input" {
+        leaf augmented-leaf-in-input {
+            type string;
+        }
+    }
+
+    augment "/action-cont/action-in-cont/output" {
+        leaf augmented-leaf-in-output {
+            type string;
+        }
+    }
+}
\ No newline at end of file