Publish StoreUtils as NormalizedNodes
[yangtools.git] / yang / yang-data-impl / src / test / java / org / opendaylight / yangtools / yang / data / impl / NodeHelper.java
1 /*
2  * Copyright (c) 2013 Cisco Systems, Inc. and others.  All rights reserved.
3  *
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
7  */
8 package org.opendaylight.yangtools.yang.data.impl;
9
10 import groovy.lang.Binding;
11 import groovy.lang.GroovyShell;
12 import groovy.lang.Script;
13 import java.io.ByteArrayInputStream;
14 import java.io.ByteArrayOutputStream;
15 import java.io.IOException;
16 import java.io.InputStream;
17 import java.io.InputStreamReader;
18 import java.io.PrintStream;
19 import java.io.Reader;
20 import java.io.StringWriter;
21 import java.lang.reflect.Method;
22 import java.text.MessageFormat;
23 import java.util.ArrayList;
24 import java.util.List;
25 import java.util.Set;
26 import javax.xml.transform.OutputKeys;
27 import javax.xml.transform.Transformer;
28 import javax.xml.transform.TransformerException;
29 import javax.xml.transform.TransformerFactory;
30 import javax.xml.transform.dom.DOMSource;
31 import javax.xml.transform.stream.StreamResult;
32 import org.custommonkey.xmlunit.Diff;
33 import org.junit.Assert;
34 import org.opendaylight.yangtools.yang.common.QName;
35 import org.opendaylight.yangtools.yang.data.api.CompositeNode;
36 import org.opendaylight.yangtools.yang.data.api.Node;
37 import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNodes;
38 import org.opendaylight.yangtools.yang.model.api.Module;
39 import org.opendaylight.yangtools.yang.model.api.SchemaContext;
40 import org.opendaylight.yangtools.yang.model.parser.api.YangModelParser;
41 import org.opendaylight.yangtools.yang.parser.impl.YangParserImpl;
42 import org.slf4j.Logger;
43 import org.slf4j.LoggerFactory;
44 import org.w3c.dom.Document;
45 import org.xml.sax.SAXException;
46
47 /**
48  * @author michal.rehak
49  *
50  * @deprecated Use {@link NormalizedNodes} instead.
51  */
52 @Deprecated
53 public abstract class NodeHelper {
54
55     private static final Logger LOG = LoggerFactory.getLogger(NodeHelper.class);
56
57     /** xml source of example network configuration */
58     public static final String NETWORK_XML =
59             "<network xmlns=\"urn:opendaylight:controller:network\">\n" +
60                     //"<network>\n" +
61                     "    <topologies>\n" +
62                     "        <topology>\n" +
63                     "            <topology-id>topId_01</topology-id>\n" +
64                     "            <nodes>\n" +
65                     "                <node>\n" +
66                     "                    <node-id>nodeId_02</node-id>\n" +
67                     "                    <supporting-ne>networkId_02</supporting-ne>\n" +
68                     "                    <termination-points>\n" +
69                     "                        <termination-point>\n" +
70                     "                            <tp-id>tpId_03</tp-id>\n" +
71                     "                        </termination-point>\n" +
72                     "                    </termination-points>\n" +
73                     "                </node>\n" +
74                     "                <node>\n" +
75                     "                    <node-id>nodeId_16</node-id>\n" +
76                     "                    <supporting-ne>networkId_17</supporting-ne>\n" +
77                     "                    <termination-points>\n" +
78                     "                        <termination-point>\n" +
79                     "                            <tp-id>tpId_18</tp-id>\n" +
80                     "                        </termination-point>\n" +
81                     "                    </termination-points>\n" +
82                     "                </node>\n" +
83                     "                <node>\n" +
84                     "                    <node-id>nodeId_19</node-id>\n" +
85                     "                    <supporting-ne>networkId_20</supporting-ne>\n" +
86                     "                    <termination-points>\n" +
87                     "                        <termination-point>\n" +
88                     "                            <tp-id>tpId_18</tp-id>\n" +
89                     "                        </termination-point>\n" +
90                     "                        <termination-point>\n" +
91                     "                            <tp-id>tpId_19</tp-id>\n" +
92                     "                        </termination-point>\n" +
93                     "                    </termination-points>\n" +
94                     "                </node>\n" +
95                     "            </nodes>\n" +
96                     "            <links>\n" +
97                     "                <link>\n" +
98                     "                    <link-id>linkId_04</link-id>\n" +
99                     "                    <source>\n" +
100                     "                        <source-node>nodeId_05</source-node>\n" +
101                     "                        <source-tp>tpId_06</source-tp>\n" +
102                     "                    </source>\n" +
103                     "                    <destination>\n" +
104                     "                        <dest-node>nodeId_07</dest-node>\n" +
105                     "                        <dest-tp>tpId_08</dest-tp>\n" +
106                     "                    </destination>\n" +
107                     "                </link>\n" +
108                     "                <link>\n" +
109                     "                    <link-id>linkId_11</link-id>\n" +
110                     "                    <source>\n" +
111                     "                        <source-node>nodeId_12</source-node>\n" +
112                     "                        <source-tp>tpId_13</source-tp>\n" +
113                     "                    </source>\n" +
114                     "                    <destination>\n" +
115                     "                        <dest-node>nodeId_14</dest-node>\n" +
116                     "                        <dest-tp>tpId_15</dest-tp>\n" +
117                     "                    </destination>\n" +
118                     "                </link>\n" +
119                     "            </links>\n" +
120                     "        </topology>\n" +
121                     "    </topologies>\n" +
122                     "    <network-elements>\n" +
123                     "        <network-element>\n" +
124                     "            <element-id>ntElementId_09</element-id>\n" +
125                     "        </network-element>\n" +
126                     "        <network-element>\n" +
127                     "            <element-id>ntElementId_10</element-id>\n" +
128                     "        </network-element>\n" +
129                     "    </network-elements>\n" +
130                     "</network>";
131
132     private static String domTreeString(final Document domTree) throws TransformerException {
133         TransformerFactory transformerFact = TransformerFactory.newInstance();
134         transformerFact.setAttribute("indent-number", 4);
135         Transformer transformer = transformerFact.newTransformer();
136         transformer.setOutputProperty(OutputKeys.INDENT, "yes");
137         //initialize StreamResult with File object to save to file
138         StreamResult result = new StreamResult(new StringWriter());
139         DOMSource source = new DOMSource(domTree);
140         transformer.transform(source, result);
141         return result.getWriter().toString();
142     }
143
144     /**
145      * @param domTree
146      * @param out
147      * @throws Exception
148      */
149     private static void dumpDoc(final Document domTree, final PrintStream out) throws Exception {
150         out.println(domTreeString(domTree));
151     }
152
153     public static void dumpDoc(final Document domTree, final Logger logger) throws TransformerException {
154         logger.info("{}", domTreeString(domTree));
155     }
156
157     /**
158      * @param qName
159      * @return example tree, see {@link #NETWORK_XML}
160      */
161     public static CompositeNode buildTestConfigTree(final QName qName) {
162         List<Node<?>> value = new ArrayList<Node<?>>();
163         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "element-id"), null, "ntElementId_09"));
164         CompositeNode ntElementNode1 = NodeFactory.createImmutableCompositeNode(QName.create(qName, "network-element"),
165                 null, value);
166         assignParentToChildren(ntElementNode1);
167
168         value = new ArrayList<Node<?>>();
169         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "element-id"), null, "ntElementId_10"));
170         CompositeNode ntElementNode2 = NodeFactory.createImmutableCompositeNode(QName.create(qName, "network-element"),
171                 null, value);
172         assignParentToChildren(ntElementNode2);
173
174         value = new ArrayList<Node<?>>();
175         value.add(ntElementNode1);
176         value.add(ntElementNode2);
177         CompositeNode ntElementsNode = NodeFactory.createImmutableCompositeNode(
178                 QName.create(qName, "network-elements"), null, value);
179         assignParentToChildren(ntElementsNode);
180
181         value = new ArrayList<Node<?>>();
182         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "dest-node"), null, "nodeId_07"));
183         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "dest-tp"), null, "tpId_08"));
184         CompositeNode destination = NodeFactory.createImmutableCompositeNode(
185                 QName.create(qName, "destination"), null,
186                 value);
187         assignParentToChildren(destination);
188
189         value = new ArrayList<Node<?>>();
190         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "source-node"), null, "nodeId_05"));
191         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "source-tp"), null, "tpId_06"));
192         CompositeNode source = NodeFactory.createImmutableCompositeNode(
193                 QName.create(qName, "source"), null, value);
194         assignParentToChildren(source);
195
196         value = new ArrayList<Node<?>>();
197         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "link-id"), null, "linkId_04"));
198         value.add(source);
199         value.add(destination);
200         CompositeNode link1 = NodeFactory.createImmutableCompositeNode(
201                 QName.create(qName, "link"), null, value);
202         assignParentToChildren(link1);
203
204         value = new ArrayList<Node<?>>();
205         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "dest-node"), null, "nodeId_14"));
206         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "dest-tp"), null, "tpId_15"));
207         destination = NodeFactory.createImmutableCompositeNode(
208                 QName.create(qName, "destination"), null, value);
209         assignParentToChildren(destination);
210
211         value = new ArrayList<Node<?>>();
212         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "source-node"), null, "nodeId_12"));
213         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "source-tp"), null, "tpId_13"));
214         source = NodeFactory.createImmutableCompositeNode(
215                 QName.create(qName, "source"), null, value);
216         assignParentToChildren(source);
217
218         value = new ArrayList<Node<?>>();
219         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "link-id"), null, "linkId_11"));
220         value.add(source);
221         value.add(destination);
222         CompositeNode link2 = NodeFactory.createImmutableCompositeNode(
223                 QName.create(qName, "link"), null, value);
224         assignParentToChildren(link2);
225
226         value = new ArrayList<Node<?>>();
227         value.add(link1);
228         value.add(link2);
229         CompositeNode links = NodeFactory.createImmutableCompositeNode(
230                 QName.create(qName, "links"), null, value);
231         assignParentToChildren(links);
232
233
234         value = new ArrayList<Node<?>>();
235         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "tp-id"), null, "tpId_03"));
236         CompositeNode terminationPointNode1 = NodeFactory.createImmutableCompositeNode(
237                 QName.create(qName, "termination-point"), null, value);
238         assignParentToChildren(terminationPointNode1);
239
240         value = new ArrayList<Node<?>>();
241         value.add(terminationPointNode1);
242         CompositeNode terminationPointsNode = NodeFactory.createImmutableCompositeNode(
243                 QName.create(qName, "termination-points"), null, value);
244         assignParentToChildren(terminationPointsNode);
245
246         value = new ArrayList<Node<?>>();
247         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "node-id"), null, "nodeId_02"));
248         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "supporting-ne"), null, "networkId_02"));
249         value.add(terminationPointsNode);
250         CompositeNode node1Node = NodeFactory.createImmutableCompositeNode(
251                 QName.create(qName, "node"), null, value);
252         assignParentToChildren(node1Node);
253
254         value = new ArrayList<Node<?>>();
255         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "tp-id"), null, "tpId_18"));
256         terminationPointNode1 = NodeFactory.createImmutableCompositeNode(
257                 QName.create(qName, "termination-point"),
258                 null, value);
259         assignParentToChildren(terminationPointNode1);
260
261         value = new ArrayList<Node<?>>();
262         value.add(terminationPointNode1);
263         terminationPointsNode = NodeFactory.createImmutableCompositeNode(
264                 QName.create(qName, "termination-points"),
265                 null, value);
266         assignParentToChildren(terminationPointsNode);
267
268         value = new ArrayList<Node<?>>();
269         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "node-id"), null, "nodeId_16"));
270         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "supporting-ne"), null, "networkId_17"));
271         value.add(terminationPointsNode);
272         CompositeNode node2Node = NodeFactory.createImmutableCompositeNode(
273                 QName.create(qName, "node"), null, value);
274         assignParentToChildren(node2Node);
275
276         value = new ArrayList<Node<?>>();
277         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "tp-id"), null, "tpId_18"));
278         terminationPointNode1 = NodeFactory.createImmutableCompositeNode(
279                 QName.create(qName, "termination-point"),
280                 null, value);
281         assignParentToChildren(terminationPointNode1);
282
283         value = new ArrayList<Node<?>>();
284         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "tp-id"), null, "tpId_19"));
285         CompositeNode terminationPointNode2 = NodeFactory.createImmutableCompositeNode(
286                 QName.create(qName, "termination-point"), null, value);
287         assignParentToChildren(terminationPointNode2);
288
289         value = new ArrayList<Node<?>>();
290         value.add(terminationPointNode1);
291         value.add(terminationPointNode2);
292         terminationPointsNode = NodeFactory.createImmutableCompositeNode(
293                 QName.create(qName, "termination-points"),
294                 null, value);
295         assignParentToChildren(terminationPointsNode);
296
297         value = new ArrayList<Node<?>>();
298         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "node-id"), null, "nodeId_19"));
299         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "supporting-ne"), null, "networkId_20"));
300         value.add(terminationPointsNode);
301         CompositeNode node3Node = NodeFactory.createImmutableCompositeNode(
302                 QName.create(qName, "node"), null, value);
303         assignParentToChildren(node3Node);
304
305         value = new ArrayList<Node<?>>();
306         value.add(node1Node);
307         value.add(node2Node);
308         value.add(node3Node);
309         CompositeNode nodesNode = NodeFactory.createImmutableCompositeNode(
310                 QName.create(qName, "nodes"), null, value);
311         assignParentToChildren(nodesNode);
312
313         value = new ArrayList<Node<?>>();
314         value.add(links);
315         value.add(nodesNode);
316         value.add(NodeFactory.createImmutableSimpleNode(QName.create(qName, "topology-id"), null, "topId_01"));
317         CompositeNode topology = NodeFactory.createImmutableCompositeNode(
318                 QName.create(qName, "topology"), null, value);
319         assignParentToChildren(topology);
320
321         value = new ArrayList<Node<?>>();
322         value.add(topology);
323         CompositeNode topologies = NodeFactory.createImmutableCompositeNode(
324                 QName.create(qName, "topologies"), null,
325                 value);
326         assignParentToChildren(topologies);
327
328         value = new ArrayList<Node<?>>();
329         value.add(topologies);
330         value.add(ntElementsNode);
331         CompositeNode network = NodeFactory.createImmutableCompositeNode(
332                 QName.create(qName, "network"), null, value);
333         assignParentToChildren(network);
334
335         return network;
336     }
337
338     /**
339      * @param parentNode
340      */
341     public static void assignParentToChildren(final CompositeNode parentNode) {
342         for (Node<?> child : parentNode.getValue()) {
343             ((AbstractNodeTO<?>) child).setParent(parentNode);
344         }
345     }
346
347     /**
348      * @return schema context of controller-network.yang
349      */
350     public static SchemaContext loadSchemaContext() {
351         YangModelParser yParser = new YangParserImpl();
352         List<InputStream> yangInputStreams = new ArrayList<>();
353         yangInputStreams.add(NodeHelper.class.getResourceAsStream(
354                 "/controller-network.yang"));
355         yangInputStreams.add(NodeHelper.class.getResourceAsStream(
356                 "/ietf-inet-types@2010-09-24.yang"));
357         Set<Module> modules = yParser
358                 .parseYangModelsFromStreams(yangInputStreams);
359         return yParser.resolveSchemaContext(modules);
360     }
361
362     /**
363      * @param scriptName
364      * @return tree root
365      * @throws Exception
366      */
367     public static CompositeNode loadConfigByGroovy(final String scriptName) throws Exception {
368         InputStream configStream = NodeHelper.class.getResourceAsStream(scriptName);
369         Binding binding = new Binding();
370         GroovyShell gShell = new GroovyShell(binding);
371         LOG.debug("groovy: starting script parse..  {}", scriptName);
372         Script configScript = gShell.parse(new InputStreamReader(configStream));
373         LOG.debug("groovy: starting script..  {}", scriptName);
374         configScript.run();
375         LOG.debug("groovy: digging result");
376         Object xmlGen = binding.getVariable("xmlGen");
377         LOG.debug("xmlGen = {}", xmlGen);
378         Method getter = xmlGen.getClass().getDeclaredMethod("getBuilder", new Class[0]);
379         MyNodeBuilder builder = (MyNodeBuilder) getter.invoke(xmlGen, new Object[0]);
380
381         return builder.getRootNode();
382     }
383
384     /**
385      * @param pattern , e.g.: <pre>"//{0}:network/{1}:xx[text() = 'sss']"</pre>
386      * @param nsArg , e.g.: <pre>{"uri:ns1", "uri:ns2"}</pre>
387      * @return pattern with namespaces: <pre>//uri:ns1:network/uri:ns2:xx[text() = ''sss'']"</pre>
388      */
389     public static String AddNamespaceToPattern(final String pattern, final Object... nsArg) {
390         Object[] ns = nsArg;
391         String patternNs = pattern.replaceAll("'", "''");
392         if (ns == null) {
393             ns = new Object[]{""};
394         } else {
395             // add ':' into pattern after placeholders
396             patternNs = patternNs.replaceAll("(\\{[0-9]+\\})", "$1:");
397         }
398
399         return MessageFormat.format(patternNs, ns);
400     }
401
402     /**
403      * @param tree
404      * @param xmlFile
405      * @param clazz
406      * @throws Exception
407      * @throws SAXException
408      * @throws IOException
409      */
410     public static void compareXmlTree(final Document tree, final String xmlFile, final Class<?> clazz) throws Exception,
411     SAXException, IOException {
412         ByteArrayOutputStream actualRaw = new ByteArrayOutputStream();
413         dumpDoc(tree, new PrintStream(actualRaw));
414         Reader actualReader = new InputStreamReader(new ByteArrayInputStream(actualRaw.toByteArray()));
415
416         Reader expectedReader = new InputStreamReader(clazz.getResourceAsStream(xmlFile));
417         Diff myDiff = new Diff(expectedReader, actualReader);
418         myDiff.overrideDifferenceListener(new IgnoreWhiteCharsDiffListener());
419
420         boolean similar = myDiff.similar();
421         if (! similar) {
422             LOG.info("{}", new String(actualRaw.toByteArray()));
423         }
424         Assert.assertEquals(myDiff.toString(), true, similar);
425     }
426 }