2 * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
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
8 package org.opendaylight.yangtools.yang.parser.stmt.rfc6020;
10 import static org.opendaylight.yangtools.yang.parser.spi.meta.StmtContextUtils.firstAttributeOf;
13 import java.util.Date;
14 import java.util.Optional;
15 import org.opendaylight.yangtools.concepts.SemVer;
16 import org.opendaylight.yangtools.yang.common.QNameModule;
17 import org.opendaylight.yangtools.yang.model.api.ModuleIdentifier;
18 import org.opendaylight.yangtools.yang.model.api.YangStmtMapping;
19 import org.opendaylight.yangtools.yang.model.api.meta.EffectiveStatement;
20 import org.opendaylight.yangtools.yang.model.api.stmt.ModuleStatement;
21 import org.opendaylight.yangtools.yang.model.api.stmt.NamespaceStatement;
22 import org.opendaylight.yangtools.yang.model.api.stmt.PrefixStatement;
23 import org.opendaylight.yangtools.yang.model.repo.api.SemVerSourceIdentifier;
24 import org.opendaylight.yangtools.yang.model.util.ModuleIdentifierImpl;
25 import org.opendaylight.yangtools.yang.parser.spi.ModuleNamespace;
26 import org.opendaylight.yangtools.yang.parser.spi.NamespaceToModule;
27 import org.opendaylight.yangtools.yang.parser.spi.PreLinkageModuleNamespace;
28 import org.opendaylight.yangtools.yang.parser.spi.meta.AbstractStatementSupport;
29 import org.opendaylight.yangtools.yang.parser.spi.meta.SemanticVersionModuleNamespace;
30 import org.opendaylight.yangtools.yang.parser.spi.meta.SemanticVersionNamespace;
31 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContext;
32 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContext.Mutable;
33 import org.opendaylight.yangtools.yang.parser.spi.meta.StmtContextUtils;
34 import org.opendaylight.yangtools.yang.parser.spi.meta.SubstatementValidator;
35 import org.opendaylight.yangtools.yang.parser.spi.source.ImpPrefixToNamespace;
36 import org.opendaylight.yangtools.yang.parser.spi.source.ImportPrefixToModuleCtx;
37 import org.opendaylight.yangtools.yang.parser.spi.source.ModuleCtxToModuleIdentifier;
38 import org.opendaylight.yangtools.yang.parser.spi.source.ModuleCtxToModuleQName;
39 import org.opendaylight.yangtools.yang.parser.spi.source.ModuleNameToModuleQName;
40 import org.opendaylight.yangtools.yang.parser.spi.source.ModuleNameToNamespace;
41 import org.opendaylight.yangtools.yang.parser.spi.source.ModuleNamespaceForBelongsTo;
42 import org.opendaylight.yangtools.yang.parser.spi.source.ModuleQNameToModuleName;
43 import org.opendaylight.yangtools.yang.parser.spi.source.PrefixToModule;
44 import org.opendaylight.yangtools.yang.parser.spi.source.SourceException;
45 import org.opendaylight.yangtools.yang.parser.stmt.rfc6020.effective.ModuleEffectiveStatementImpl;
47 public class ModuleStatementSupport extends
48 AbstractStatementSupport<String, ModuleStatement, EffectiveStatement<String, ModuleStatement>> {
49 private static final SubstatementValidator SUBSTATEMENT_VALIDATOR = SubstatementValidator.builder(YangStmtMapping
51 .addAny(YangStmtMapping.ANYXML)
52 .addAny(YangStmtMapping.AUGMENT)
53 .addAny(YangStmtMapping.CHOICE)
54 .addOptional(YangStmtMapping.CONTACT)
55 .addAny(YangStmtMapping.CONTAINER)
56 .addOptional(YangStmtMapping.DESCRIPTION)
57 .addAny(YangStmtMapping.DEVIATION)
58 .addAny(YangStmtMapping.EXTENSION)
59 .addAny(YangStmtMapping.FEATURE)
60 .addAny(YangStmtMapping.GROUPING)
61 .addAny(YangStmtMapping.IDENTITY)
62 .addAny(YangStmtMapping.IMPORT)
63 .addAny(YangStmtMapping.INCLUDE)
64 .addAny(YangStmtMapping.LEAF)
65 .addAny(YangStmtMapping.LEAF_LIST)
66 .addAny(YangStmtMapping.LIST)
67 .addMandatory(YangStmtMapping.NAMESPACE)
68 .addAny(YangStmtMapping.NOTIFICATION)
69 .addOptional(YangStmtMapping.ORGANIZATION)
70 .addMandatory(YangStmtMapping.PREFIX)
71 .addOptional(YangStmtMapping.REFERENCE)
72 .addAny(YangStmtMapping.REVISION)
73 .addAny(YangStmtMapping.RPC)
74 .addAny(YangStmtMapping.TYPEDEF)
75 .addAny(YangStmtMapping.USES)
76 .addOptional(YangStmtMapping.YANG_VERSION)
77 .addOptional(SupportedExtensionsMapping.OPENCONFIG_VERSION)
80 public ModuleStatementSupport() {
81 super(YangStmtMapping.MODULE);
85 public String parseArgumentValue(final StmtContext<?, ?, ?> ctx, final String value) {
90 public ModuleStatement createDeclared(final StmtContext<String, ModuleStatement, ?> ctx) {
91 return new ModuleStatementImpl(ctx);
95 public EffectiveStatement<String, ModuleStatement> createEffective(
96 final StmtContext<String, ModuleStatement, EffectiveStatement<String, ModuleStatement>> ctx) {
97 return new ModuleEffectiveStatementImpl(ctx);
101 public void onPreLinkageDeclared(final Mutable<String, ModuleStatement,
102 EffectiveStatement<String, ModuleStatement>> stmt) {
103 final String moduleName = stmt.getStatementArgument();
105 final URI moduleNs = firstAttributeOf(stmt.declaredSubstatements(), NamespaceStatement.class);
106 SourceException.throwIfNull(moduleNs, stmt.getStatementSourceReference(),
107 "Namespace of the module [%s] is missing", stmt.getStatementArgument());
108 stmt.addToNs(ModuleNameToNamespace.class, moduleName, moduleNs);
110 final String modulePrefix = firstAttributeOf(stmt.declaredSubstatements(), PrefixStatement.class);
111 SourceException.throwIfNull(modulePrefix, stmt.getStatementSourceReference(),
112 "Prefix of the module [%s] is missing", stmt.getStatementArgument());
113 stmt.addToNs(ImpPrefixToNamespace.class, modulePrefix, moduleNs);
115 stmt.addContext(PreLinkageModuleNamespace.class, moduleName, stmt);
117 final Optional<Date> revisionDate = Optional.ofNullable(StmtContextUtils.getLatestRevision(
118 stmt.declaredSubstatements()));
119 final QNameModule qNameModule = QNameModule.create(moduleNs, revisionDate.orElse(null)).intern();
121 stmt.addToNs(ModuleCtxToModuleQName.class, stmt, qNameModule);
122 stmt.setRootIdentifier(ModuleIdentifierImpl.create(stmt.getStatementArgument(), revisionDate));
126 public void onLinkageDeclared(final Mutable<String, ModuleStatement,
127 EffectiveStatement<String, ModuleStatement>> stmt) {
129 final Optional<URI> moduleNs = Optional.ofNullable(firstAttributeOf(stmt.declaredSubstatements(),
130 NamespaceStatement.class));
131 SourceException.throwIf(!moduleNs.isPresent(), stmt.getStatementSourceReference(),
132 "Namespace of the module [%s] is missing", stmt.getStatementArgument());
134 final Optional<Date> revisionDate = Optional.ofNullable(StmtContextUtils.getLatestRevision(
135 stmt.declaredSubstatements()));
136 final QNameModule qNameModule = QNameModule.create(moduleNs.get(), revisionDate.orElse(null)).intern();
137 final StmtContext<?, ModuleStatement, EffectiveStatement<String, ModuleStatement>> possibleDuplicateModule =
138 stmt.getFromNamespace(NamespaceToModule.class, qNameModule);
139 if (possibleDuplicateModule != null && possibleDuplicateModule != stmt) {
140 throw new SourceException(stmt.getStatementSourceReference(), "Module namespace collision: %s. At %s",
141 qNameModule.getNamespace(), possibleDuplicateModule.getStatementSourceReference());
144 final ModuleIdentifier moduleIdentifier = ModuleIdentifierImpl.create(stmt.getStatementArgument(),
147 stmt.addContext(ModuleNamespace.class, moduleIdentifier, stmt);
148 stmt.addContext(ModuleNamespaceForBelongsTo.class, moduleIdentifier.getName(), stmt);
149 stmt.addContext(NamespaceToModule.class, qNameModule, stmt);
151 final String modulePrefix = firstAttributeOf(stmt.declaredSubstatements(), PrefixStatement.class);
152 SourceException.throwIfNull(modulePrefix, stmt.getStatementSourceReference(),
153 "Prefix of the module [%s] is missing", stmt.getStatementArgument());
155 stmt.addToNs(PrefixToModule.class, modulePrefix, qNameModule);
156 stmt.addToNs(ModuleNameToModuleQName.class, stmt.getStatementArgument(), qNameModule);
157 stmt.addToNs(ModuleCtxToModuleQName.class, stmt, qNameModule); // tu
158 stmt.addToNs(ModuleCtxToModuleIdentifier.class, stmt, moduleIdentifier);
159 stmt.addToNs(ModuleQNameToModuleName.class, qNameModule, stmt.getStatementArgument());
160 stmt.addToNs(ImportPrefixToModuleCtx.class, modulePrefix, stmt);
162 if (stmt.isEnabledSemanticVersioning()) {
163 addToSemVerModuleNamespace(stmt, moduleIdentifier);
167 private static void addToSemVerModuleNamespace(
168 final Mutable<String, ModuleStatement, EffectiveStatement<String, ModuleStatement>> stmt,
169 final ModuleIdentifier moduleIdentifier) {
170 final String moduleName = stmt.getStatementArgument();
171 final SemVer moduleSemVer = stmt.getFromNamespace(SemanticVersionNamespace.class, stmt);
172 final SemVerSourceIdentifier id = SemVerSourceIdentifier.create(moduleName, moduleSemVer);
173 stmt.addToNs(SemanticVersionModuleNamespace.class, id, stmt);
177 protected SubstatementValidator getSubstatementValidator() {
178 return SUBSTATEMENT_VALIDATOR;