o.o
o.o

Reputation: 3751

Parse XSD file to get element names from complex type

I am trying to get the element names in an XSD file. Let's say I have this xsd:

<xsd:complexType name="SomethingOne">
        <xsd:sequence>
            <xsd:element name="Id" type="xsd:int"/>
            <xsd:element name="Time" type="xsd:string"/>
            <xsd:element name="Location" type="xsd:string"/>
            <xsd:element name="Building" type="xsd:string"/>
            <xsd:element name="Comments" type="xsd:string"/>
        </xsd:sequence>
    </xsd:complexType>

    <xsd:complexType name="SomethingTwo">
        <xsd:sequence>
            <xsd:element name="Id" type="xsd:int"/>
            <xsd:element name="Time" type="xsd:string"/>
            <xsd:element name="Location" type="xsd:string"/>
            <xsd:element name="Building" type="xsd:string"/>
            <xsd:element name="Phone" type="xsd:string"/>
            <xsd:element name="Device" type="xsd:string"/>
            <xsd:element name="Protocol" type="xsd:string"/>
            <xsd:element name="Comments" type="xsd:string"/>
        </xsd:sequence>
    </xsd:complexType>

For SomethingOne, I want to print out all the element names (e.g. Id, Time, Location, etc...). Here's the Java code I have:

public void parse(String id) {
    try {
        // Setup classes to parse XSD file for complex types
        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
        DocumentBuilder db = dbf.newDocumentBuilder();
        Document doc = db.parse(new FileInputStream("filepath.xsd"));

        // Given the id, go to correct place in XSD to get all the parameters
        XPath xpath = XPathFactory.newInstance().newXPath();
        NodeList result = (NodeList) xpath.compile(getExpression(id)).evaluate(doc, XPathConstants.NODESET);

        for(int i = 0; i < result.getLength(); i++) 
        {
            Element e = (Element) result.item(i);
            System.out.println(e.getAttribute("name") + " = " + e.getNodeValue());
        }

    } catch(Exception e) {
        e.printStackTrace();
    }
}

// Get XSD Expression
private String getExpression(String id) {
    String expression = "";

    switch(id)
    {
    case "99":
        expression = "//xsd:complexType[@name='SomethingOne']//xsd:element";
        break;

    default:
        System.out.println("\n Invalid id");
        break;
    }

    return expression;
}

The problem I'm having is the for loop. result.getLength() returns 0. I cannot figure out why. Any help would be appreciated, thank you!

Upvotes: 0

Views: 6220

Answers (1)

norim_13
norim_13

Reputation: 303

Is your xsd valid? I tested the expression online and it worked, but only with a small workarounds in your xsd.

I just put the code inside a xsd:schema tag:

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" targetNamespace="http://www.w3schools.com" elementFormDefault="qualified">
    <xsd:complexType name="SomethingOne">
        <xsd:sequence>
            <xsd:element name="Id" type="xsd:int"/>
            <xsd:element name="Time" type="xsd:string"/>
            <xsd:element name="Location" type="xsd:string"/>
            <xsd:element name="Building" type="xsd:string"/>
            <xsd:element name="Comments" type="xsd:string"/>
        </xsd:sequence>
    </xsd:complexType>

    <xsd:complexType name="SomethingTwo">
        <xsd:sequence>
            <xsd:element name="Id" type="xsd:int"/>
            <xsd:element name="Time" type="xsd:string"/>
            <xsd:element name="Location" type="xsd:string"/>
            <xsd:element name="Building" type="xsd:string"/>
            <xsd:element name="Phone" type="xsd:string"/>
            <xsd:element name="Device" type="xsd:string"/>
            <xsd:element name="Protocol" type="xsd:string"/>
            <xsd:element name="Comments" type="xsd:string"/>
        </xsd:sequence>
    </xsd:complexType>
</xsd:schema>

The xpath query seems to be ok with these changes. Tested here: http://www.freeformatter.com/xpath-tester.html


UPDATE:

Remove "xsd:" in the xpath query:

//complexType[@name='SomethingOne']//element

I tested it in a Java project and returned 5 results.

Upvotes: 1

Related Questions