2 * Copyright (c) 2013 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.builder.util;
10 import java.util.ArrayList;
11 import java.util.HashSet;
12 import java.util.LinkedHashMap;
13 import java.util.List;
16 import java.util.TreeSet;
17 import org.opendaylight.yangtools.yang.common.QName;
18 import org.opendaylight.yangtools.yang.model.api.DataNodeContainer;
19 import org.opendaylight.yangtools.yang.model.api.DataSchemaNode;
20 import org.opendaylight.yangtools.yang.model.api.DocumentedNode;
21 import org.opendaylight.yangtools.yang.model.api.GroupingDefinition;
22 import org.opendaylight.yangtools.yang.model.api.SchemaPath;
23 import org.opendaylight.yangtools.yang.model.api.TypeDefinition;
24 import org.opendaylight.yangtools.yang.model.api.UsesNode;
25 import org.opendaylight.yangtools.yang.parser.builder.api.DataNodeContainerBuilder;
26 import org.opendaylight.yangtools.yang.parser.builder.api.DataSchemaNodeBuilder;
27 import org.opendaylight.yangtools.yang.parser.builder.api.GroupingBuilder;
28 import org.opendaylight.yangtools.yang.parser.builder.api.TypeDefinitionBuilder;
29 import org.opendaylight.yangtools.yang.parser.builder.api.UsesNodeBuilder;
30 import org.opendaylight.yangtools.yang.parser.builder.impl.BuilderUtils;
31 import org.opendaylight.yangtools.yang.parser.util.YangParseException;
34 * Basic implementation of DataNodeContainerBuilder.
36 * @deprecated Pre-Beryllium implementation, scheduled for removal.
39 public abstract class AbstractDocumentedDataNodeContainerBuilder extends AbstractDocumentedNodeBuilder implements DataNodeContainerBuilder {
40 protected final QName qname;
42 private final Map<QName, DataSchemaNode> childNodes = new LinkedHashMap<>();
43 private final List<DataSchemaNodeBuilder> addedChildNodes = new ArrayList<>();
45 private final Set<GroupingDefinition> groupings = new TreeSet<>(Comparators.SCHEMA_NODE_COMP);
46 private final Set<GroupingBuilder> addedGroupings = new HashSet<>();
48 private final Set<TypeDefinition<?>> typedefs = new TreeSet<>(Comparators.SCHEMA_NODE_COMP);
49 private final Set<TypeDefinitionBuilder> addedTypedefs = new HashSet<>();
51 private final Set<UsesNode> usesNodes = new HashSet<>();
52 private final List<UsesNodeBuilder> addedUsesNodes = new ArrayList<>();
54 protected AbstractDocumentedDataNodeContainerBuilder(final String moduleName, final int line, final QName qname) {
55 super(moduleName, line);
59 protected AbstractDocumentedDataNodeContainerBuilder(final String moduleName, final int line, final QName qname, final SchemaPath path, final DataNodeContainer base) {
60 super(moduleName, line);
63 // We do copy of child nodes with namespace change
64 // FIXME: Copy should be part of builder API so impl we prevent
65 // cyclic dependencies and each builder carries its own semantic for copy.
66 addedChildNodes.addAll(BuilderUtils.wrapChildNodes(moduleName, line, base.getChildNodes(), path, qname));
67 addedGroupings.addAll(BuilderUtils.wrapGroupings(moduleName, line, base.getGroupings(), path, qname));
68 addedTypedefs.addAll(BuilderUtils.wrapTypedefs(moduleName, line, base, path, qname));
69 // FIXME: unkownSchemaNodes should be available in DataNodeContainer
70 // addedUnknownNodes.addAll(BuilderUtils.wrapUnknownNodes(moduleName,
71 // line, base.getUnknownSchemaNodes(), path, qname));
72 usesNodes.addAll(base.getUses());
74 if (base instanceof DocumentedNode) {
75 DocumentedNode node = (DocumentedNode) base;
76 setDescription(node.getDescription());
77 setReference(node.getReference());
78 setStatus(node.getStatus());
83 public final QName getQName() {
88 public final Map<QName, DataSchemaNode> getChildNodes() {
93 public final List<DataSchemaNodeBuilder> getChildNodeBuilders() {
94 return addedChildNodes;
98 public final DataSchemaNodeBuilder getDataChildByName(final String name) {
99 for (DataSchemaNodeBuilder child : addedChildNodes) {
100 if (child.getQName().getLocalName().equals(name)) {
108 public final void addChildNode(final DataSchemaNodeBuilder child) {
109 checkIsPresent(child);
110 addedChildNodes.add(child);
114 public final void addChildNode(final int index, final DataSchemaNodeBuilder child) {
115 checkIsPresent(child);
116 if (index > addedChildNodes.size()) {
117 addedChildNodes.add(child);
119 addedChildNodes.add(index, child);
123 private void checkIsPresent(final DataSchemaNodeBuilder child) {
124 for (DataSchemaNodeBuilder addedChildNode : addedChildNodes) {
125 if (addedChildNode.getQName().equals(child.getQName())) {
126 throw new YangParseException(child.getModuleName(), child.getLine(), String.format(
127 "Can not add '%s' to '%s' in module '%s': node with same name already declared at line %d",
128 child, this, getModuleName(), addedChildNode.getLine()));
134 public final void addChildNodeToContext(final DataSchemaNodeBuilder child) {
135 addedChildNodes.add(child);
139 public final void addChildNode(final DataSchemaNode child) {
141 QName childName = child.getQName();
142 if (childNodes.containsKey(childName)) {
143 throw new YangParseException(getModuleName(), getLine(), String.format(
144 "Can not add '%s' to '%s' in module '%s': node with same name already declared", child, this,
147 childNodes.put(childName, child);
151 public final Set<GroupingDefinition> getGroupings() {
156 public final Set<GroupingBuilder> getGroupingBuilders() {
157 return addedGroupings;
161 public void addGrouping(final GroupingBuilder grouping) {
163 QName groupingName = grouping.getQName();
164 for (GroupingBuilder addedGrouping : addedGroupings) {
165 if (addedGrouping.getQName().equals(groupingName)) {
166 throw new YangParseException(grouping.getModuleName(), grouping.getLine(), String.format(
167 "Can not add '%s': grouping with same name already declared in module '%s' at line %d",
168 grouping, getModuleName(), addedGrouping.getLine()));
171 addedGroupings.add(grouping);
175 public final Set<TypeDefinition<?>> getTypeDefinitions() {
179 public final Set<UsesNode> getUsesNodes() {
184 public final List<UsesNodeBuilder> getUsesNodeBuilders() {
185 return addedUsesNodes;
189 public final void addUsesNode(final UsesNodeBuilder usesNode) {
191 addedUsesNodes.add(usesNode);
196 public final Set<TypeDefinitionBuilder> getTypeDefinitionBuilders() {
197 return addedTypedefs;
201 public void addTypedef(final TypeDefinitionBuilder type) {
203 String typeName = type.getQName().getLocalName();
204 for (TypeDefinitionBuilder addedTypedef : addedTypedefs) {
205 if (addedTypedef.getQName().getLocalName().equals(typeName)) {
206 throw new YangParseException(getModuleName(), type.getLine(), "Can not add typedef '" + typeName
207 + "': typedef with same name already declared at line " + addedTypedef.getLine());
210 addedTypedefs.add(type);
213 protected abstract String getStatementName();
215 protected void buildChildren() {
219 for (DataSchemaNodeBuilder node : addedChildNodes) {
220 childNodes.put(node.getQName(), node.build());
223 for (GroupingBuilder builder : addedGroupings) {
224 groupings.add(builder.build());
227 for (TypeDefinitionBuilder entry : addedTypedefs) {
228 typedefs.add(entry.build());
231 for (UsesNodeBuilder builder : addedUsesNodes) {
232 usesNodes.add(builder.build());