
/*
This Java source file was generated by test-to-java.xsl
and is a derived work from the source document.
The source document contained the following notice:


Copyright (c) 2001-2004 World Wide Web Consortium,
(Massachusetts Institute of Technology, Institut National de
Recherche en Informatique et en Automatique, Keio University). All
Rights Reserved. This program is distributed under the W3C's Software
Intellectual Property License. This program is distributed in the
hope that it will be useful, but WITHOUT ANY WARRANTY; without even
the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
PURPOSE.
See W3C License http://www.w3.org/Consortium/Legal/ for more details.

*/

package org.w3c.domts.level1.core;

import org.w3c.dom.*;


import org.w3c.domts.DOMTestCase;
import org.w3c.domts.DOMTestDocumentBuilderFactory;



/**
 * The "getElementsByTagName(name)" method may use the
 * special value "*" to match all tags in the element
 * tree.
 * Create a NodeList of all the descendant elements
 * of the last employee by using the special value "*".
 * The method should return all the descendant children(6)
 * in the order the children were encountered.
* @author NIST
* @author Mary Brady
* @see <a href="http://www.w3.org/TR/1998/REC-DOM-Level-1-19981001/level-one-core#ID-1938918D">http://www.w3.org/TR/1998/REC-DOM-Level-1-19981001/level-one-core#ID-1938918D</a>
*/
public final class elementgetelementsbytagnamespecialvalue extends DOMTestCase {

   /**
    * Constructor.
    * @param factory document factory, may not be null
    * @throws org.w3c.domts.DOMTestIncompatibleException Thrown if test is not compatible with parser configuration
    */
   public elementgetelementsbytagnamespecialvalue(final DOMTestDocumentBuilderFactory factory)  throws org.w3c.domts.DOMTestIncompatibleException {
      super(factory);

    //
    //   check if loaded documents are supported for content type
    //
    String contentType = getContentType();
    preload(contentType, "staff", false);
    }

   /**
    * Runs the test case.
    * @throws Throwable Any uncaught exception causes test to fail
    */
   public void runTest() throws Throwable {
      Document doc;
      NodeList elementList;
      Element lastEmployee;
      NodeList lastempList;
      Node child;
      String childName;
      java.util.List result = new java.util.ArrayList();
      
      java.util.List expectedResult = new java.util.ArrayList();
      expectedResult.add("employeeId");
      expectedResult.add("name");
      expectedResult.add("position");
      expectedResult.add("salary");
      expectedResult.add("gender");
      expectedResult.add("address");
      
      doc = (Document) load("staff", false);
      elementList = doc.getElementsByTagName("employee");
      lastEmployee = (Element) elementList.item(4);
      lastempList = lastEmployee.getElementsByTagName("*");
      for (int indexN1006A = 0; indexN1006A < lastempList.getLength(); indexN1006A++) {
          child = (Node) lastempList.item(indexN1006A);
    childName = child.getNodeName();
      result.add(childName);
        }
      assertEquals("tagNames", expectedResult, result);
      }
   /**
    *  Gets URI that identifies the test.
    *  @return uri identifier of test
    */
   public String getTargetURI() {
      return "http://www.w3.org/2001/DOM-Test-Suite/level1/core/elementgetelementsbytagnamespecialvalue";
   }
   /**
    * Runs this test from the command line.
    * @param args command line arguments
    */
   public static void main(final String[] args) {
        DOMTestCase.doMain(elementgetelementsbytagnamespecialvalue.class, args);
   }
}

