2 * Copyright (c) 2014 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.controller.sal.restconf.impl.nn.to.xml.test;
10 import static org.junit.Assert.assertTrue;
12 import com.google.common.base.VerifyException;
13 import com.google.common.collect.Iterables;
14 import java.io.ByteArrayOutputStream;
15 import java.io.OutputStream;
16 import java.util.List;
17 import javax.ws.rs.core.MediaType;
18 import org.junit.BeforeClass;
19 import org.junit.Rule;
20 import org.junit.Test;
21 import org.junit.rules.ExpectedException;
22 import org.mockito.Mockito;
23 import org.opendaylight.controller.sal.rest.impl.test.providers.AbstractBodyReaderTest;
24 import org.opendaylight.netconf.sal.rest.impl.NormalizedNodeXmlBodyWriter;
25 import org.opendaylight.netconf.sal.restconf.impl.ControllerContext;
26 import org.opendaylight.restconf.common.context.InstanceIdentifierContext;
27 import org.opendaylight.restconf.common.context.NormalizedNodeContext;
28 import org.opendaylight.yangtools.yang.common.QName;
29 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifier;
30 import org.opendaylight.yangtools.yang.data.api.schema.ContainerNode;
31 import org.opendaylight.yangtools.yang.data.impl.codec.TypeDefinitionAwareCodec;
32 import org.opendaylight.yangtools.yang.data.impl.schema.Builders;
33 import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.DataContainerNodeAttrBuilder;
34 import org.opendaylight.yangtools.yang.model.api.ContainerSchemaNode;
35 import org.opendaylight.yangtools.yang.model.api.DataNodeContainer;
36 import org.opendaylight.yangtools.yang.model.api.DataSchemaNode;
37 import org.opendaylight.yangtools.yang.model.api.LeafSchemaNode;
38 import org.opendaylight.yangtools.yang.model.api.SchemaContext;
39 import org.opendaylight.yangtools.yang.model.api.SchemaPath;
40 import org.opendaylight.yangtools.yang.model.api.type.BitsTypeDefinition;
41 import org.opendaylight.yangtools.yang.model.api.type.EnumTypeDefinition;
42 import org.opendaylight.yangtools.yang.model.util.type.BaseTypes;
43 import org.opendaylight.yangtools.yang.model.util.type.BitsTypeBuilder;
44 import org.opendaylight.yangtools.yang.model.util.type.EnumerationTypeBuilder;
45 import org.opendaylight.yangtools.yang.model.util.type.UnionTypeBuilder;
47 public class NnToXmlTest extends AbstractBodyReaderTest {
50 public ExpectedException thrown = ExpectedException.none();
52 private final NormalizedNodeXmlBodyWriter xmlBodyWriter;
53 private static SchemaContext schemaContext;
55 public NnToXmlTest() throws NoSuchFieldException, SecurityException {
56 this.xmlBodyWriter = new NormalizedNodeXmlBodyWriter();
60 public static void initialization() {
61 schemaContext = schemaContextLoader("/nn-to-xml/yang", schemaContext);
62 CONTROLLER_CONTEXT.setSchemas(schemaContext);
66 public void nnAsYangIdentityrefToXMLTest() throws Exception {
67 final NormalizedNodeContext normalizedNodeContext = prepareIdrefData(null, true);
68 nnToXml(normalizedNodeContext, "<lf11 xmlns:x=\"referenced:module\">x:iden</lf11>");
72 public void nnAsYangIdentityrefWithQNamePrefixToXMLTest() throws Exception {
73 final NormalizedNodeContext normalizedNodeContext = prepareIdrefData("prefix", true);
74 nnToXml(normalizedNodeContext, "<lf11 xmlns", "=\"referenced:module\">", ":iden</lf11>");
78 public void nnAsYangIdentityrefWithPrefixToXMLTest() throws Exception {
79 final NormalizedNodeContext normalizedNodeContext = prepareIdrefData("prefix", false);
80 nnToXml(normalizedNodeContext, "<lf11>no qname value</lf11>");
84 public void nnAsYangLeafrefWithPrefixToXMLTest() throws Exception {
85 final NormalizedNodeContext normalizedNodeContext = prepareLeafrefData();
86 nnToXml(normalizedNodeContext, "<lfBoolean>true</lfBoolean>", "<lfLfref>true</lfLfref>");
90 * Negative test when leaf of type leafref references to not-existing leaf.
91 * {@code VerifyException} is expected.
94 public void nnAsYangLeafrefWithPrefixToXMLNegativeTest() throws Exception {
95 final NormalizedNodeContext normalizedNodeContext = prepareLeafrefNegativeData();
97 thrown.expect(VerifyException.class);
98 nnToXml(normalizedNodeContext, "<not-existing>value</not-existing>",
99 "<lfLfrefNegative>value</lfLfrefnegative>");
103 public void nnAsYangStringToXmlTest() throws Exception {
104 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
105 TypeDefinitionAwareCodec.from(BaseTypes.stringType()).deserialize("lfStr value"), "lfStr");
106 nnToXml(normalizedNodeContext, "<lfStr>lfStr value</lfStr>");
110 public void nnAsYangInt8ToXmlTest() throws Exception {
111 final String elName = "lfInt8";
113 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
114 TypeDefinitionAwareCodec.from(BaseTypes.int8Type()).deserialize("14"), elName);
115 nnToXml(normalizedNodeContext, "<" + elName + ">14</" + elName + ">");
119 public void nnAsYangInt16ToXmlTest() throws Exception {
120 final String elName = "lfInt16";
122 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
123 TypeDefinitionAwareCodec.from(BaseTypes.int16Type()).deserialize("3000"), elName);
124 nnToXml(normalizedNodeContext, "<" + elName + ">3000</" + elName + ">");
128 public void nnAsYangInt32ToXmlTest() throws Exception {
129 final String elName = "lfInt32";
131 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
132 TypeDefinitionAwareCodec.from(BaseTypes.int32Type()).deserialize("201234"), elName);
133 nnToXml(normalizedNodeContext, "<" + elName + ">201234</" + elName + ">");
137 public void nnAsYangInt64ToXmlTest() throws Exception {
138 final String elName = "lfInt64";
140 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
141 TypeDefinitionAwareCodec.from(BaseTypes.int64Type()).deserialize("5123456789"), elName);
142 nnToXml(normalizedNodeContext, "<" + elName + ">5123456789</" + elName + ">");
146 public void nnAsYangUint8ToXmlTest() throws Exception {
147 final String elName = "lfUint8";
149 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
150 TypeDefinitionAwareCodec.from(BaseTypes.uint8Type()).deserialize("200"), elName);
151 nnToXml(normalizedNodeContext, "<" + elName + ">200</" + elName + ">");
155 public void snAsYangUint16ToXmlTest() throws Exception {
156 final String elName = "lfUint16";
158 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
159 TypeDefinitionAwareCodec.from(BaseTypes.uint16Type()).deserialize("4000"), elName);
160 nnToXml(normalizedNodeContext, "<" + elName + ">4000</" + elName + ">");
164 public void nnAsYangUint32ToXmlTest() throws Exception {
165 final String elName = "lfUint32";
167 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
168 TypeDefinitionAwareCodec.from(BaseTypes.uint32Type()).deserialize("4123456789"), elName);
169 nnToXml(normalizedNodeContext, "<" + elName + ">4123456789</" + elName + ">");
173 public void snAsYangUint64ToXmlTest() throws Exception {
174 final String elName = "lfUint64";
175 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
176 TypeDefinitionAwareCodec.from(BaseTypes.uint64Type()).deserialize("5123456789"), elName);
177 nnToXml(normalizedNodeContext, "<" + elName + ">5123456789</" + elName + ">");
181 public void nnAsYangBinaryToXmlTest() throws Exception {
182 final String elName = "lfBinary";
183 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
184 TypeDefinitionAwareCodec.from(BaseTypes.binaryType())
185 .deserialize("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz01234567"),
187 nnToXml(normalizedNodeContext,
188 "<" + elName + ">ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz01234567</" + elName + ">");
192 public void nnAsYangBitsToXmlTest() throws Exception {
193 final BitsTypeDefinition.Bit mockBit1 = Mockito.mock(BitsTypeDefinition.Bit.class);
194 Mockito.when(mockBit1.getName()).thenReturn("one");
195 Mockito.when(mockBit1.getPosition()).thenReturn(1L);
196 final BitsTypeDefinition.Bit mockBit2 = Mockito.mock(BitsTypeDefinition.Bit.class);
197 Mockito.when(mockBit2.getName()).thenReturn("two");
198 Mockito.when(mockBit2.getPosition()).thenReturn(2L);
199 final BitsTypeBuilder bitsTypeBuilder = BaseTypes.bitsTypeBuilder(Mockito.mock(SchemaPath.class));
200 bitsTypeBuilder.addBit(mockBit1);
201 bitsTypeBuilder.addBit(mockBit2);
203 final String elName = "lfBits";
204 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
205 TypeDefinitionAwareCodec.from(bitsTypeBuilder.build()).deserialize("one two"), elName);
206 nnToXml(normalizedNodeContext, "<" + elName + ">one two</" + elName + ">");
210 public void nnAsYangEnumerationToXmlTest() throws Exception {
211 final EnumTypeDefinition.EnumPair mockEnum = Mockito.mock(EnumTypeDefinition.EnumPair.class);
212 Mockito.when(mockEnum.getName()).thenReturn("enum2");
214 final EnumerationTypeBuilder enumerationTypeBuilder = BaseTypes
215 .enumerationTypeBuilder(Mockito.mock(SchemaPath.class));
216 enumerationTypeBuilder.addEnum(mockEnum);
218 final String elName = "lfEnumeration";
219 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
220 TypeDefinitionAwareCodec.from(enumerationTypeBuilder.build()).deserialize("enum2"), elName);
221 nnToXml(normalizedNodeContext, "<" + elName + ">enum2</" + elName + ">");
225 public void nnAsYangEmptyToXmlTest() throws Exception {
226 final String elName = "lfEmpty";
227 final NormalizedNodeContext normalizedNodeContext = prepareNNC(
228 TypeDefinitionAwareCodec.from(BaseTypes.emptyType()).deserialize(""), elName);
229 nnToXml(normalizedNodeContext, "<" + elName + "></" + elName + ">");
233 public void nnAsYangBooleanToXmlTest() throws Exception {
234 final String elName = "lfBoolean";
235 NormalizedNodeContext normalizedNodeContext = prepareNNC(
236 TypeDefinitionAwareCodec.from(BaseTypes.booleanType()).deserialize("false"), elName);
237 nnToXml(normalizedNodeContext, "<" + elName + ">false</" + elName + ">");
239 normalizedNodeContext = prepareNNC(TypeDefinitionAwareCodec.from(BaseTypes.booleanType()).deserialize("true"),
241 nnToXml(normalizedNodeContext, "<" + elName + ">true</" + elName + ">");
245 public void nnAsYangUnionToXmlTest() throws Exception {
246 final BitsTypeDefinition.Bit mockBit1 = Mockito.mock(BitsTypeDefinition.Bit.class);
247 Mockito.when(mockBit1.getName()).thenReturn("first");
248 Mockito.when(mockBit1.getPosition()).thenReturn(1L);
249 final BitsTypeDefinition.Bit mockBit2 = Mockito.mock(BitsTypeDefinition.Bit.class);
250 Mockito.when(mockBit2.getName()).thenReturn("second");
251 Mockito.when(mockBit2.getPosition()).thenReturn(2L);
253 final BitsTypeBuilder bitsTypeBuilder = BaseTypes.bitsTypeBuilder(Mockito.mock(SchemaPath.class));
254 bitsTypeBuilder.addBit(mockBit1);
255 bitsTypeBuilder.addBit(mockBit2);
257 final UnionTypeBuilder unionTypeBuilder = BaseTypes.unionTypeBuilder(Mockito.mock(SchemaPath.class));
258 unionTypeBuilder.addType(BaseTypes.int8Type());
259 unionTypeBuilder.addType(bitsTypeBuilder.build());
260 unionTypeBuilder.addType(BaseTypes.booleanType());
261 unionTypeBuilder.addType(BaseTypes.stringType());
263 final String elName = "lfUnion";
266 final String int8 = "15";
267 NormalizedNodeContext normalizedNodeContext = prepareNNC(
268 TypeDefinitionAwareCodec.from(unionTypeBuilder.build()).deserialize(int8), elName);
269 nnToXml(normalizedNodeContext, "<" + elName + ">15</" + elName + ">");
272 final String bits = "first second";
273 normalizedNodeContext = prepareNNC(TypeDefinitionAwareCodec.from(unionTypeBuilder.build()).deserialize(bits),
275 nnToXml(normalizedNodeContext, "<" + elName + ">[first, second]</" + elName + ">");
278 final String bool = "true";
279 normalizedNodeContext = prepareNNC(TypeDefinitionAwareCodec.from(unionTypeBuilder.build()).deserialize(bool),
281 nnToXml(normalizedNodeContext, "<" + elName + ">true</" + elName + ">");
284 final String s = "Hi!";
285 normalizedNodeContext = prepareNNC(TypeDefinitionAwareCodec.from(unionTypeBuilder.build()).deserialize(s),
287 nnToXml(normalizedNodeContext, "<" + elName + ">Hi!</" + elName + ">");
290 private static NormalizedNodeContext prepareNNC(final Object object, final String name) {
291 final QName cont = QName.create("basic:module", "2013-12-02", "cont");
292 final QName lf = QName.create("basic:module", "2013-12-02", name);
294 final DataSchemaNode contSchema = schemaContext.getDataChildByName(cont);
296 final DataContainerNodeAttrBuilder<NodeIdentifier, ContainerNode> contData = Builders
297 .containerBuilder((ContainerSchemaNode) contSchema);
299 final List<DataSchemaNode> instanceLf = ControllerContext
300 .findInstanceDataChildrenByName((DataNodeContainer) contSchema, lf.getLocalName());
301 final DataSchemaNode schemaLf = Iterables.getFirst(instanceLf, null);
303 contData.withChild(Builders.leafBuilder((LeafSchemaNode) schemaLf).withValue(object).build());
305 final NormalizedNodeContext testNormalizedNodeContext = new NormalizedNodeContext(
306 new InstanceIdentifierContext<>(null, contSchema, null, schemaContext), contData.build());
308 return testNormalizedNodeContext;
311 private void nnToXml(final NormalizedNodeContext normalizedNodeContext, final String... xmlRepresentation)
313 final OutputStream output = new ByteArrayOutputStream();
314 this.xmlBodyWriter.writeTo(normalizedNodeContext, null, null, null, this.mediaType, null, output);
316 for (String element : xmlRepresentation) {
317 assertTrue(output.toString().contains(element));
321 private static NormalizedNodeContext prepareLeafrefData() {
322 final QName cont = QName.create("basic:module", "2013-12-02", "cont");
323 final QName lfBoolean = QName.create("basic:module", "2013-12-02", "lfBoolean");
324 final QName lfLfref = QName.create("basic:module", "2013-12-02", "lfLfref");
326 final DataSchemaNode contSchema = schemaContext.getDataChildByName(cont);
328 final DataContainerNodeAttrBuilder<NodeIdentifier, ContainerNode> contData = Builders
329 .containerBuilder((ContainerSchemaNode) contSchema);
331 List<DataSchemaNode> instanceLf = ControllerContext
332 .findInstanceDataChildrenByName((DataNodeContainer) contSchema, lfBoolean.getLocalName());
333 DataSchemaNode schemaLf = Iterables.getFirst(instanceLf, null);
335 contData.withChild(Builders.leafBuilder((LeafSchemaNode) schemaLf).withValue(Boolean.TRUE).build());
337 instanceLf = ControllerContext.findInstanceDataChildrenByName((DataNodeContainer) contSchema,
338 lfLfref.getLocalName());
339 schemaLf = Iterables.getFirst(instanceLf, null);
341 contData.withChild(Builders.leafBuilder((LeafSchemaNode) schemaLf).withValue("true").build());
343 final NormalizedNodeContext testNormalizedNodeContext = new NormalizedNodeContext(
344 new InstanceIdentifierContext<>(null, contSchema, null, schemaContext), contData.build());
346 return testNormalizedNodeContext;
349 private static NormalizedNodeContext prepareLeafrefNegativeData() {
350 final QName cont = QName.create("basic:module", "2013-12-02", "cont");
351 final QName lfLfref = QName.create("basic:module", "2013-12-02", "lfLfrefNegative");
353 final DataSchemaNode contSchema = schemaContext.getDataChildByName(cont);
354 final DataContainerNodeAttrBuilder<NodeIdentifier, ContainerNode> contData = Builders
355 .containerBuilder((ContainerSchemaNode) contSchema);
357 final List<DataSchemaNode> instanceLf = ControllerContext.findInstanceDataChildrenByName((DataNodeContainer)
358 contSchema, lfLfref.getLocalName());
359 final DataSchemaNode schemaLf = Iterables.getFirst(instanceLf, null);
361 contData.withChild(Builders.leafBuilder((LeafSchemaNode) schemaLf).withValue("value").build());
363 return new NormalizedNodeContext(
364 new InstanceIdentifierContext<>(null, contSchema, null, schemaContext), contData.build());
367 private static NormalizedNodeContext prepareIdrefData(final String prefix, final boolean valueAsQName) {
368 final QName cont = QName.create("basic:module", "2013-12-02", "cont");
369 final QName cont1 = QName.create("basic:module", "2013-12-02", "cont1");
370 final QName lf11 = QName.create("basic:module", "2013-12-02", "lf11");
372 final DataSchemaNode contSchema = schemaContext.getDataChildByName(cont);
374 final DataContainerNodeAttrBuilder<NodeIdentifier, ContainerNode> contData = Builders
375 .containerBuilder((ContainerSchemaNode) contSchema);
377 final DataSchemaNode cont1Schema = ((ContainerSchemaNode) contSchema).getDataChildByName(cont1);
379 final DataContainerNodeAttrBuilder<NodeIdentifier, ContainerNode> cont1Data = Builders
380 .containerBuilder((ContainerSchemaNode) cont1Schema);
384 value = QName.create("referenced:module", "2013-12-02", "iden");
386 value = "no qname value";
389 final List<DataSchemaNode> instanceLf = ControllerContext
390 .findInstanceDataChildrenByName((DataNodeContainer) cont1Schema, lf11.getLocalName());
391 final DataSchemaNode schemaLf = Iterables.getFirst(instanceLf, null);
393 cont1Data.withChild(Builders.leafBuilder((LeafSchemaNode) schemaLf).withValue(value).build());
395 contData.withChild(cont1Data.build());
397 final NormalizedNodeContext testNormalizedNodeContext = new NormalizedNodeContext(
398 new InstanceIdentifierContext<>(null, contSchema, null, schemaContext), contData.build());
399 return testNormalizedNodeContext;
403 protected MediaType getMediaType() {