Elements annotated with @XmlElementRef not showing up in JAXB Marshalled Strings?

Viewed 194

The Background

I am working with an application that uses data structures that we have retrieved and generated using jaxws-maven-plugin to communicate with an external application. We are able to receive the XML documents and unmarshall them into java objects using JAXB and the class structures they have provided us. However, when we re-marshall these objects into Strings to persist in the database for future debugging, we lose information.

A snippet of the objects we use to convert:

/*the "root" object*/
//XML tags indicating field access, name, and prop order
public class PersonAppResObj {
    @XmlElement(name = "ApplicationObj", required = true)
    protected ApplicationObj application;
    @XmlElement(name = "ContactInfo", required = true)
    protected List<ContactInfo> contactInfo;
    ...
}
//XML tags indicating field access, name, and prop order
public class ApplicationObj extends other.pkg.ApplicationObj {
    @XmlElement(name = "PrimaryApplicant")
    protected List<XObj> primaryApplicant;
    ...
}
package other.pkg
//XML tags indicating field access, name, and prop order
public class ApplicationObj extends GenericApp {
    @XmlElementRef(name="Applicant", namespace="http://pkg.com/1/pkgs", type=JAXBElement.class, required=false)
    protected List<JAXBElement<? extends Applicant>> applicant;
    @XmlElement(name = "ApplicationPrimaryContact", required = true)
    protected XObj applicationPrimaryContact;
    ...
}

The following snippets are a simple Kotlin object that converts between the JAXB elements and the Strings, and a test for that object:

object Converter {
    fun xmlToXObj(respString: String): XObj? {
        val jaxbContext = JAXBContext.newInstance(ResponseRoot().javaClass)
        val unmarshaller = jaxbContext.createUnmarshaller()
        unmarshaller.setEventHandler {
            println(it.message)
            true
        }
        return (unmarshaller.unmarshal(ByteArrayInputStream(respString.toByteArray())) as ResponseRoot).xObj
    }
    fun xobjToXML(resp: XObj): String {
        val responseRoot = ResponseRoot(); responseRoot.xobj = resp
        val resMarsh = JAXBContext.newInstance(responseRoot.javaClass).createMarshaller()
        val resStream = ByteArrayOutputStream()
        resMarsh.marshal(responseRoot, resStream)
        return String(resStream.toByteArray())
    }
}
//autowired var feClient fetches info from other application
    @Test
    fun readWrite() {
        val rawResponse = feClient.fetchApp("AA", "1A")
        val xmlString = Converter.xobjToXML(rawResponse)
        val parsedResponse = Converter.xmlToXObj(xmlString)
        val parsedTwiceXML = Converter.xobjToXML(parsedResponse!!)
        println(xmlString)
        println(parsedTwiceXML)
    }

now, to the real bulk of the issue: When I run the readWrite test, I lose the Applicant information from the other.pkg.ApplicationObj:

//println(xmlString)
<ns4:PersonAppResObj>
            <ns4:ApplicationObj>
                <ns4:Applicant ns1:id="Applicant1">
                ...
                <ns3:PrimaryContact ns1:ref="primaryContact"/>

//println(parsedTwiceXML)
<ns4:PersonAppResObj>
            <ns4:ApplicationObj>
                <ns3:PrimaryContact ns1:ref="primaryContact"/>
                //no applicant to be found

The error that comes up in console is unexpected element (uri:"...", local:"Applicant"). Expected elements are <{...}PrimaryFilerPerson>,<{...}JointFilerPerson>,<{...}ApplicationPrimaryContact>,<{...}ApplicationMultipleIndicator>,<{...}Applicant>

The Main Issue

There were two similar errors that came up in the console, and those elements were missing as well. When I looked at those objects in the generated class files, all 3 elements that didn't show up were annotated with @XmlElementRef.

Firstly, what could be causing this issue? Is it just a case of the marshaller not finding the referenced objects?

Second, is there a way to fix this issue without editing the generated objects at all? If not, what can I do without changing how the xml will look?

0 Answers
Related