Make declared statement inheritance a StatementContextBase property 79/87179/13
authorRobert Varga <robert.varga@pantheon.tech>
Mon, 27 Jan 2020 20:16:55 +0000 (21:16 +0100)
committerRobert Varga <robert.varga@pantheon.tech>
Tue, 28 Jan 2020 17:53:47 +0000 (18:53 +0100)
We have inconsistencies between handling of inference-time and build-time
declared statements. When a declared statement is created in reactor,
its declared view will be materialized at the statement itself, not
in the original context.

This means statements which are subject to (even unused!) inference
will create a disconnected declared view. Statements which are not
infered, will correctly reuse declared instances with their origin.

Fix this by making following of getOriginalCtx() an implementation
given in StatementContextBase, resulting in centralized code and
consistent results.

JIRA: YANGTOOLS-652
Change-Id: Id8afb814821398e416afbfc6c9e3aeeb789f94a8
Signed-off-by: Robert Varga <robert.varga@pantheon.tech>
yang/yang-parser-reactor/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/reactor/InferredStatementContext.java
yang/yang-parser-reactor/src/main/java/org/opendaylight/yangtools/yang/parser/stmt/reactor/StatementContextBase.java
yang/yang-parser-rfc7950/src/main/java/org/opendaylight/yangtools/yang/parser/rfc7950/stmt/BaseQNameStatementSupport.java
yang/yang-parser-rfc7950/src/main/java/org/opendaylight/yangtools/yang/parser/rfc7950/stmt/BaseStatementSupport.java
yang/yang-parser-rfc7950/src/main/java/org/opendaylight/yangtools/yang/parser/rfc7950/stmt/DeclaredEffectiveStatementBase.java

index f6245602b23c70622843563c0b47673c676f6e21..3378efde40672533c8d141c404202f355a72448a 100644 (file)
@@ -109,6 +109,11 @@ final class InferredStatementContext<A, D extends DeclaredStatement<A>, E extend
         return Optional.of(prototype);
     }
 
+    @Override
+    D createDeclared() {
+        return prototype.buildDeclared();
+    }
+
     @Override
     InferredStatementContext<A, D, E> reparent(final StatementContextBase<?, ?, ?> newParent) {
         return new InferredStatementContext<>(this, newParent);
index 9c02ab20fa72c532beb280c2255ecd1cfcaddbbe..30da6de9d7c5592dbc577f4e37cb2a02a9e15bfd 100644 (file)
@@ -507,7 +507,11 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
         }
         checkArgument(completedPhase == ModelProcessingPhase.FULL_DECLARATION
                 || completedPhase == ModelProcessingPhase.EFFECTIVE_MODEL);
-        return declaredInstance = definition.getFactory().createDeclared(this);
+        return declaredInstance = createDeclared();
+    }
+
+    @NonNull D createDeclared() {
+        return definition.getFactory().createDeclared(this);
     }
 
     @Override
index f359a485d218e43c3cbe3bb8f2b77aa899110b6c..d03945d75f0a1fed8f8ce48fdace836512a9bea1 100644 (file)
@@ -33,7 +33,7 @@ public abstract class BaseQNameStatementSupport<D extends DeclaredStatement<QNam
 
     @Override
     public final E createEffective(final StmtContext<QName, D, E> ctx) {
-        final D declared = BaseStatementSupport.buildDeclared(ctx);
+        final D declared = ctx.buildDeclared();
         final ImmutableList<? extends EffectiveStatement<?, ?>> substatements =
                 BaseStatementSupport.buildEffectiveSubstatements(ctx);
         return substatements.isEmpty() ? createEmptyEffective(ctx, declared)
index c7650293fca189f78560376cdb8dd6f669a237fd..97f64a9975151d223906d5ce95fcb815abda1efb 100644 (file)
@@ -7,8 +7,6 @@
  */
 package org.opendaylight.yangtools.yang.parser.rfc7950.stmt;
 
-import static com.google.common.base.Verify.verifyNotNull;
-
 import com.google.common.annotations.Beta;
 import com.google.common.collect.ImmutableList;
 import java.util.ArrayList;
@@ -53,7 +51,7 @@ public abstract class BaseStatementSupport<A, D extends DeclaredStatement<A>,
 
     @Override
     public final E createEffective(final StmtContext<A, D, E> ctx) {
-        final D declared = buildDeclared(ctx);
+        final D declared = ctx.buildDeclared();
         final ImmutableList<? extends EffectiveStatement<?, ?>> substatements = buildEffectiveSubstatements(ctx);
         return substatements.isEmpty() ? createEmptyEffective(ctx, declared)
                 : createEffective(ctx, declared, substatements);
@@ -80,17 +78,6 @@ public abstract class BaseStatementSupport<A, D extends DeclaredStatement<A>,
         return stmt != null ? stmt.argument() : defValue;
     }
 
-    static final <A, D extends DeclaredStatement<A>> @NonNull D buildDeclared(final StmtContext<A, D, ?> ctx) {
-        /*
-         * Share original instance of declared statement between all effective
-         * statements which have been copied or derived from this original
-         * declared statement.
-         */
-        @SuppressWarnings("unchecked")
-        final StmtContext<?, D, ?> lookupCtx = (StmtContext<?, D, ?>) ctx.getOriginalCtx().orElse(ctx);
-        return verifyNotNull(lookupCtx.buildDeclared(), "Statement %s failed to build declared statement", lookupCtx);
-    }
-
     /**
      * Create a set of substatements. This method is split out so it can be overridden in
      * ExtensionEffectiveStatementImpl to leak a not-fully-initialized instance.
index 859e09d835e766c89f7eef63ebd22a211c18dde8..fad96f27a74c2ca7d1e8e96458cb1d55adc56406 100644 (file)
@@ -30,7 +30,7 @@ public abstract class DeclaredEffectiveStatementBase<A, D extends DeclaredStatem
         super(ctx);
         argument = ctx.getStatementArgument();
         statementSource = ctx.getStatementSource();
-        declaredInstance = BaseStatementSupport.buildDeclared(ctx);
+        declaredInstance = ctx.buildDeclared();
     }
 
     @Override