1 /*
   2  * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
   3  */
   4 /*
   5  * Licensed to the Apache Software Foundation (ASF) under one or more
   6  * contributor license agreements.  See the NOTICE file distributed with
   7  * this work for additional information regarding copyright ownership.
   8  * The ASF licenses this file to You under the Apache License, Version 2.0
   9  * (the "License"); you may not use this file except in compliance with
  10  * the License.  You may obtain a copy of the License at
  11  *
  12  *      http://www.apache.org/licenses/LICENSE-2.0
  13  *
  14  * Unless required by applicable law or agreed to in writing, software
  15  * distributed under the License is distributed on an "AS IS" BASIS,
  16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  17  * See the License for the specific language governing permissions and
  18  * limitations under the License.
  19  */
  20 package org.apache.qetest.dtm;
  21 
  22 import com.sun.org.apache.xml.internal.dtm.Axis;
  23 import com.sun.org.apache.xml.internal.dtm.DTM;
  24 import com.sun.org.apache.xml.internal.dtm.DTMAxisIterator;
  25 import java.io.IOException;
  26 import jaxp.library.JAXPBaseTest;
  27 import static org.apache.qetest.dtm.QeDtmConst.generateDTM;
  28 import static org.apache.qetest.dtm.QeDtmConst.getNodeName;
  29 import static org.testng.Assert.assertEquals;
  30 import org.testng.annotations.DataProvider;
  31 import org.testng.annotations.Test;
  32 
  33 /**
  34  *
  35  * Test for Axis Iterator walking. 
  36  */
  37 public class TestDTMIter extends JAXPBaseTest {
  38     /**
  39      * DTM instance.
  40      */
  41     private final DTM dtm;
  42 
  43     /*
  44      * Intiate by creating DTM instance and generate initial context.
  45      * 
  46      */
  47     public TestDTMIter() {
  48         dtm = generateDTM();
  49     }
  50     
  51     /**
  52      * A data provider that provide validation parameters and expected lines.
  53      * 
  54      * @return an two dimensional array that provide axis type and expected 
  55      * lines.
  56      */
  57     @DataProvider
  58     public Object[][] iterProvider() {
  59         final Object[][] chkChild = new Object[][] {
  60             { 65542, "COMMENT", "#comment", 3, " Default test document " },
  61             { 65543, "PROCESSING_INSTRUCTION", "api", 3, "a1=\"yes\" a2=\"no\"" },
  62             { 65544, "ELEMENT", "A", 3, null },
  63             { 65554, "ELEMENT", "Aa", 3, null },
  64             { 65555, "ELEMENT", "Ab", 3, null },
  65             { 65556, "ELEMENT", "Ac", 3, null },
  66             { 65558, "ELEMENT", "Ad", 3, null }
  67         };
  68 
  69         final Object[][] chkParent = new Object[][]{
  70             {65537, "ELEMENT", "Document", 2, null}
  71         };
  72 
  73         Object[][] chkSelf = new Object[][]{
  74             {65558, "ELEMENT", "Ad", 3, null}
  75         };
  76 
  77         final Object[][] chkNamespace = new Object[][]{
  78             {65538, "NAMESPACE", "xmlns:xml", 3, "http://www.w3.org/XML/1998/namespace"},
  79             {65539, "NAMESPACE", "xmlns:d", 3, "www.d.com"},
  80             {65559, "NAMESPACE", "xmlns:Ad", 4, "www.Ad.com"},
  81             {65560, "NAMESPACE", "xmlns:y", 4, "www.y.com"},
  82             {65561, "NAMESPACE", "xmlns:z", 4, "www.z.com"}
  83         };
  84 
  85         final Object[][] chkPreceding = new Object[][]{
  86             { 65542, "COMMENT", "#comment", 3, " Default test document "},
  87             { 65543, "PROCESSING_INSTRUCTION", "api", 3, "a1=\"yes\" a2=\"no\""},
  88             { 65544, "ELEMENT", "A", 3, null},
  89             { 65545, "COMMENT", "#comment", 4, " A Subtree "},
  90             { 65546, "ELEMENT", "B", 4, null},
  91             { 65547, "ELEMENT", "C", 5, null},
  92             { 65548, "ELEMENT", "D", 6, null},
  93             { 65549, "ELEMENT", "E", 7, null},
  94             { 65550, "ELEMENT", "F", 8, null},
  95             { 65554, "ELEMENT", "Aa", 3, null},
  96             { 65555, "ELEMENT", "Ab", 3, null},
  97             { 65556, "ELEMENT", "Ac", 3, null},
  98             { 65557, "ELEMENT", "Ac1", 4, null}
  99         };
 100 
 101         final Object[][] chkPrecedingsibling = new Object[][]{
 102             {65542, "COMMENT", "#comment", 3, " Default test document "},
 103             {65543, "PROCESSING_INSTRUCTION", "api", 3, "a1=\"yes\" a2=\"no\""},
 104             {65544, "ELEMENT", "A", 3, null},
 105             {65554, "ELEMENT", "Aa", 3, null},
 106             {65555, "ELEMENT", "Ab", 3, null},
 107             {65556, "ELEMENT", "Ac", 3, null}
 108         };
 109 
 110         final Object[][] chkFollowing = new Object[][]{
 111             { 65554, "ELEMENT", "Aa", 3, null},
 112             { 65555, "ELEMENT", "Ab", 3,  null},
 113             { 65556, "ELEMENT", "Ac", 3, null},
 114             { 65557, "ELEMENT", "Ac1", 4, null},
 115             { 65558, "ELEMENT", "Ad", 3, null},
 116             { 65562, "ELEMENT", "Ad1", 4, null}
 117         };
 118         
 119         final Object[][] checkFollowingSibling = new Object[][]{
 120             { 65554, "ELEMENT", "Aa", 3, null},
 121             { 65555, "ELEMENT", "Ab", 3, null},
 122             { 65556, "ELEMENT", "Ac", 3, null},
 123             { 65558, "ELEMENT", "Ad", 3, null},
 124         };
 125         
 126         final Object[][] checkDescendant = new Object[][]{
 127             {  65545, "COMMENT", "#comment", 4, " A Subtree "},
 128             {  65546, "ELEMENT", "B", 4, null},
 129             {  65547, "ELEMENT", "C", 5, null},
 130             {  65548, "ELEMENT", "D", 6, null},
 131             {  65549, "ELEMENT", "E", 7, null},
 132             {  65550, "ELEMENT", "F", 8, null}
 133         };
 134         
 135         final Object[][] checkDescendantSelf = new Object[][]{
 136             {   65544, "ELEMENT", "A", 3, null},
 137             {   65545, "COMMENT", "#comment", 4, " A Subtree "},
 138             {   65546, "ELEMENT", "B", 4, null},
 139             {   65547, "ELEMENT", "C", 5, null},
 140             {   65548, "ELEMENT", "D", 6, null},
 141             {   65549, "ELEMENT", "E", 7, null},
 142             {   65550, "ELEMENT", "F", 8, null}
 143         };
 144         
 145         final Object[][] checkAncestor = new Object[][]{
 146             { 65536, "DOCUMENT", "#document", 1, null},
 147             { 65537, "ELEMENT", "Document", 2, null},
 148             { 65544, "ELEMENT", "A", 3, null},
 149             { 65546, "ELEMENT", "B", 4, null},
 150             { 65547, "ELEMENT", "C", 5, null},
 151             { 65548, "ELEMENT", "D", 6, null},
 152             { 65549, "ELEMENT", "E", 7, null}
 153         };
 154  
 155         final Object[][] checkAncestorSelf = new Object[][]{
 156             { 65536, "DOCUMENT", "#document", 1, null},
 157             { 65537, "ELEMENT", "Document", 2, null},
 158             { 65544, "ELEMENT", "A", 3, null},
 159             { 65546, "ELEMENT", "B", 4, null},
 160             { 65547, "ELEMENT", "C", 5, null},
 161             { 65548, "ELEMENT", "D", 6, null},
 162             { 65549, "ELEMENT", "E", 7, null},
 163             { 65550, "ELEMENT", "F", 8, null}
 164         };        
 165         return new Object[][]{
 166             {65537, Axis.CHILD, "Document", false, chkChild},
 167             {65558, Axis.PARENT, "Ad", false, chkParent},
 168             {65558, Axis.SELF, "Ad", false, chkSelf},
 169             {65558, Axis.NAMESPACE, "Ad", false, chkNamespace},
 170             {65558, Axis.PRECEDING, "Ad", true, chkPreceding},
 171             {65558, Axis.PRECEDINGSIBLING, "Ad", true, chkPrecedingsibling},
 172             {65558, Axis.FOLLOWING, "Ad", false, chkFollowing},
 173             {65558, Axis.FOLLOWINGSIBLING, "Ad", false, checkFollowingSibling},
 174             {65544, Axis.DESCENDANT, "A", false, checkDescendant},
 175             {65544, Axis.DESCENDANTORSELF, "A", false, checkDescendantSelf} ,
 176             {65550, Axis.ANCESTOR, "F", true, checkAncestor},
 177             {65550, Axis.ANCESTORORSELF, "F", true, checkAncestorSelf}
 178         };
 179     }
 180 
 181     /**
 182      * Walk all kind of AxisIterator and checking API as expected.
 183      *
 184      * @param startNode node id to get AxisIterator.
 185      * @param axisType Axis type.
 186      * @param expectedName expected node name.
 187      * @param reversable expected boolean value for checking if the AxisIterator
 188      *        is revertible.
 189      * @param expectedLines an two dimensional array that will be validate
 190      *        traversal of AxisIterator
 191      * @throws IOException if any I/O operation error.
 192      */
 193     @Test(dataProvider = "iterProvider")
 194     public void test(int startNode, int axisType, String expectedName, 
 195             boolean reversable, Object[][] expectedLines) throws IOException {
 196         // This permission is special for the testing.
 197         setPermissions(
 198             new RuntimePermission("accessClassInPackage.com.sun.org.apache.xml.internal.utils"),
 199             new RuntimePermission("accessClassInPackage.com.sun.org.apache.xpath.internal.objects"));
 200         
 201         // Get a Iterator by given Axis type.
 202         DTMAxisIterator iter = dtm.getAxisIterator(axisType);
 203         iter.setStartNode(startNode);
 204 
 205         // Print out info about the axis
 206         assertEquals(dtm.getNodeName(startNode), expectedName);
 207         assertEquals(iter.isReverse(), reversable);
 208 
 209         // Iterate the axis and write node info to output file
 210         int line = 0;
 211         for (int itNode = iter.next(); DTM.NULL != itNode; 
 212                 itNode = iter.next(), line++) {
 213             assertEquals(itNode, expectedLines[line][0]);
 214             assertEquals(getNodeName(dtm, itNode), expectedLines[line][1]);
 215             assertEquals(dtm.getNodeName(itNode), expectedLines[line][2]);
 216             Integer expectedLevel = (Integer)expectedLines[line][3];
 217             assertEquals(dtm.getLevel(itNode), expectedLevel.shortValue());
 218             assertEquals(dtm.getNodeValue(itNode), expectedLines[line][4]);
 219         }
 220     }
 221 }