Adjust test suite parser update to conform with API changes
[yangtools.git] / yang / yang-parser-rfc7950 / src / main / java / org / opendaylight / yangtools / yang / parser / rfc7950 / namespace / SchemaNodeIdentifierBuildNamespace.java
1 /*
2  * Copyright (c) 2015 Cisco Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.yangtools.yang.parser.rfc7950.namespace;
9
10 import static java.util.Objects.requireNonNull;
11
12 import com.google.common.annotations.Beta;
13 import java.util.Collection;
14 import java.util.Iterator;
15 import java.util.Optional;
16 import javax.annotation.Nonnull;
17 import org.opendaylight.yangtools.yang.common.QName;
18 import org.opendaylight.yangtools.yang.model.api.meta.EffectiveStatement;
19 import org.opendaylight.yangtools.yang.model.api.meta.IdentifierNamespace;
20 import org.opendaylight.yangtools.yang.model.api.stmt.SchemaNodeIdentifier;
21 import org.opendaylight.yangtools.yang.model.api.stmt.UnknownStatement;
22 import org.opendaylight.yangtools.yang.parser.spi.meta.DerivedNamespaceBehaviour;
23 import org.opendaylight.yangtools.yang.parser.spi.meta.NamespaceBehaviour;
24 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContext;
25 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContext.Mutable;
26 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContextUtils;
27
28 @Beta
29 public final class SchemaNodeIdentifierBuildNamespace
30         extends DerivedNamespaceBehaviour<SchemaNodeIdentifier, Mutable<?, ?, EffectiveStatement<?, ?>>, QName,
31                 SchemaNodeIdentifierBuildNamespace, ChildSchemaNodeNamespace<?, ?>>
32         implements IdentifierNamespace<SchemaNodeIdentifier, Mutable<?, ?, EffectiveStatement<?, ?>>> {
33
34     @SuppressWarnings({"unchecked", "rawtypes"})
35     public SchemaNodeIdentifierBuildNamespace() {
36         super(SchemaNodeIdentifierBuildNamespace.class, (Class) ChildSchemaNodeNamespace.class);
37     }
38
39     /**
40      * Find statement context identified by interpreting specified {@link SchemaNodeIdentifier} starting at specified
41      * {@link StmtContext}.
42      *
43      * @param root Search root context
44      * @param identifier {@link SchemaNodeIdentifier} relative to search root
45      * @return Matching statement context, if present.
46      * @throws NullPointerException if any of the arguments is null
47      */
48     public static Optional<StmtContext<?, ?, ?>> findNode(final StmtContext<?, ?, ?> root,
49             final SchemaNodeIdentifier identifier) {
50         return Optional.ofNullable(root.getFromNamespace(SchemaNodeIdentifierBuildNamespace.class,
51             requireNonNull(identifier)));
52     }
53
54     @Override
55     public Mutable<?, ?, EffectiveStatement<?, ?>> get(@Nonnull final SchemaNodeIdentifier key) {
56         throw new UnsupportedOperationException("Direct access to namespace is not supported");
57     }
58
59     @SuppressWarnings("unchecked")
60     @Override
61     public Mutable<?, ?, EffectiveStatement<?, ?>> getFrom(final NamespaceStorageNode storage,
62             final SchemaNodeIdentifier key) {
63         final NamespaceStorageNode lookupStartStorage;
64         if (key.isAbsolute() || storage.getStorageNodeType() == StorageNodeType.ROOT_STATEMENT_LOCAL) {
65             lookupStartStorage = NamespaceBehaviour.findClosestTowardsRoot(storage, StorageNodeType.GLOBAL);
66         } else {
67             lookupStartStorage = storage;
68         }
69         final Iterator<QName> iterator = key.getPathFromRoot().iterator();
70         if (!iterator.hasNext()) {
71             if (lookupStartStorage instanceof StmtContext<?, ?, ?>) {
72                 return (Mutable<?, ?, EffectiveStatement<?, ?>>) lookupStartStorage;
73             }
74             return null;
75         }
76         QName nextPath = iterator.next();
77         Mutable<?, ?, EffectiveStatement<?, ?>> current = lookupStartStorage.getFromLocalStorage(
78             ChildSchemaNodeNamespace.class,nextPath);
79         if (current == null && lookupStartStorage instanceof StmtContext<?, ?, ?>) {
80             return tryToFindUnknownStatement(nextPath.getLocalName(),
81                 (Mutable<?, ?, EffectiveStatement<?, ?>>) lookupStartStorage);
82         }
83         while (current != null && iterator.hasNext()) {
84             nextPath = iterator.next();
85             final Mutable<?, ?, EffectiveStatement<?, ?>> nextNodeCtx = current.getFromNamespace(
86                 ChildSchemaNodeNamespace.class,nextPath);
87             if (nextNodeCtx == null) {
88                 return tryToFindUnknownStatement(nextPath.getLocalName(), current);
89             }
90             current = nextNodeCtx;
91         }
92         return current;
93     }
94
95     @SuppressWarnings("unchecked")
96     private static Mutable<?, ?, EffectiveStatement<?, ?>> tryToFindUnknownStatement(final String localName,
97             final Mutable<?, ?, EffectiveStatement<?, ?>> current) {
98         final Collection<? extends StmtContext<?, ?, ?>> unknownSubstatements = StmtContextUtils.findAllSubstatements(
99             current, UnknownStatement.class);
100         for (final StmtContext<?, ?, ?> unknownSubstatement : unknownSubstatements) {
101             if (localName.equals(unknownSubstatement.rawStatementArgument())) {
102                 return (Mutable<?, ?, EffectiveStatement<?, ?>>) unknownSubstatement;
103             }
104         }
105         return null;
106     }
107
108     @Override
109     public QName getSignificantKey(final SchemaNodeIdentifier key) {
110         return key.getLastComponent();
111     }
112 }