2
votes

I'm using JAXB/MOXy to unmarshall an XML file containing around 50 Objects of this class :

@XmlRootElement(name="Message")
public class MyClass{

private String name="";


private String messageComment;


private String messageType;


private Vector<Param> params = new Vector<Param>();

private String subtype;

public UcipMessageUnmarshaller(){}

public String getName() {
    return name;
}

@XmlElement
public void setName(String name) {
    this.name = name;
}

public Vector<Param> getParams() {
    return params;
}

@XmlElementWrapper(name="params")
@XmlElement (name="param")
public void setParams(Vector<Param> params) {
    this.params = params;
}

public static Param getParam(String name, Boolean mandatory){
    return new Param(name, mandatory);
}

public void setComment(String comment) {
    this.messageComment = comment;
}


@XmlAttribute(name="comment")
public void setMessageComment(String messageComment) {
    this.messageComment = messageComment;
}

@XmlAttribute(name="type")
public void setMessageType(String messageType) {
    this.messageType = messageType;
}


@XmlAttribute(name="comment")
public String getMessageComment() {
    return messageComment;
}

public String getMessageType() {
    return messageType;
}

public String getSubtype() {
    return subtype;
}

@XmlElement
public void setSubtype(String subtype) {
    this.subtype = subtype;
}
    }

but I'm encountering a weird problem : some of my Objects are having a very strange "name", for example one of them is getting : y></pstRefillAccountAfterFlag others are having a part of their name mixed with a part of the name of another object.

here is an example of my XML file :

<Message>
    <name>MessageName</name>
    <params>
        <param>
            <name>Param1Name</name>
            <mandatory>true</mandatory>
        </param>
        <param>
            <name>Param2Name</name>
            <mandatory>true</mandatory>
        </param>
        <param>
            <name>Param3Name</name>
            <mandatory>true</mandatory>
        </param>
        <param>
            <name>Param4Name</name>
            <mandatory>true</mandatory>
        </param>
        <param>
            <name>Param4Name</name>
            <mandatory>false</mandatory>
        </param>
        <param>
            <name>Param5Name</name>
            <mandatory>true</mandatory>
        </param>
        <param>
            <name>Param6Name</name>
            <mandatory>false</mandatory>
        </param>
    </params>
</Message>

it's the <name> value that's coming erroneous.

what could possibly be the reason ?

PS: the result will differ (but always wrong) if I change my file between linearized and pretty-printed XML.

BR

1
Could you provide some additional information: Which version of EclipseLink are you using? What input type are you unmarshalling from? Are you aware if there are any non-default SAX or StAX parsers on the classpath?bdoughan
Hi Blaise, I'm using EclipseLink 2.4.1 not sure what you mean the input type, I'll edit the original question and add an xml example. apart from eclipselink, nothing related to XML is in my classpath.Rima
Does your example XML return the wrong name? If so, what name does it return?Samuel Edwin Ward
@Rima - Unmarshalling from InputStream, File, etcbdoughan
@BlaiseDoughan here is a link of an eclipse project that reproduces the error, setup a break point at line 72 in AIRIP.java, run the debug, and have a look at a -> messages -> elementData[26] -> params -> elementData[15] -> name for an example of this error. edit: you'll have to add the eclipselink jar to your porject linkRima

1 Answers

1
votes

Note: I'm the EclipseLink JAXB (MOXy) lead and a member of the JAXB (JSR-222) expert group.

@BlaiseDoughan here is a link of an eclipse project that reproduces the error, setup a break point at line 72 in AIRIP.java, run the debug, and have a look at a -> messages -> elementData[26] -> params -> elementData[15] -> name for an example of this error. edit: you'll have to add the eclipselink jar to your porject link

Based on the project you linked to (thank you for providing that). If you remove MOXy from the picture you see interesting results:

SAXDemo

Currently when you unmarshal from a File MOXy will process the XML input using a SAX parser. Below I've created a simple application that uses a SAX parser to process the XML document you provided and output the contents of all the character events that contain the String "<".

import javax.xml.parsers.*;
import org.xml.sax.*;
import org.xml.sax.helpers.DefaultHandler;

public class SAXDemo {

    public static void main(String[] args) throws Exception {
        SAXParserFactory spf = SAXParserFactory.newInstance();
        spf.setNamespaceAware(true);
        SAXParser sp = spf.newSAXParser();
        XMLReader xr = sp.getXMLReader();
        xr.setContentHandler(new DefaultHandler() {

            @Override
            public void characters(char[] ch, int start, int length)
                    throws SAXException {
                String string = new String(ch, start, length);
                if(string.contains("<")) {
                    System.out.println(string);
                }
            }}
       );

       xr.parse("ressources/messages001.xml");
    }

}

Output

Below is the output from running the demo code. Most of the lines correspond to content id CDATA sections so they're expected, but the line /param><param><name>subscrlag is not. This means that reason MOXy is unmarshalling the wrong value is that the underlying SAX parser is reporting the wrong characters event.

<node relation=\"XOR\"><name>adjustmentAmountRelative</name><name>mainAccountValueNew</name></node><node relation=\"AND\" comment=\"in case the request is an update of already assigned community\"><name>communityInformationCurrent</name><name>communityInformationNew</name></node>
<node relation=\"AND\"><name>promotionPlanID</name><name>promotionStartDate</name><name>promotionEndDate</name></node>
/param><param><name>subscrlag
<node relation=\"XOR\"><name>adjustmentAmountRelative</name><name>mainAccountValueNew</name></node><node relation=\"XOR\"><name>supervisionExpiryDateRelative</name><name>supervisionExpiryDate</name></node><node relation=\"XOR\"><name>serviceFeeExpiryDateRelative</name><name>serviceFeeExpiryDate</name></node>
<node relation=\"OR\"><name>msisdnCurrent</name><name>msisdnCurrentNAI</name><name>msisdnNew</name><name>msisdnNewNAI</name><name>imsiCurrent</name><name>imsiNew</name><name>naiCurrent</name><name>naiNew</name><name>sipUriCurrent</name><name>sipUriNew</name><name>privateCurrent</name><name>privateNew</name></node><node relation=\"XOR\"><name>chargingInformation</name><name>externalContract</name></node>
<node relation=\"AND\" comment=\"in case the request is an update of already assigned community\"><name>communityInformationCurrent</name><name>communityInformationNew</name></node>
<node relation=\"XOR\"><name>fafInformation</name><name>fafInformationList</name></node><node relation=\"AND\"><name>selectedOption</name><name>chargingRequestInformation</name></node>
<node relation=\"XOR\"><node relation=\"\"><name>updateAction</name><name>productID</name></node><node relation=\"\"><node relation=\"XOR\"><node relation=\"OR\"><node relation=\"XOR\"><name>startDate</name><name>startDateRelative</name><node relation=\"\" comment=\"Optional\"><name>startPamPeriodIndicator</name><name>currentTimeOffset</name></node></node><node relation=\"XOR\"><name>expiryDate</name><name>expiryDateRelative</name><name>expiryPamPeriodIndicator</name></node></node><node relation=\"OR\"><node relation=\"XOR\"><name>startDateTime</name><name>startDateTimeRelative</name></node><node relation=\"XOR\"><name>expiryDateTime</name><name>expiryDateTimeRelative</name></node></node></node><name>pamServiceID</name><name>offerType</name><name>offerProviderID</name><name>dedicatedAccountUpdateInformation</name><name>attributeUpdateInformationList</name></node></node>
<node relation=\"OR\"><name>promotionRefillAmountRelative</name><name>promotionRefillCounterStepRelative</name><name>progressionRefillAmountRelative</name><name>progressionRefillCounterStepRelative</name></node>
<node relation=\"OR\"><name>accountGroupID</name><name>serviceOfferings</name></node>
<node relation=\"OR\"><name>usageCounterUpdateInformation</name><name>usageThresholdUpdateInformation</name></node>

ISSUE - XML Version 1.1

Your XML document contains the following header with the version set to 1.1. If you change the version to be 1.0 everything seems to work properly. The default SAX parser implementation in the JDK appears to fail when the version is set to 1.1.

<?xml version="1.1" encoding="utf-8"?>

SOLUTION - Use Another SAX Parser

The good thing about using a standard parser API such as SAX is that you can always swap in a new parser. I ran your example adding Xerces2 Java Parser 2.11.0 Release to the classpath, and the example ran as expected.