2 * ============LICENSE_START===================================================
3 * SPARKY (AAI UI service)
4 * ============================================================================
5 * Copyright © 2017 AT&T Intellectual Property.
6 * Copyright © 2017 Amdocs
8 * ============================================================================
9 * Licensed under the Apache License, Version 2.0 (the "License");
10 * you may not use this file except in compliance with the License.
11 * You may obtain a copy of the License at
13 * http://www.apache.org/licenses/LICENSE-2.0
15 * Unless required by applicable law or agreed to in writing, software
16 * distributed under the License is distributed on an "AS IS" BASIS,
17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18 * See the License for the specific language governing permissions and
19 * limitations under the License.
20 * ============LICENSE_END=====================================================
22 * ECOMP and OpenECOMP are trademarks
23 * and service marks of AT&T Intellectual Property.
26 package org.onap.aai.sparky.util;
28 import static org.junit.Assert.assertEquals;
29 import static org.junit.Assert.assertNotNull;
30 import static org.junit.Assert.assertNull;
31 import static org.junit.Assert.assertTrue;
33 import java.io.IOException;
34 import java.util.ArrayList;
35 import java.util.List;
37 import org.junit.Before;
38 import org.junit.Test;
39 import org.onap.aai.sparky.util.NodeUtils;
40 import org.onap.aai.sparky.util.TreeWalker;
42 import com.fasterxml.jackson.core.JsonProcessingException;
43 import com.fasterxml.jackson.databind.JsonNode;
44 import com.fasterxml.jackson.databind.ObjectMapper;
47 * The Class TreeWalkerTest.
49 public class TreeWalkerTest {
55 * @throws Exception the exception
58 public void init() throws Exception {
62 * Validate json node conversion null input.
65 public void validateJsonNodeConversionNullInput() {
67 TreeWalker walker = new TreeWalker();
70 JsonNode convertedNode = walker.convertJsonToNode(null);
71 assertNull("Converted node should have be null", convertedNode);
73 } catch (JsonProcessingException exc) {
75 } catch (IOException exc) {
82 * Validate json node conversion empty non json input.
85 public void validateJsonNodeConversionEmptyNonJsonInput() {
87 TreeWalker walker = new TreeWalker();
90 JsonNode convertedNode = walker.convertJsonToNode("");
91 assertNull("Converted node should have be null", convertedNode);
93 } catch (JsonProcessingException exc) {
95 } catch (IOException exc) {
102 * Validate json node conversion empty json input.
105 public void validateJsonNodeConversionEmptyJsonInput() {
107 TreeWalker walker = new TreeWalker();
110 JsonNode convertedNode = walker.convertJsonToNode("{}");
111 assertNotNull("Converted node should not be null", convertedNode);
113 ObjectMapper objectMapper = new ObjectMapper();
114 String convertedNodeAsStr = objectMapper.writeValueAsString(convertedNode);
116 assertEquals("{}", convertedNodeAsStr);
118 } catch (JsonProcessingException exc) {
120 } catch (IOException exc) {
127 * Validate walk tree null input.
130 public void validateWalkTreeNullInput() {
132 TreeWalker walker = new TreeWalker();
134 List<String> paths = new ArrayList<String>();
135 walker.walkTree(paths, null);
136 assertEquals(0, paths.size());
141 * Validate walk tree empty node.
144 public void validateWalkTreeEmptyNode() {
147 TreeWalker walker = new TreeWalker();
148 List<String> paths = new ArrayList<String>();
149 walker.walkTree(paths, walker.convertJsonToNode("{}"));
150 assertEquals(0, paths.size());
151 } catch (JsonProcessingException exc) {
153 } catch (IOException exc) {
160 * Validate walk tree one parent node.
163 public void validateWalkTreeOneParentNode() {
166 TreeWalker walker = new TreeWalker();
167 List<String> paths = new ArrayList<String>();
168 walker.walkTree(paths, walker.convertJsonToNode("{ \"root\" : { } }"));
169 assertEquals(1, paths.size());
170 } catch (JsonProcessingException exc) {
172 } catch (IOException exc) {
179 * Validate walk tree one parent node with object array.
182 public void validateWalkTreeOneParentNodeWithObjectArray() {
186 "{\"Employee\":[{\"id\":\"101\",\"name\":\"Pushkar\",\"salary\":\"5000\"},"
187 + "{\"id\":\"102\",\"name\":\"Rahul\",\"salary\":\"4000\"},"
188 + "{\"id\":\"103\",\"name\":\"tanveer\",\"salary\":\"56678\"}]}";
189 TreeWalker walker = new TreeWalker();
190 List<String> paths = new ArrayList<String>();
191 walker.walkTree(paths, walker.convertJsonToNode(jsonStr));
192 assertEquals(9, paths.size());
193 } catch (JsonProcessingException exc) {
195 } catch (IOException exc) {
202 * Validate walk tree one parent node with value array.
205 public void validateWalkTreeOneParentNodeWithValueArray() {
208 String jsonStr = "{ \"colors\" : [ \"yellow\", \"blue\", \"red\" ] }";
209 TreeWalker walker = new TreeWalker();
210 List<String> paths = new ArrayList<String>();
211 walker.walkTree(paths, walker.convertJsonToNode(jsonStr));
213 assertEquals(3, paths.size());
214 } catch (JsonProcessingException exc) {
216 } catch (IOException exc) {
223 * Test walk for complex entity type aai entity node descriptors.
226 public void testWalkForComplexEntityType_AaiEntityNodeDescriptors() {
230 "{ \"generalNodeClass\": { \"class\": \"aai-entity-node general-node\","
231 + " \"visualElements\": [ { \"type\": \"circle\","
232 + " \"class\": \"outer\", \"svgAttributes\": {"
233 + " \"r\": \"20\" } }, {"
234 + " \"type\": \"circle\", \"class\": \"inner\", "
235 + " \"svgAttributes\": { \"r\": \"10\" "
236 + "} }, { \"type\": \"text\", "
237 + "\"class\": \"id-type-label\", \"displayKey\": \"itemType\", "
238 + " \"shapeAttributes\": { \"offset\": { "
239 + " \"x\": \"0\", \"y\": \"30\" } "
240 + " } }, { \"type\": \"text\", "
241 + " \"class\": \"id-value-label\", \"displayKey\":"
242 + " \"itemNameValue\", \"shapeAttributes\": { "
243 + " \"offset\": { \"x\": \"0\", "
244 + " \"y\": \"40\" } } } ] "
245 + " }, \"searchedNodeClass\": { \"class\": \"aai-entity-node search-node\","
246 + " \"visualElements\": [ { \"type\": \"circle\","
247 + " \"class\": \"outer\", \"svgAttributes\": { "
248 + " \"r\": \"20\" } }, { "
249 + " \"type\": \"circle\", \"class\": \"inner\", "
250 + " \"svgAttributes\": { \"r\": \"10\" }"
251 + " }, { \"type\": \"text\", "
252 + "\"class\": \"id-type-label\", \"displayKey\": \"itemType\", "
253 + " \"shapeAttributes\": { \"offset\": { "
254 + " \"x\": \"0\", \"y\": \"30\" }"
255 + " } }, { \"type\": \"text\", "
256 + " \"class\": \"id-value-label\", "
257 + "\"displayKey\": \"itemNameValue\", \"shapeAttributes\": {"
258 + " \"offset\": { \"x\": \"0\","
259 + " \"y\": \"40\" } }"
260 + " } ] }, \"selectedSearchedNodeClass\": { "
261 + "\"class\": \"aai-entity-node selected-search-node\", \"visualElements\": ["
262 + " { \"type\": \"circle\", "
263 + "\"class\": \"outer\", \"svgAttributes\": {"
264 + " \"r\": \"20\" } }, {"
265 + " \"type\": \"circle\", \"class\": \"inner\","
266 + " \"svgAttributes\": { \"r\": \"10\" "
267 + " } }, { \"type\": \"text\", "
268 + " \"class\": \"id-type-label\", \"displayKey\": \"itemType\","
269 + " \"shapeAttributes\": { \"offset\": {"
270 + " \"x\": \"0\", \"y\": \"30\""
272 + " \"type\": \"text\", \"class\": \"id-value-label\", "
273 + " \"displayKey\": \"itemNameValue\", \"shapeAttributes\": {"
274 + " \"offset\": { \"x\": \"0\", "
275 + " \"y\": \"40\" } } } ]"
276 + " }, \"selectedNodeClass\": { \"class\":"
277 + " \"aai-entity-node selected-node\","
278 + " \"visualElements\": [ { \"type\": \"circle\","
279 + " \"class\": \"outer\", \"svgAttributes\": {"
280 + " \"r\": \"20\" } }, {"
281 + " \"type\": \"circle\", \"class\": \"inner\","
282 + " \"svgAttributes\": { \"r\": \"10\" "
283 + " } }, { \"type\": \"text\", "
284 + " \"class\": \"id-type-label\", \"displayKey\": \"itemType\","
285 + " \"shapeAttributes\": { \"offset\": "
287 + " \"x\": \"0\", \"y\": \"30\" } "
288 + " } }, { \"type\": \"text\","
289 + " \"class\": \"id-value-label\", \"displayKey\":"
290 + " \"itemNameValue\", \"shapeAttributes\": { "
291 + "\"offset\": { \"x\": \"0\", "
292 + "\"y\": \"40\" } } } ] }}";
293 TreeWalker walker = new TreeWalker();
294 List<String> paths = new ArrayList<String>();
295 walker.walkTree(paths, walker.convertJsonToNode(jsonStr));
297 assertEquals(68, paths.size());
300 * Example of expected value
302 * generalNodeClass.class=aai-entity-node general-node
303 * generalNodeClass.visualElements.type=circle generalNodeClass.visualElements.class=outer
304 * generalNodeClass.visualElements.svgAttributes.r=20
305 * generalNodeClass.visualElements.type=circle generalNodeClass.visualElements.class=inner
306 * generalNodeClass.visualElements.svgAttributes.r=10
307 * generalNodeClass.visualElements.type=text
308 * generalNodeClass.visualElements.class=id-type-label
309 * generalNodeClass.visualElements.displayKey=itemType
310 * generalNodeClass.visualElements.shapeAttributes.offset.x=0
311 * generalNodeClass.visualElements.shapeAttributes.offset.y=30
312 * generalNodeClass.visualElements.type=text
313 * generalNodeClass.visualElements.class=id-value-label
314 * generalNodeClass.visualElements.displayKey=itemNameValue
315 * generalNodeClass.visualElements.shapeAttributes.offset.x=0
316 * generalNodeClass.visualElements.shapeAttributes.offset.y=40
317 * searchedNodeClass.class=aai-entity-node search-node
318 * searchedNodeClass.visualElements.type=circle searchedNodeClass.visualElements.class=outer
319 * searchedNodeClass.visualElements.svgAttributes.r=20
320 * searchedNodeClass.visualElements.type=circle searchedNodeClass.visualElements.class=inner
321 * searchedNodeClass.visualElements.svgAttributes.r=10
322 * searchedNodeClass.visualElements.type=text
323 * searchedNodeClass.visualElements.class=id-type-label
324 * searchedNodeClass.visualElements.displayKey=itemType
325 * searchedNodeClass.visualElements.shapeAttributes.offset.x=0
326 * searchedNodeClass.visualElements.shapeAttributes.offset.y=30
327 * searchedNodeClass.visualElements.type=text
328 * searchedNodeClass.visualElements.class=id-value-label
329 * searchedNodeClass.visualElements.displayKey=itemNameValue
330 * searchedNodeClass.visualElements.shapeAttributes.offset.x=0
331 * searchedNodeClass.visualElements.shapeAttributes.offset.y=40
332 * selectedSearchedNodeClass.class=aai-entity-node selected-search-node
333 * selectedSearchedNodeClass.visualElements.type=circle
334 * selectedSearchedNodeClass.visualElements.class=outer
335 * selectedSearchedNodeClass.visualElements.svgAttributes.r=20
336 * selectedSearchedNodeClass.visualElements.type=circle
337 * selectedSearchedNodeClass.visualElements.class=inner
338 * selectedSearchedNodeClass.visualElements.svgAttributes.r=10
339 * selectedSearchedNodeClass.visualElements.type=text
340 * selectedSearchedNodeClass.visualElements.class=id-type-label
341 * selectedSearchedNodeClass.visualElements.displayKey=itemType
342 * selectedSearchedNodeClass.visualElements.shapeAttributes.offset.x=0
343 * selectedSearchedNodeClass.visualElements.shapeAttributes.offset.y=30
344 * selectedSearchedNodeClass.visualElements.type=text
345 * selectedSearchedNodeClass.visualElements.class=id-value-label
346 * selectedSearchedNodeClass.visualElements.displayKey=itemNameValue
347 * selectedSearchedNodeClass.visualElements.shapeAttributes.offset.x=0
348 * selectedSearchedNodeClass.visualElements.shapeAttributes.offset.y=40
349 * selectedNodeClass.class=aai-entity-node selected-node
350 * selectedNodeClass.visualElements.type=circle selectedNodeClass.visualElements.class=outer
351 * selectedNodeClass.visualElements.svgAttributes.r=20
352 * selectedNodeClass.visualElements.type=circle selectedNodeClass.visualElements.class=inner
353 * selectedNodeClass.visualElements.svgAttributes.r=10
354 * selectedNodeClass.visualElements.type=text
355 * selectedNodeClass.visualElements.class=id-type-label
356 * selectedNodeClass.visualElements.displayKey=itemType
357 * selectedNodeClass.visualElements.shapeAttributes.offset.x=0
358 * selectedNodeClass.visualElements.shapeAttributes.offset.y=30
359 * selectedNodeClass.visualElements.type=text
360 * selectedNodeClass.visualElements.class=id-value-label
361 * selectedNodeClass.visualElements.displayKey=itemNameValue
362 * selectedNodeClass.visualElements.shapeAttributes.offset.x=0
363 * selectedNodeClass.visualElements.shapeAttributes.offset.y=40
366 } catch (JsonProcessingException exc) {
368 } catch (IOException exc) {
375 * Test complex object inversion equality.
378 public void testComplexObjectInversionEquality() {
381 * Dave Adams (1-Nov-2016):
383 * Ok.. I agree...weird title of the test-case. This test is focused on the isEqual equality
384 * test within the NodeUtils helper class which compares the sorted structural paths of two Json
385 * Object representations. I attempted to normalize unordered structures to produce an equality
386 * result, as there doesn't seem to be any natural equality test between two JsonNode objects
387 * that I could find to date.
389 * Basically, this test is confirming that if the same object values are present in different
390 * orders, they are effectively the same Json Object representation, and pass, at least my
391 * structural value equality test.
393 * I reordered the aaiEntityNodeDescriptors top level class types, and change the order of the
394 * x,y coordinates to be y,x. Same values different order. Once again, the expectation is that
395 * both representations are objectively equal, they just have different json representations.
400 "{ \"generalNodeClass\": { \"class\": \"aai-entity-node general-node\","
401 + " \"visualElements\": [ { \"type\": \"circle\","
402 + " \"class\": \"outer\", \"svgAttributes\": {"
403 + " \"r\": \"20\" } }, {"
404 + " \"type\": \"circle\", \"class\": \"inner\","
405 + " \"svgAttributes\": { \"r\": \"10\""
406 + " } }, { \"type\": \"text\","
407 + " \"class\": \"id-type-label\", \"displayKey\":"
408 + " \"itemType\", \"shapeAttributes\": { \"offset\":"
409 + " { \"x\": \"0\", \"y\": \"30\""
411 + " \"type\": \"text\", \"class\": \"id-value-label\","
412 + " \"displayKey\": \"itemNameValue\","
413 + " \"shapeAttributes\": { \"offset\":"
414 + " { \"x\": \"0\", \"y\": \"40\""
416 + " \"searchedNodeClass\": { \"class\": \"aai-entity-node search-node\","
417 + " \"visualElements\": [ { \"type\": \"circle\","
418 + " \"class\": \"outer\", \"svgAttributes\": {"
419 + " \"r\": \"20\" } }, {"
420 + " \"type\": \"circle\", \"class\": \"inner\","
421 + " \"svgAttributes\": { \"r\": \"10\""
422 + " } }, { \"type\": \"text\","
423 + " \"class\": \"id-type-label\", \"displayKey\":"
424 + " \"itemType\", \"shapeAttributes\": { \"offset\": {"
425 + " \"x\": \"0\", \"y\": \"30\""
427 + " \"type\": \"text\", \"class\": \"id-value-label\","
428 + " \"displayKey\": \"itemNameValue\","
429 + " \"shapeAttributes\": { \"offset\": {"
430 + " \"x\": \"0\", \"y\": \"40\""
432 + " \"selectedSearchedNodeClass\": { \"class\":"
433 + " \"aai-entity-node selected-search-node\", \"visualElements\": ["
434 + " { \"type\": \"circle\", \"class\":"
435 + " \"outer\", \"svgAttributes\": { \"r\": \"20\""
436 + " } }, { \"type\": \"circle\","
437 + " \"class\": \"inner\", \"svgAttributes\": {"
438 + " \"r\": \"10\" } }, {"
439 + " \"type\": \"text\", \"class\": \"id-type-label\","
440 + " \"displayKey\": \"itemType\", \"shapeAttributes\": {"
441 + " \"offset\": { \"x\": \"0\","
442 + " \"y\": \"30\" } }"
443 + " }, { \"type\": \"text\","
444 + " \"class\": \"id-value-label\","
445 + " \"displayKey\": \"itemNameValue\","
446 + " \"shapeAttributes\": { \"offset\": {"
447 + " \"x\": \"0\", \"y\": \"40\""
449 + " \"selectedNodeClass\": { \"class\": \"aai-entity-node selected-node\","
450 + " \"visualElements\": [ { \"type\": \"circle\","
451 + " \"class\": \"outer\", \"svgAttributes\": {"
452 + " \"r\": \"20\" } }, {"
453 + " \"type\": \"circle\", \"class\": \"inner\","
454 + " \"svgAttributes\": { \"r\": \"10\""
455 + " } }, { \"type\": \"text\","
456 + " \"class\": \"id-type-label\", \"displayKey\":"
457 + " \"itemType\", \"shapeAttributes\": {"
458 + " \"offset\": { \"x\": \"0\","
460 + " } }, { \"type\": \"text\","
461 + " \"class\": \"id-value-label\", \"displayKey\":"
462 + " \"itemNameValue\", \"shapeAttributes\": {"
463 + " \"offset\": { \"x\": \"0\","
464 + " \"y\": \"40\" } }"
467 "{ \"searchedNodeClass\": { \"class\": \"aai-entity-node search-node\","
468 + " \"visualElements\": [ { \"type\": \"circle\","
469 + " \"class\": \"outer\", \"svgAttributes\": {"
470 + " \"r\": \"20\" } },"
471 + " { \"type\": \"circle\","
472 + " \"class\": \"inner\", \"svgAttributes\": {"
473 + " \"r\": \"10\" } }, {"
474 + " \"type\": \"text\", \"class\": \"id-type-label\","
475 + " \"displayKey\": \"itemType\", \"shapeAttributes\": {"
476 + " \"offset\": { \"y\": \"30\","
477 + " \"x\": \"0\" } }"
478 + " }, { \"type\": \"text\","
479 + " \"class\": \"id-value-label\","
480 + " \"displayKey\": \"itemNameValue\","
481 + " \"shapeAttributes\": { \"offset\": {"
482 + " \"y\": \"40\", \"x\": \"0\""
484 + " \"selectedSearchedNodeClass\": { \"class\":"
485 + " \"aai-entity-node selected-search-node\", \"visualElements\": ["
486 + " { \"type\": \"circle\", \"class\":"
487 + " \"outer\", \"svgAttributes\": { \"r\": \"20\""
488 + " } }, { \"type\": \"circle\","
489 + " \"class\": \"inner\", \"svgAttributes\": {"
490 + " \"r\": \"10\" } }, {"
491 + " \"type\": \"text\", \"class\": \"id-type-label\","
492 + " \"displayKey\": \"itemType\", \"shapeAttributes\": {"
493 + " \"offset\": { \"y\": \"30\","
494 + " \"x\": \"0\" } }"
495 + " }, { \"type\": \"text\","
496 + " \"class\": \"id-value-label\","
497 + " \"displayKey\": \"itemNameValue\","
498 + " \"shapeAttributes\": { \"offset\": {"
499 + " \"y\": \"40\", \"x\": \"0\""
501 + " \"selectedNodeClass\": { \"class\": \"aai-entity-node selected-node\","
502 + " \"visualElements\": [ { \"type\": \"circle\","
503 + " \"class\": \"outer\", \"svgAttributes\": {"
504 + " \"r\": \"20\" } }, {"
505 + " \"type\": \"circle\", \"class\": \"inner\","
506 + " \"svgAttributes\": { \"r\": \"10\""
507 + " } }, { \"type\": \"text\","
508 + " \"class\": \"id-type-label\","
509 + " \"displayKey\": \"itemType\", \"shapeAttributes\": {"
510 + " \"offset\": { \"y\": \"30\","
511 + " \"x\": \"0\" } }"
512 + " }, { \"type\": \"text\","
513 + " \"class\": \"id-value-label\","
514 + " \"displayKey\": \"itemNameValue\","
515 + " \"shapeAttributes\": { \"offset\": {"
516 + " \"y\": \"40\", \"x\": \"0\""
518 + " \"generalNodeClass\": { \"class\":"
519 + " \"aai-entity-node general-node\", \"visualElements\": ["
520 + " { \"type\": \"circle\","
521 + " \"class\": \"outer\", \"svgAttributes\": {"
522 + " \"r\": \"20\" } },"
523 + " { \"type\": \"circle\","
524 + " \"class\": \"inner\", \"svgAttributes\": {"
525 + " \"r\": \"10\" } },"
526 + " { \"type\": \"text\","
527 + " \"class\": \"id-type-label\", \"displayKey\":"
528 + " \"itemType\", \"shapeAttributes\": {"
529 + " \"offset\": { \"y\": \"30\","
532 + " \"type\": \"text\","
533 + " \"class\": \"id-value-label\", \"displayKey\":"
534 + " \"itemNameValue\", \"shapeAttributes\": {"
535 + " \"offset\": { \"y\": \"40\","
539 TreeWalker walker = new TreeWalker();
540 List<String> n1Paths = new ArrayList<String>();
541 List<String> n2Paths = new ArrayList<String>();
543 JsonNode n1 = walker.convertJsonToNode(n1Str);
544 JsonNode n2 = walker.convertJsonToNode(n2Str);
545 walker.walkTree(n1Paths, n1);
546 walker.walkTree(n2Paths, n2);
548 assertEquals(68, n1Paths.size());
549 assertEquals(68, n2Paths.size());
551 assertTrue(NodeUtils.isEqual(n1, n2));
553 } catch (JsonProcessingException exc) {
555 } catch (IOException exc) {