Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Creating an XML file from XSD from JAXB

Tags:

java

xml

jaxb

xsd

I'm having trouble creating an XML file from XSD using JAXB below is the XSD file used to create it. (Note: Names have been edited due to confidentiality)

    <?xml version="1.0" encoding="UTF-8"?>
    <xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" targetNamespace="http://ibm.org/seleniumframework" xmlns:xs="http://www.w3.org/2001/XMLSchema">

    <xs:element name="Test" type="sel:Test">
        <xs:complexType>
            <xs:choice minOccurs="1" maxOccurs="unbounded">
                <xs:element name="Option1" type="sel:Option1Type" xmlns:sel="http://ibm.org/seleniumframework"/>
                <xs:element name="Option2" type="sel:Option2Type" xmlns:sel="http://ibm.org/seleniumframework"/>
                <xs:element name="Option3" type="sel:ScreensType" xmlns:sel="http://ibm.org/seleniumframework"/>
            </xs:choice>
        </xs:complexType>
    </xs:element>

    <xs:complexType name="ScreensType">
        <xs:sequence>
            <xs:element type="sel:ScreenType" name="Screen" minOccurs="1" maxOccurs="unbounded" xmlns:sel="http://ibm.org/seleniumframework"/>
        </xs:sequence>
    </xs:complexType>

    <xs:complexType name="ScreenType">
        <xs:sequence>
            <xs:element name="ScreenData" minOccurs="1" maxOccurs="unbounded" xmlns:sel="http://ibm.org/seleniumframework"/>
        </xs:sequence>
        <xs:attribute type="xs:string" name="name1" use="required" />
        <xs:attribute type="xs:string" name="name2" use="required" />
        <xs:attribute type="xs:string" name="name3" use="required" />
    </xs:complexType>

</xs:schema>

This is the code I am using to try and create the XML:

public void generateXml() throws JAXBException, IOException {

            Test test = new Test();
            ScreensType screens = new ScreensType();
            ScreenType screen = new ScreenType();
            screen.setName1("a");
            screen.setName2("b");
            screen.setName3("c");

            File f = new File("new.xml");
            JAXBContext context= JAXBContext.newInstance("com.q1labs.qa.xmlgenerator.model.generatedxmlclasses");
            Marshaller jaxbMarshaller = context.createMarshaller();
            jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);

            jaxbMarshaller.marshal(test, f);
            jaxbMarshaller.marshal(test, System.out);

        }

This is the output

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
        <Test xmlns="http://ibm.org/seleniumframework"/>

How can I get the code to output the screens and the screen tag along with it's properties, I'm not sure what I'm doing wrong.

like image 232
Colin747 Avatar asked Aug 27 '12 18:08

Colin747


2 Answers

You create an instance of Test and ScreensType but never set any of their properties before marshalling them to XML. Below is the corrected code.

public void generateXml() throws JAXBException, IOException {
    Test test = new Test();
    ScreensType screens = new ScreensType();
    test.getOption1OrOption2OrOption3().add(screens);
    ScreenType screen = new ScreenType();
    screen.setName1("a");
    screen.setName2("b");
    screen.setName3("c");
    screens.getScreen().add(screen);

    File f = new File("new.xml");
    JAXBContext context= JAXBContext.newInstance("com.q1labs.qa.xmlgenerator.model.generatedxmlclasses");
    Marshaller jaxbMarshaller = context.createMarshaller();
    jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);

    jaxbMarshaller.marshal(test, f);
    jaxbMarshaller.marshal(test, System.out);
}

Output

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<Test xmlns="http://ibm.org/seleniumframework">
    <Option3>
        <Screen name1="a" name2="b" name3="c"/>
    </Option3>
</Test>
like image 89
bdoughan Avatar answered Sep 20 '22 13:09

bdoughan


After trying for couple of days, eventually i was able to create the xml from xsd properly using the code given below. Hope this helps :

           String filename = "<filepath/filename>";

          final Document doc = loadXsdDocument(filename);

       //Find the docs root element and use it to find the targetNamespace
            final Element rootElem = doc.getDocumentElement();
            String targetNamespace = null;
            if (rootElem != null && rootElem.getNodeName().equals("xs:schema")) 
                       {
                targetNamespace = rootElem.getAttribute("targetNamespace");
            }


                        //Parse the file into an XSModel object
            XSModel xsModel = new XSParser().parse(filename);

                        //Define defaults for the XML generation
            XSInstance instance = new XSInstance();
            instance.minimumElementsGenerated = 1;
            instance.maximumElementsGenerated = 1;
            instance.generateDefaultAttributes = true;
            instance.generateOptionalAttributes = true;
            instance.maximumRecursionDepth = 0;
            instance.generateAllChoices = true;
            instance.showContentModel = true;
            instance.generateOptionalElements = true;

                        //Build the sample xml doc
                        //Replace first param to XMLDoc with a file input stream to write to file
            QName rootElement = new QName(targetNamespace, "<xsd file name>");
            XMLDocument sampleXml = new XMLDocument(new StreamResult(System.out), true, 4, null);
            instance.generate(xsModel, rootElement, sampleXml);
        } catch (TransformerConfigurationException e) 
                {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

    public static Document loadXsdDocument(String inputName) {
        final String filename = inputName;

        final DocumentBuilderFactory factory = DocumentBuilderFactory
                .newInstance();
        factory.setValidating(false);
        factory.setIgnoringElementContentWhitespace(true);
        factory.setIgnoringComments(true);
        Document doc = null;

        try {
            final DocumentBuilder builder = factory.newDocumentBuilder();
            final File inputFile = new File(filename);
            doc = builder.parse(inputFile);
        } catch (final Exception e) {
            e.printStackTrace();
            // throw new ContentLoadException(msg);
        }

        return doc;
    }
like image 32
Amarnath Avatar answered Sep 19 '22 13:09

Amarnath