3

I have an XSD file. Using xjc I generate classes from it. How can I change the propOrder value from XmlType annotation in generated clases? I don't want to change XSD file as long as I am not an owner of it and I don't want to change classes generated from this schema. Is there any way to achieve this with custom binding file(xjb)? The problem is that propOrder value is not desirable for me. As a last solution I consider using parseMethod/printMethod for this class but this will be too tricky.

I am dealing with FpML(XML base format), here is an XSD element:

<xsd:complexType name="TradeIdentifier">
    <xsd:sequence>
        <xsd:choice>

            <xsd:sequence>
                <xsd:element name="issuer" type="IssuerId"></xsd:element>
                <xsd:element name="tradeId" type="TradeId"></xsd:element>
            </xsd:sequence>

            <xsd:sequence>
                <xsd:group ref="PartyAndAccountReferences.model">
                </xsd:group>
                <xsd:element name="reportingRole" type="ReportingRole" minOccurs="0"></xsd:element>
                <xsd:choice maxOccurs="unbounded">
                    <xsd:element name="tradeId" type="TradeId"></xsd:element>
                    <xsd:element name="versionedTradeId" type="VersionedTradeId"></xsd:element>
                </xsd:choice>
            </xsd:sequence>

        </xsd:choice>
    </xsd:sequence>
</xsd:complexType>

and here is propOrder:

@XmlType(name = "TradeIdentifier", propOrder = {
    "issuer",
    "tradeId",
    "partyReference",
    "accountReference",
    "reportingRole",
    "tradeIdOrVersionedTradeId"
})

when I set in object partyReference and tradeId, the generated xml is:

<partyTradeIdentifier>
    <tradeId>NONREF</tradeId>
    <partyReference href="Party2"/>
</partyTradeIdentifier>

which fails XSD verification with error:

[org.xml.sax.SAXParseException: cvc-complex-type.2.4.a: Invalid content was found starting with element 'tradeId'. One of '{"http://www.nsd.ru/repository/fpml-5.4":issuer, "http://www.nsd.ru/repository/fpml-5.4":partyReference}' is expected.]

The solution is to place partyReference element prior to tradeId. When I do it manually, everything works. But I don't want to change generated class manually, because in case of schema change I will have to repeat such manipulations. This is a way to hell.

I tried to rename one tradeId, so there would be two fields. But instead just one tradeId field is renamed and problem remains.

Mikhail
  • 4,175
  • 15
  • 31
  • If you change the `propOrder` you will lose the ability to validate against the XML schema. How is the current order not desirable? You could always use XSLT to control the output: http://blog.bdoughan.com/2012/11/using-jaxb-with-xslt-to-produce-html.html – bdoughan Apr 24 '13 at 10:31
  • Ability to validate against schema is what I'am trying to achieve. – Mikhail Apr 24 '13 at 10:55
  • 1
    Looks like this bug https://java.net/jira/browse/JAXB-793. I have not find any workaround. – Mikhail Apr 24 '13 at 11:57

1 Answers1

1

binding.xml

Try generating the classes from your XML schema using the following binding file:

<?xml version="1.0" encoding="UTF-8"?>
<bindings xmlns="http://java.sun.com/xml/ns/jaxb" xmlns:xsi="http://www.w3.org/2000/10/XMLSchema-instance"
    xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc"
    xsi:schemaLocation="
http://java.sun.com/xml/ns/jaxb http://java.sun.com/xml/ns/jaxb/bindingschema_2_0.xsd"
    version="2.1">
    <globalBindings>
        <xjc:simple />
    </globalBindings>
</bindings>

XJC Call

xjc -extension -b binding.xml schema.xsd
bdoughan
  • 147,609
  • 23
  • 300
  • 400
  • 1
    This works! Where did you find it? I have not find any mention about in "Customizing JAXB Bindings" tutorial. – Mikhail Apr 24 '13 at 12:55
  • @Noofiz - You can find information about it on http://jaxb.java.net. I would provide the specific link, but I think java.net is currently down for maintenance. – bdoughan Apr 24 '13 at 14:03