0

This is an example xml object like what I get from my API call:

<?xml version="1.0" ?>
<sourceSets>
    <sourceSet>
        <sourceSetIdentifier>1055491</sourceSetIdentifier>
        <sourceSetData>...</sourceSetName>
    </sourceSet>
    <sourceSet>
        <sourceSetIdentifier>1055493</sourceSetIdentifier>
        <sourceSetData>...</sourceSetName>
    </sourceSet>
</sourceSets>

Here is SourceSets.java:

@XmlAccessorType(XmlAccessType.FIELD)
@XmlRootElement(name = "sourceSets")
public class SourceSets {
       @XmlElement(required = true)
       protected List<SourceSet> sourceSet;

       // getter, setter
}

SourceSet.java is also there and is tested working, no problem.

To read this in, I use:

inputXML = ... // as seen above

public static void main(String[] args) {

    InputStream ins = new ByteArrayInputStream(
        inputString.getBytes(StandardCharsets.UTF_8));

    SourceSets sourceSets = null;
    try {

        JAXBContext jc = JAXBContext
                .newInstance(SourceSets.class);
        Unmarshaller unmarshaller = jc.createUnmarshaller();
        sourceSets = (SourceSets) unmarshaller.unmarshal(is);
    } catch (PropertyException e) {
        e.printStackTrace();
    } catch (JAXBException e) {
        e.printStackTrace();
    }

    System.out.println("Length of source sets");
    System.out.println(sourceSets.getSourceSet().size());
}

And the resulting output is:

Length of source sets
2

The problem is that the xml actually comes with a namespace attached to the sourceSets object:

<sourceSets xmlns="http://source/url">

Now, if I try to run my script, I get an UnmarshallException:

javax.xml.bind.UnmarshalException: unexpected element (uri:"http://source/url", local:"sourceSets"). Expected elements are <{}sourceSet>,<{}sourceSets>,<{}subscription>
    at com.sun.xml.internal.bind.v2.runtime.unmarshaller.UnmarshallingContext.handleEvent(UnmarshallingContext.java:726)
    at com.sun.xml.internal.bind.v2.runtime.unmarshaller.Loader.reportError(Loader.java:247)
    at com.sun.xml.internal.bind.v2.runtime.unmarshaller.Loader.reportError(Loader.java:242)
    ...
    at com.package.testing.SourceManualTest.main(SourceManualTest.java:78)

So to SourceSets.java I add a namespace definition to the @XmlRootElement annotation, like

@XmlRootElement(namespace = "http://source/url", name = "sourceSets")

With this change, the UnmarshallException goes away and it runs again...but now it doesn't read in any SourceSet objects:

Length of source sets
0

How do I account for the namespace xml tag, but still parse the xml to POJO?

kingledion
  • 2,263
  • 3
  • 25
  • 39

1 Answers1

0

You have several alternatives:

  1. Define the namespace in a package-info.java file:
@XmlSchema(elementFormDefault = XmlNsForm.QUALIFIED,
        namespace = "http://your-namespace.org/")
package org.your_namespace;

import javax.xml.bind.annotation.XmlNsForm;
import javax.xml.bind.annotation.XmlSchema;
  1. Explicitly define the namespace in all XML element annotations:
@XmlRootElement(name = "sourceSets", namespace = "http://your-namespace.org/")
public class SourceSets {
    @XmlElement(required = true, namespace = "http://your-namespace.org/")
    protected List<SourceSet> sourceSet;
}

Related question: JAXB: Namespace annotation not inherited during unmarshalling - regression in JDK 1.8_102?

nandsito
  • 3,782
  • 2
  • 19
  • 26