2 * Copyright (c) 2016 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.data.impl.schema.tree;
10 import static org.junit.Assert.assertEquals;
11 import static org.junit.Assert.fail;
13 import com.google.common.collect.ImmutableMap;
14 import org.junit.AfterClass;
15 import org.junit.BeforeClass;
16 import org.junit.Test;
17 import org.opendaylight.yangtools.yang.common.QName;
18 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier;
19 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifier;
20 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifierWithPredicates;
21 import org.opendaylight.yangtools.yang.data.api.schema.ContainerNode;
22 import org.opendaylight.yangtools.yang.data.api.schema.MapEntryNode;
23 import org.opendaylight.yangtools.yang.data.api.schema.MapNode;
24 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataTree;
25 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataTreeCandidate;
26 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataTreeConfiguration;
27 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataTreeModification;
28 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataValidationFailedException;
29 import org.opendaylight.yangtools.yang.data.impl.schema.Builders;
30 import org.opendaylight.yangtools.yang.data.impl.schema.ImmutableNodes;
31 import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.DataContainerNodeBuilder;
32 import org.opendaylight.yangtools.yang.model.api.EffectiveModelContext;
34 public class Bug5968Test {
35 private static final String NS = "bug5968";
36 private static final String REV = "2016-07-28";
37 private static final QName ROOT = QName.create(NS, REV, "root");
38 private static final QName MY_LIST = QName.create(NS, REV, "my-list");
39 private static final QName LIST_ID = QName.create(NS, REV, "list-id");
40 private static final QName MANDATORY_LEAF = QName.create(NS, REV, "mandatory-leaf");
41 private static final QName COMMON_LEAF = QName.create(NS, REV, "common-leaf");
43 private static EffectiveModelContext SCHEMA_CONTEXT;
46 public static void beforeClass() {
47 SCHEMA_CONTEXT = TestModel.createTestContext("/bug5968.yang");
51 public static void afterClass() {
52 SCHEMA_CONTEXT = null;
55 private static DataTree initDataTree(final EffectiveModelContext schemaContext, final boolean withMapNode)
56 throws DataValidationFailedException {
57 final DataTree inMemoryDataTree = new InMemoryDataTreeFactory().create(
58 DataTreeConfiguration.DEFAULT_CONFIGURATION, schemaContext);
60 final DataContainerNodeBuilder<NodeIdentifier, ContainerNode> root = Builders.containerBuilder()
61 .withNodeIdentifier(new NodeIdentifier(ROOT));
62 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
63 modificationTree.write(
64 YangInstanceIdentifier.of(ROOT),
65 withMapNode ? root.withChild(
66 Builders.mapBuilder().withNodeIdentifier(new NodeIdentifier(MY_LIST)).build()).build() : root
68 modificationTree.ready();
70 inMemoryDataTree.validate(modificationTree);
71 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
72 inMemoryDataTree.commit(prepare);
74 return inMemoryDataTree;
77 private static DataTree emptyDataTree(final EffectiveModelContext schemaContext)
78 throws DataValidationFailedException {
79 return new InMemoryDataTreeFactory().create(DataTreeConfiguration.DEFAULT_CONFIGURATION, schemaContext);
83 public void writeInvalidContainerTest() throws DataValidationFailedException {
84 final DataTree inMemoryDataTree = emptyDataTree(SCHEMA_CONTEXT);
86 final MapNode myList = createMap(true);
87 final DataContainerNodeBuilder<NodeIdentifier, ContainerNode> root = Builders.containerBuilder()
88 .withNodeIdentifier(new NodeIdentifier(ROOT)).withChild(myList);
90 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
91 modificationTree.write(YangInstanceIdentifier.of(ROOT), root.build());
94 modificationTree.ready();
95 inMemoryDataTree.validate(modificationTree);
96 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
97 inMemoryDataTree.commit(prepare);
98 fail("Should fail due to missing mandatory leaf.");
99 } catch (final IllegalArgumentException e) {
100 assertEquals("Node (bug5968?revision=2016-07-28)my-list[{(bug5968?revision=2016-07-28)list-id=1}] is "
101 + "missing mandatory descendant /(bug5968?revision=2016-07-28)mandatory-leaf", e.getMessage());
106 public void writeInvalidMapTest() throws DataValidationFailedException {
107 final DataTree inMemoryDataTree = emptyDataTree(SCHEMA_CONTEXT);
108 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
109 writeMap(modificationTree, true);
112 modificationTree.ready();
113 inMemoryDataTree.validate(modificationTree);
114 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
115 inMemoryDataTree.commit(prepare);
116 fail("Should fail due to missing mandatory leaf.");
117 } catch (final IllegalArgumentException e) {
118 assertEquals("Node (bug5968?revision=2016-07-28)my-list[{(bug5968?revision=2016-07-28)list-id=1}] is "
119 + "missing mandatory descendant /(bug5968?revision=2016-07-28)mandatory-leaf", e.getMessage());
124 public void writeInvalidMapEntryTest() throws DataValidationFailedException {
125 final DataTree inMemoryDataTree = initDataTree(SCHEMA_CONTEXT, true);
126 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
128 writeMapEntry(modificationTree, "1", null, "common-value");
131 modificationTree.ready();
132 inMemoryDataTree.validate(modificationTree);
133 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
134 inMemoryDataTree.commit(prepare);
135 fail("Should fail due to missing mandatory leaf.");
136 } catch (final IllegalArgumentException e) {
137 assertEquals("Node (bug5968?revision=2016-07-28)my-list[{(bug5968?revision=2016-07-28)list-id=1}] is "
138 + "missing mandatory descendant /(bug5968?revision=2016-07-28)mandatory-leaf", e.getMessage());
142 private static void writeMap(final DataTreeModification modificationTree, final boolean mandatoryDataMissing) {
143 final MapNode myList = createMap(mandatoryDataMissing);
144 modificationTree.write(YangInstanceIdentifier.of(ROOT).node(MY_LIST), myList);
147 private static MapNode createMap(final boolean mandatoryDataMissing) {
150 .withNodeIdentifier(new NodeIdentifier(MY_LIST))
152 mandatoryDataMissing ? createMapEntry("1", "common-value") : createMapEntry("1",
153 "mandatory-value", "common-value")).build();
156 private static void writeMapEntry(final DataTreeModification modificationTree, final Object listIdValue,
157 final Object mandatoryLeafValue, final Object commonLeafValue) throws DataValidationFailedException {
158 final MapEntryNode taskEntryNode = mandatoryLeafValue == null ? createMapEntry(listIdValue, commonLeafValue)
159 : createMapEntry(listIdValue, mandatoryLeafValue, commonLeafValue);
161 modificationTree.write(
162 YangInstanceIdentifier.of(ROOT).node(MY_LIST)
163 .node(NodeIdentifierWithPredicates.of(MY_LIST, ImmutableMap.of(LIST_ID, listIdValue))),
167 private static MapEntryNode createMapEntry(final Object listIdValue, final Object mandatoryLeafValue,
168 final Object commonLeafValue) {
169 return Builders.mapEntryBuilder()
170 .withNodeIdentifier(NodeIdentifierWithPredicates.of(MY_LIST, ImmutableMap.of(LIST_ID, listIdValue)))
171 .withChild(ImmutableNodes.leafNode(LIST_ID, listIdValue))
172 .withChild(ImmutableNodes.leafNode(MANDATORY_LEAF, mandatoryLeafValue))
173 .withChild(ImmutableNodes.leafNode(COMMON_LEAF, commonLeafValue)).build();
176 private static MapEntryNode createMapEntry(final Object listIdValue, final Object commonLeafValue) {
177 return Builders.mapEntryBuilder()
178 .withNodeIdentifier(NodeIdentifierWithPredicates.of(MY_LIST, ImmutableMap.of(LIST_ID, listIdValue)))
179 .withChild(ImmutableNodes.leafNode(LIST_ID, listIdValue))
180 .withChild(ImmutableNodes.leafNode(COMMON_LEAF, commonLeafValue)).build();
184 public void writeValidContainerTest() throws DataValidationFailedException {
185 final DataTree inMemoryDataTree = emptyDataTree(SCHEMA_CONTEXT);
187 final MapNode myList = createMap(false);
188 final DataContainerNodeBuilder<NodeIdentifier, ContainerNode> root = Builders.containerBuilder()
189 .withNodeIdentifier(new NodeIdentifier(ROOT)).withChild(myList);
191 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
192 modificationTree.write(YangInstanceIdentifier.of(ROOT), root.build());
193 modificationTree.ready();
194 inMemoryDataTree.validate(modificationTree);
195 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
196 inMemoryDataTree.commit(prepare);
200 public void writeValidMapTest() throws DataValidationFailedException {
201 final DataTree inMemoryDataTree = emptyDataTree(SCHEMA_CONTEXT);
202 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
203 writeMap(modificationTree, false);
205 modificationTree.ready();
206 inMemoryDataTree.validate(modificationTree);
207 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
208 inMemoryDataTree.commit(prepare);
212 public void writeValidMapEntryTest() throws DataValidationFailedException {
213 final DataTree inMemoryDataTree = initDataTree(SCHEMA_CONTEXT, true);
214 final DataTreeModification modificationTree = inMemoryDataTree.takeSnapshot().newModification();
216 writeMapEntry(modificationTree, "1", "mandatory-value", "common-value");
218 modificationTree.ready();
219 inMemoryDataTree.validate(modificationTree);
220 final DataTreeCandidate prepare = inMemoryDataTree.prepare(modificationTree);
221 inMemoryDataTree.commit(prepare);