Fix StmtContext nullness problems
[yangtools.git] / yang / yang-parser-reactor / src / main / java / org / opendaylight / yangtools / yang / parser / stmt / reactor / StatementContextBase.java
index c4307a107f93d027139b76547c405d77d1d76293..cb2c434daeb95b0ba34bc904c9dbd72016f0e5fe 100644 (file)
@@ -7,9 +7,13 @@
  */
 package org.opendaylight.yangtools.yang.parser.stmt.reactor;
 
+import static com.google.common.base.Preconditions.checkArgument;
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+import static java.util.Objects.requireNonNull;
+
 import com.google.common.base.MoreObjects;
 import com.google.common.base.MoreObjects.ToStringHelper;
-import com.google.common.base.Preconditions;
 import com.google.common.collect.ImmutableCollection;
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.ImmutableMultimap;
@@ -23,11 +27,11 @@ import java.util.EnumMap;
 import java.util.EventListener;
 import java.util.Iterator;
 import java.util.Map.Entry;
+import java.util.Objects;
 import java.util.Optional;
 import java.util.Set;
-import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
 import org.eclipse.jdt.annotation.NonNull;
+import org.eclipse.jdt.annotation.Nullable;
 import org.opendaylight.yangtools.util.OptionalBoolean;
 import org.opendaylight.yangtools.yang.common.QName;
 import org.opendaylight.yangtools.yang.common.QNameModule;
@@ -91,8 +95,8 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
 
     private static final Logger LOG = LoggerFactory.getLogger(StatementContextBase.class);
 
-    private final StatementDefinitionContext<A, D, E> definition;
-    private final StatementSourceReference statementDeclSource;
+    private final @NonNull StatementDefinitionContext<A, D, E> definition;
+    private final @NonNull StatementSourceReference statementDeclSource;
     private final StmtContext<?, ?, ?> originalCtx;
     private final CopyHistory copyHistory;
     private final String rawArgument;
@@ -104,9 +108,9 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
     private StatementMap substatements = StatementMap.empty();
 
     private boolean isSupportedToBuildEffective = true;
-    private ModelProcessingPhase completedPhase = null;
-    private D declaredInstance;
-    private E effectiveInstance;
+    private @Nullable ModelProcessingPhase completedPhase;
+    private @Nullable D declaredInstance;
+    private @Nullable E effectiveInstance;
 
     // BooleanFields value
     private byte supportedByFeatures;
@@ -115,19 +119,16 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
 
     StatementContextBase(final StatementDefinitionContext<A, D, E> def, final StatementSourceReference ref,
             final String rawArgument) {
-        this.definition = Preconditions.checkNotNull(def);
-        this.statementDeclSource = Preconditions.checkNotNull(ref);
+        this.definition = requireNonNull(def);
+        this.statementDeclSource = requireNonNull(ref);
         this.rawArgument = def.internArgument(rawArgument);
         this.copyHistory = CopyHistory.original();
         this.originalCtx = null;
     }
 
     StatementContextBase(final StatementContextBase<A, D, E> original, final CopyType copyType) {
-        this.definition = Preconditions.checkNotNull(original.definition,
-                "Statement context definition cannot be null copying from: %s", original.getStatementSourceReference());
-        this.statementDeclSource = Preconditions.checkNotNull(original.statementDeclSource,
-                "Statement context statementDeclSource cannot be null copying from: %s",
-                original.getStatementSourceReference());
+        this.definition = original.definition;
+        this.statementDeclSource = original.statementDeclSource;
         this.rawArgument = original.rawArgument;
         this.copyHistory = CopyHistory.of(copyType, original.getCopyHistory());
         this.originalCtx = original.getOriginalCtx().orElse(original);
@@ -238,7 +239,6 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      *
      * @return root context of statement
      */
-    @Nonnull
     @Override
     public abstract RootStatementContext<?, ?, ?> getRoot();
 
@@ -247,7 +247,6 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      *
      * @return origin of statement
      */
-    @Nonnull
     @Override
     public StatementSource getStatementSource() {
         return statementDeclSource.getStatementSource();
@@ -258,7 +257,6 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      *
      * @return reference of statement source
      */
-    @Nonnull
     @Override
     public StatementSourceReference getStatementSourceReference() {
         return statementDeclSource;
@@ -269,13 +267,11 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
         return rawArgument;
     }
 
-    @Nonnull
     @Override
     public Collection<? extends StmtContext<?, ?, ?>> declaredSubstatements() {
         return substatements.values();
     }
 
-    @Nonnull
     @Override
     public Collection<? extends Mutable<?, ?, ?>> mutableDeclaredSubstatements() {
         return substatements.values();
@@ -286,7 +282,6 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
         return mutableEffectiveSubstatements();
     }
 
-    @Nonnull
     @Override
     public Collection<? extends Mutable<?, ?, ?>> mutableEffectiveSubstatements() {
         if (effective instanceof ImmutableCollection) {
@@ -387,14 +382,14 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
             return;
         }
 
-        statements.forEach(Preconditions::checkNotNull);
+        statements.forEach(Objects::requireNonNull);
         beforeAddEffectiveStatement(statements.size());
         effective.addAll(statements);
     }
 
     private void beforeAddEffectiveStatement(final int toAdd) {
         final ModelProcessingPhase inProgressPhase = getRoot().getSourceContext().getInProgressPhase();
-        Preconditions.checkState(inProgressPhase == ModelProcessingPhase.FULL_DECLARATION
+        checkState(inProgressPhase == ModelProcessingPhase.FULL_DECLARATION
                 || inProgressPhase == ModelProcessingPhase.EFFECTIVE_MODEL,
                 "Effective statement cannot be added in declared phase at: %s", getStatementSourceReference());
 
@@ -410,15 +405,18 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      * @param def definition context
      * @param ref source reference
      * @param argument statement argument
+     * @param <X> new substatement argument type
+     * @param <Y> new substatement declared type
+     * @param <Z> new substatement effective type
      * @return A new substatement
      */
     @SuppressWarnings("checkstyle:methodTypeParameterName")
-    public final <CA, CD extends DeclaredStatement<CA>, CE extends EffectiveStatement<CA, CD>>
-            StatementContextBase<CA, CD, CE> createSubstatement(final int offset,
-                    final StatementDefinitionContext<CA, CD, CE> def, final StatementSourceReference ref,
+    public final <X, Y extends DeclaredStatement<X>, Z extends EffectiveStatement<X, Y>>
+            StatementContextBase<X, Y, Z> createSubstatement(final int offset,
+                    final StatementDefinitionContext<X, Y, Z> def, final StatementSourceReference ref,
                     final String argument) {
         final ModelProcessingPhase inProgressPhase = getRoot().getSourceContext().getInProgressPhase();
-        Preconditions.checkState(inProgressPhase != ModelProcessingPhase.EFFECTIVE_MODEL,
+        checkState(inProgressPhase != ModelProcessingPhase.EFFECTIVE_MODEL,
                 "Declared statement cannot be added in effective phase at: %s", getStatementSourceReference());
 
         final Optional<StatementSupport<?, ?, ?>> implicitParent = definition.getImplicitParentFor(def.getPublicView());
@@ -427,7 +425,7 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
                     ref, argument);
         }
 
-        final StatementContextBase<CA, CD, CE> ret = new SubstatementContext<>(this, def, ref, argument);
+        final StatementContextBase<X, Y, Z> ret = new SubstatementContext<>(this, def, ref, argument);
         substatements = substatements.put(offset, ret);
         def.onStatementAdded(ret);
         return ret;
@@ -439,6 +437,11 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
         return createSubstatement(offset, def, ImplicitSubstatement.of(ref), argument);
     }
 
+    public void appendImplicitStatement(final StatementSupport<?, ?, ?> statementToAdd) {
+        createSubstatement(substatements.capacity(), new StatementDefinitionContext<>(statementToAdd),
+                ImplicitSubstatement.of(getStatementSourceReference()), null);
+    }
+
     /**
      * Lookup substatement by its offset in this statement.
      *
@@ -453,8 +456,12 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
         this.fullyDefined = true;
     }
 
+    final void resizeSubstatements(final int expectedSize) {
+        substatements = substatements.ensureCapacity(expectedSize);
+    }
+
     final void walkChildren(final ModelProcessingPhase phase) {
-        Preconditions.checkState(fullyDefined);
+        checkState(fullyDefined);
         substatements.values().forEach(stmt -> {
             stmt.walkChildren(phase);
             stmt.endDeclared(phase);
@@ -463,7 +470,7 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
 
     @Override
     public D buildDeclared() {
-        Preconditions.checkArgument(completedPhase == ModelProcessingPhase.FULL_DECLARATION
+        checkArgument(completedPhase == ModelProcessingPhase.FULL_DECLARATION
                 || completedPhase == ModelProcessingPhase.EFFECTIVE_MODEL);
         if (declaredInstance == null) {
             declaredInstance = definition().getFactory().createDeclared(this);
@@ -486,7 +493,7 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      *            to be executed (completed)
      * @return if phase was successfully completed
      * @throws SourceException
-     *             when an error occured in source parsing
+     *             when an error occurred in source parsing
      */
     boolean tryToCompletePhase(final ModelProcessingPhase phase) {
 
@@ -571,7 +578,7 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      *
      * @return statement definition
      */
-    protected final StatementDefinitionContext<A, D, E> definition() {
+    protected final @NonNull StatementDefinitionContext<A, D, E> definition() {
         return definition;
     }
 
@@ -632,8 +639,8 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
     final <K, V, N extends IdentifierNamespace<K, V>> void selectMatch(final Class<N> type,
             final NamespaceKeyCriterion<K> criterion, final OnNamespaceItemAdded listener) {
         final Optional<Entry<K, V>> optMatch = getFromNamespace(type, criterion);
-        Preconditions.checkState(optMatch.isPresent(),
-            "Failed to find a match for criterion %s in namespace %s node %s", criterion, type, this);
+        checkState(optMatch.isPresent(), "Failed to find a match for criterion %s in namespace %s node %s", criterion,
+            type, this);
         final Entry<K, V> match = optMatch.get();
         listener.namespaceItemAdded(StatementContextBase.this, type, match.getKey(), match.getValue());
     }
@@ -651,8 +658,8 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
     private <K, V, N extends IdentifierNamespace<K, V>> NamespaceBehaviourWithListeners<K, V, N> getBehaviour(
             final Class<N> type) {
         final NamespaceBehaviour<K, V, N> behaviour = getBehaviourRegistry().getNamespaceBehaviour(type);
-        Preconditions.checkArgument(behaviour instanceof NamespaceBehaviourWithListeners,
-            "Namespace %s does not support listeners", type);
+        checkArgument(behaviour instanceof NamespaceBehaviourWithListeners, "Namespace %s does not support listeners",
+            type);
 
         return (NamespaceBehaviourWithListeners<K, V, N>) behaviour;
     }
@@ -660,7 +667,6 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
     /**
      * See {@link StatementSupport#getPublicView()}.
      */
-    @Nonnull
     @Override
     public StatementDefinition getPublicDefinition() {
         return definition().getPublicView();
@@ -684,10 +690,8 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
      * @throws NullPointerException if any of the arguments is null
      */
     void addPhaseCompletedListener(final ModelProcessingPhase phase, final OnPhaseFinished listener) {
-        Preconditions.checkNotNull(phase, "Statement context processing phase cannot be null at: %s",
-                getStatementSourceReference());
-        Preconditions.checkNotNull(listener, "Statement context phase listener cannot be null at: %s",
-                getStatementSourceReference());
+        checkNotNull(phase, "Statement context processing phase cannot be null at: %s", getStatementSourceReference());
+        checkNotNull(listener, "Statement context phase listener cannot be null at: %s", getStatementSourceReference());
 
         ModelProcessingPhase finishedPhase = completedPhase;
         while (finishedPhase != null) {
@@ -713,8 +717,8 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
     void addMutation(final ModelProcessingPhase phase, final ContextMutation mutation) {
         ModelProcessingPhase finishedPhase = completedPhase;
         while (finishedPhase != null) {
-            Preconditions.checkState(!phase.equals(finishedPhase),
-                "Mutation registered after phase was completed at: %s", getStatementSourceReference());
+            checkState(!phase.equals(finishedPhase), "Mutation registered after phase was completed at: %s",
+                getStatementSourceReference());
             finishedPhase = finishedPhase.getPreviousPhase();
         }
 
@@ -733,10 +737,10 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
     @Override
     public <X, Y extends DeclaredStatement<X>, Z extends EffectiveStatement<X, Y>> Mutable<X, Y, Z> childCopyOf(
             final StmtContext<X, Y, Z> stmt, final CopyType type, final QNameModule targetModule) {
-        Preconditions.checkState(stmt.getCompletedPhase() == ModelProcessingPhase.EFFECTIVE_MODEL,
+        checkState(stmt.getCompletedPhase() == ModelProcessingPhase.EFFECTIVE_MODEL,
                 "Attempted to copy statement %s which has completed phase %s", stmt, stmt.getCompletedPhase());
 
-        Preconditions.checkArgument(stmt instanceof SubstatementContext, "Unsupported statement %s", stmt);
+        checkArgument(stmt instanceof SubstatementContext, "Unsupported statement %s", stmt);
 
         final SubstatementContext<X, Y, Z> original = (SubstatementContext<X, Y, Z>)stmt;
         final SubstatementContext<X, Y, Z> copy = new SubstatementContext<>(original, this, type, targetModule);
@@ -784,7 +788,7 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
             final CopyType typeOfCopy, final QNameModule newQNameModule, final Collection<Mutable<?, ?, ?>> buffer) {
         if (needToCopyByUses(stmtContext)) {
             final Mutable<?, ?, ?> copy = target.childCopyOf(stmtContext, typeOfCopy, newQNameModule);
-            LOG.debug("Copying substatement {} for {} as", stmtContext, this, copy);
+            LOG.debug("Copying substatement {} for {} as {}", stmtContext, this, copy);
             buffer.add(copy);
         } else if (isReusedByUses(stmtContext)) {
             LOG.debug("Reusing substatement {} for {}", stmtContext, this);
@@ -811,7 +815,7 @@ public abstract class StatementContextBase<A, D extends DeclaredStatement<A>, E
             return false;
         }
         if (NOCOPY_FROM_GROUPING_SET.contains(def)) {
-            return !YangStmtMapping.GROUPING.equals(stmtContext.getParentContext().getPublicDefinition());
+            return !YangStmtMapping.GROUPING.equals(stmtContext.coerceParentContext().getPublicDefinition());
         }
 
         LOG.debug("Will copy {} statement {}", def, stmtContext);