2 * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved.
\r
4 * This program and the accompanying materials are made available under the
\r
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
\r
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
\r
8 package org.opendaylight.yangtools.yang.data.impl;
\r
10 import groovy.lang.Binding;
\r
11 import groovy.lang.GroovyShell;
\r
12 import groovy.lang.Script;
\r
14 import java.io.ByteArrayInputStream;
\r
15 import java.io.ByteArrayOutputStream;
\r
16 import java.io.IOException;
\r
17 import java.io.InputStream;
\r
18 import java.io.InputStreamReader;
\r
19 import java.io.PrintStream;
\r
20 import java.io.Reader;
\r
21 import java.io.StringWriter;
\r
22 import java.lang.reflect.Method;
\r
23 import java.text.MessageFormat;
\r
24 import java.util.ArrayList;
\r
25 import java.util.List;
\r
26 import java.util.Set;
\r
28 import javax.xml.transform.OutputKeys;
\r
29 import javax.xml.transform.Transformer;
\r
30 import javax.xml.transform.TransformerFactory;
\r
31 import javax.xml.transform.dom.DOMSource;
\r
32 import javax.xml.transform.stream.StreamResult;
\r
34 import org.custommonkey.xmlunit.Diff;
\r
35 import org.junit.Assert;
\r
36 import org.opendaylight.yangtools.yang.common.QName;
\r
37 import org.opendaylight.yangtools.yang.data.api.CompositeNode;
\r
38 import org.opendaylight.yangtools.yang.data.api.Node;
\r
39 import org.opendaylight.yangtools.yang.model.api.Module;
\r
40 import org.opendaylight.yangtools.yang.model.api.SchemaContext;
\r
41 import org.opendaylight.yangtools.yang.model.parser.api.YangModelParser;
\r
42 import org.opendaylight.yangtools.yang.parser.impl.YangParserImpl;
\r
43 import org.slf4j.Logger;
\r
44 import org.slf4j.LoggerFactory;
\r
45 import org.w3c.dom.Document;
\r
46 import org.xml.sax.SAXException;
\r
49 * @author michal.rehak
\r
52 public abstract class NodeHelper {
\r
54 private static final Logger LOG = LoggerFactory.getLogger(NodeHelper.class);
\r
56 /** xml source of example network configuration */
\r
57 public static final String NETWORK_XML =
\r
58 "<network xmlns=\"urn:opendaylight:controller:network\">\n" +
\r
62 " <topology-id>topId_01</topology-id>\n" +
\r
65 " <node-id>nodeId_02</node-id>\n" +
\r
66 " <supporting-ne>networkId_02</supporting-ne>\n" +
\r
67 " <termination-points>\n" +
\r
68 " <termination-point>\n" +
\r
69 " <tp-id>tpId_03</tp-id>\n" +
\r
70 " </termination-point>\n" +
\r
71 " </termination-points>\n" +
\r
74 " <node-id>nodeId_16</node-id>\n" +
\r
75 " <supporting-ne>networkId_17</supporting-ne>\n" +
\r
76 " <termination-points>\n" +
\r
77 " <termination-point>\n" +
\r
78 " <tp-id>tpId_18</tp-id>\n" +
\r
79 " </termination-point>\n" +
\r
80 " </termination-points>\n" +
\r
83 " <node-id>nodeId_19</node-id>\n" +
\r
84 " <supporting-ne>networkId_20</supporting-ne>\n" +
\r
85 " <termination-points>\n" +
\r
86 " <termination-point>\n" +
\r
87 " <tp-id>tpId_18</tp-id>\n" +
\r
88 " </termination-point>\n" +
\r
89 " <termination-point>\n" +
\r
90 " <tp-id>tpId_19</tp-id>\n" +
\r
91 " </termination-point>\n" +
\r
92 " </termination-points>\n" +
\r
97 " <link-id>linkId_04</link-id>\n" +
\r
99 " <source-node>nodeId_05</source-node>\n" +
\r
100 " <source-tp>tpId_06</source-tp>\n" +
\r
102 " <destination>\n" +
\r
103 " <dest-node>nodeId_07</dest-node>\n" +
\r
104 " <dest-tp>tpId_08</dest-tp>\n" +
\r
105 " </destination>\n" +
\r
108 " <link-id>linkId_11</link-id>\n" +
\r
110 " <source-node>nodeId_12</source-node>\n" +
\r
111 " <source-tp>tpId_13</source-tp>\n" +
\r
113 " <destination>\n" +
\r
114 " <dest-node>nodeId_14</dest-node>\n" +
\r
115 " <dest-tp>tpId_15</dest-tp>\n" +
\r
116 " </destination>\n" +
\r
120 " </topologies>\n" +
\r
121 " <network-elements>\n" +
\r
122 " <network-element>\n" +
\r
123 " <element-id>ntElementId_09</element-id>\n" +
\r
124 " </network-element>\n" +
\r
125 " <network-element>\n" +
\r
126 " <element-id>ntElementId_10</element-id>\n" +
\r
127 " </network-element>\n" +
\r
128 " </network-elements>\n" +
\r
134 * @throws Exception
\r
136 public static void dumpDoc(Document domTree, PrintStream out) throws Exception {
\r
137 TransformerFactory transformerFact = TransformerFactory.newInstance();
\r
138 transformerFact.setAttribute("indent-number", 4);
\r
139 Transformer transformer = transformerFact.newTransformer();
\r
140 transformer.setOutputProperty(OutputKeys.INDENT, "yes");
\r
141 //initialize StreamResult with File object to save to file
\r
142 StreamResult result = new StreamResult(new StringWriter());
\r
143 DOMSource source = new DOMSource(domTree);
\r
144 transformer.transform(source, result);
\r
145 String xmlString = result.getWriter().toString();
\r
146 out.println(xmlString);
\r
151 * @return example tree, see {@link #NETWORK_XML}
\r
153 public static CompositeNode buildTestConfigTree(QName qName) {
\r
154 List<Node<?>> value = new ArrayList<Node<?>>();
\r
155 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "element-id"), null, "ntElementId_09"));
\r
156 CompositeNode ntElementNode1 = NodeFactory.createImmutableCompositeNode(new QName(qName, "network-element"), null, value);
\r
157 assignParentToChildren(ntElementNode1);
\r
159 value = new ArrayList<Node<?>>();
\r
160 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "element-id"), null, "ntElementId_10"));
\r
161 CompositeNode ntElementNode2 = NodeFactory.createImmutableCompositeNode(new QName(qName, "network-element"), null, value);
\r
162 assignParentToChildren(ntElementNode2);
\r
164 value = new ArrayList<Node<?>>();
\r
165 value.add(ntElementNode1);
\r
166 value.add(ntElementNode2);
\r
167 CompositeNode ntElementsNode = NodeFactory.createImmutableCompositeNode(
\r
168 new QName(qName, "network-elements"), null, value);
\r
169 assignParentToChildren(ntElementsNode);
\r
171 value = new ArrayList<Node<?>>();
\r
172 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "dest-node"), null, "nodeId_07"));
\r
173 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "dest-tp"), null, "tpId_08"));
\r
174 CompositeNode destination = NodeFactory.createImmutableCompositeNode(
\r
175 new QName(qName, "destination"), null, value);
\r
176 assignParentToChildren(destination);
\r
178 value = new ArrayList<Node<?>>();
\r
179 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "source-node"), null, "nodeId_05"));
\r
180 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "source-tp"), null, "tpId_06"));
\r
181 CompositeNode source = NodeFactory.createImmutableCompositeNode(
\r
182 new QName(qName, "source"), null, value);
\r
183 assignParentToChildren(source);
\r
185 value = new ArrayList<Node<?>>();
\r
186 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "link-id"), null, "linkId_04"));
\r
188 value.add(destination);
\r
189 CompositeNode link1 = NodeFactory.createImmutableCompositeNode(
\r
190 new QName(qName, "link"), null, value);
\r
191 assignParentToChildren(link1);
\r
193 value = new ArrayList<Node<?>>();
\r
194 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "dest-node"), null, "nodeId_14"));
\r
195 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "dest-tp"), null, "tpId_15"));
\r
196 destination = NodeFactory.createImmutableCompositeNode(
\r
197 new QName(qName, "destination"), null, value);
\r
198 assignParentToChildren(destination);
\r
200 value = new ArrayList<Node<?>>();
\r
201 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "source-node"), null, "nodeId_12"));
\r
202 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "source-tp"), null, "tpId_13"));
\r
203 source = NodeFactory.createImmutableCompositeNode(
\r
204 new QName(qName, "source"), null, value);
\r
205 assignParentToChildren(source);
\r
207 value = new ArrayList<Node<?>>();
\r
208 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "link-id"), null, "linkId_11"));
\r
210 value.add(destination);
\r
211 CompositeNode link2 = NodeFactory.createImmutableCompositeNode(
\r
212 new QName(qName, "link"), null, value);
\r
213 assignParentToChildren(link2);
\r
215 value = new ArrayList<Node<?>>();
\r
218 CompositeNode links = NodeFactory.createImmutableCompositeNode(
\r
219 new QName(qName, "links"), null, value);
\r
220 assignParentToChildren(links);
\r
223 value = new ArrayList<Node<?>>();
\r
224 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "tp-id"), null, "tpId_03"));
\r
225 CompositeNode terminationPointNode1 = NodeFactory.createImmutableCompositeNode(
\r
226 new QName(qName, "termination-point"), null, value);
\r
227 assignParentToChildren(terminationPointNode1);
\r
229 value = new ArrayList<Node<?>>();
\r
230 value.add(terminationPointNode1);
\r
231 CompositeNode terminationPointsNode = NodeFactory.createImmutableCompositeNode(
\r
232 new QName(qName, "termination-points"), null, value);
\r
233 assignParentToChildren(terminationPointsNode);
\r
235 value = new ArrayList<Node<?>>();
\r
236 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "node-id"), null, "nodeId_02"));
\r
237 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "supporting-ne"), null, "networkId_02"));
\r
238 value.add(terminationPointsNode);
\r
239 CompositeNode node1Node = NodeFactory.createImmutableCompositeNode(
\r
240 new QName(qName, "node"), null, value);
\r
241 assignParentToChildren(node1Node);
\r
243 value = new ArrayList<Node<?>>();
\r
244 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "tp-id"), null, "tpId_18"));
\r
245 terminationPointNode1 = NodeFactory.createImmutableCompositeNode(
\r
246 new QName(qName, "termination-point"), null, value);
\r
247 assignParentToChildren(terminationPointNode1);
\r
249 value = new ArrayList<Node<?>>();
\r
250 value.add(terminationPointNode1);
\r
251 terminationPointsNode = NodeFactory.createImmutableCompositeNode(
\r
252 new QName(qName, "termination-points"), null, value);
\r
253 assignParentToChildren(terminationPointsNode);
\r
255 value = new ArrayList<Node<?>>();
\r
256 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "node-id"), null, "nodeId_16"));
\r
257 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "supporting-ne"), null, "networkId_17"));
\r
258 value.add(terminationPointsNode);
\r
259 CompositeNode node2Node = NodeFactory.createImmutableCompositeNode(
\r
260 new QName(qName, "node"), null, value);
\r
261 assignParentToChildren(node2Node);
\r
263 value = new ArrayList<Node<?>>();
\r
264 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "tp-id"), null, "tpId_18"));
\r
265 terminationPointNode1 = NodeFactory.createImmutableCompositeNode(
\r
266 new QName(qName, "termination-point"), null, value);
\r
267 assignParentToChildren(terminationPointNode1);
\r
269 value = new ArrayList<Node<?>>();
\r
270 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "tp-id"), null, "tpId_19"));
\r
271 CompositeNode terminationPointNode2 = NodeFactory.createImmutableCompositeNode(
\r
272 new QName(qName, "termination-point"), null, value);
\r
273 assignParentToChildren(terminationPointNode2);
\r
275 value = new ArrayList<Node<?>>();
\r
276 value.add(terminationPointNode1);
\r
277 value.add(terminationPointNode2);
\r
278 terminationPointsNode = NodeFactory.createImmutableCompositeNode(
\r
279 new QName(qName, "termination-points"), null, value);
\r
280 assignParentToChildren(terminationPointsNode);
\r
282 value = new ArrayList<Node<?>>();
\r
283 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "node-id"), null, "nodeId_19"));
\r
284 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "supporting-ne"), null, "networkId_20"));
\r
285 value.add(terminationPointsNode);
\r
286 CompositeNode node3Node = NodeFactory.createImmutableCompositeNode(
\r
287 new QName(qName, "node"), null, value);
\r
288 assignParentToChildren(node3Node);
\r
290 value = new ArrayList<Node<?>>();
\r
291 value.add(node1Node);
\r
292 value.add(node2Node);
\r
293 value.add(node3Node);
\r
294 CompositeNode nodesNode = NodeFactory.createImmutableCompositeNode(
\r
295 new QName(qName, "nodes"), null, value);
\r
296 assignParentToChildren(nodesNode);
\r
298 value = new ArrayList<Node<?>>();
\r
300 value.add(nodesNode);
\r
301 value.add(NodeFactory.createImmutableSimpleNode(new QName(qName, "topology-id"), null, "topId_01"));
\r
302 CompositeNode topology = NodeFactory.createImmutableCompositeNode(
\r
303 new QName(qName, "topology"), null, value);
\r
304 assignParentToChildren(topology);
\r
306 value = new ArrayList<Node<?>>();
\r
307 value.add(topology);
\r
308 CompositeNode topologies = NodeFactory.createImmutableCompositeNode(
\r
309 new QName(qName, "topologies"), null, value);
\r
310 assignParentToChildren(topologies);
\r
312 value = new ArrayList<Node<?>>();
\r
313 value.add(topologies);
\r
314 value.add(ntElementsNode);
\r
315 CompositeNode network = NodeFactory.createImmutableCompositeNode(
\r
316 new QName(qName, "network"), null, value);
\r
317 assignParentToChildren(network);
\r
323 * @param parentNode
\r
325 public static void assignParentToChildren(CompositeNode parentNode) {
\r
326 for (Node<?> child : parentNode.getChildren()) {
\r
327 ((AbstractNodeTO<?>) child).setParent(parentNode);
\r
332 * @return schema context of controller-network.yang
\r
334 public static SchemaContext loadSchemaContext() {
\r
335 YangModelParser yParser = new YangParserImpl();
\r
336 List<InputStream> yangInputStreams = new ArrayList<>();
\r
337 yangInputStreams.add(NodeHelper.class.getResourceAsStream(
\r
338 "/controller-network.yang"));
\r
339 yangInputStreams.add(NodeHelper.class.getResourceAsStream(
\r
340 "/ietf-inet-types@2010-09-24.yang"));
\r
341 Set<Module> modules = yParser
\r
342 .parseYangModelsFromStreams(yangInputStreams);
\r
343 return yParser.resolveSchemaContext(modules);
\r
347 * @param scriptName
\r
348 * @return tree root
\r
349 * @throws Exception
\r
351 public static CompositeNode loadConfigByGroovy(String scriptName) throws Exception {
\r
352 InputStream configStream = NodeHelper.class.getResourceAsStream(scriptName);
\r
353 Binding binding = new Binding();
\r
354 GroovyShell gShell = new GroovyShell(binding);
\r
355 LOG.debug("groovy: starting script parse.. " + scriptName);
\r
356 Script configScript = gShell.parse(new InputStreamReader(configStream));
\r
357 LOG.debug("groovy: starting script.. " + scriptName);
\r
358 configScript.run();
\r
359 LOG.debug("groovy: digging result");
\r
360 Object xmlGen = binding.getVariable("xmlGen");
\r
361 LOG.debug("xmlGen = " + xmlGen);
\r
362 Method getter = xmlGen.getClass().getDeclaredMethod("getBuilder", new Class[0]);
\r
363 MyNodeBuilder builder = (MyNodeBuilder) getter.invoke(xmlGen, new Object[0]);
\r
365 return builder.getRootNode();
\r
369 * @param pattern , e.g.: <pre>"//{0}:network/{1}:xx[text() = 'sss']"</pre>
\r
370 * @param nsArg , e.g.: <pre>{"uri:ns1", "uri:ns2"}</pre>
\r
371 * @return pattern with namespaces: <pre>//uri:ns1:network/uri:ns2:xx[text() = ''sss'']"</pre>
\r
373 public static String AddNamespaceToPattern(String pattern, Object... nsArg) {
\r
374 Object[] ns = nsArg;
\r
375 String patternNs = pattern.replaceAll("'", "''");
\r
377 ns = new Object[]{""};
\r
379 // add ':' into pattern after placeholders
\r
380 patternNs = patternNs.replaceAll("(\\{[0-9]+\\})", "$1:");
\r
383 return MessageFormat.format(patternNs, ns);
\r
390 * @throws Exception
\r
391 * @throws SAXException
\r
392 * @throws IOException
\r
394 public static void compareXmlTree(Document tree, String xmlFile, Class<?> clazz) throws Exception,
\r
395 SAXException, IOException {
\r
396 ByteArrayOutputStream actualRaw = new ByteArrayOutputStream();
\r
397 dumpDoc(tree, new PrintStream(actualRaw));
\r
398 Reader actualReader = new InputStreamReader(new ByteArrayInputStream(actualRaw.toByteArray()));
\r
400 Reader expectedReader = new InputStreamReader(clazz.getResourceAsStream(xmlFile));
\r
401 Diff myDiff = new Diff(expectedReader, actualReader);
\r
402 myDiff.overrideDifferenceListener(new IgnoreWhiteCharsDiffListener());
\r
404 boolean similar = myDiff.similar();
\r
406 System.out.println(new String(actualRaw.toByteArray()));
\r
408 Assert.assertEquals(myDiff.toString(), true, similar);
\r