Issue with namespaces in XMLs in JAXB unmarshalling

醉酒当歌 提交于 2019-12-02 12:09:20

问题


I have an XML to unmarshall with JAXB. The code works fine if I remove all namespace attributes from the elements but I get a null object after unmarshalling if I keep the namespace attributes.

The XML is like this:

<Animal  xmlns="http://allmycats.com/serviceplatform/1.0/" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<Cat z:Id="i3" xmlns:z="http://schemas.microsoft.com/2003/10/Serialization/">
<name>kitty</name>
</Cat>
<Cat z:Id="i2" xmlns:z="http://schemas.microsoft.com/2003/10/Serialization/">
<name>kitty2</name>
</Cat>
</Animal>

My Animal bean is like this:

    @XmlRootElement(name = "Animal")
public class Animal{
    List<Cat> cats;

    @XmlElement(name = "Cat")
    public List<Cat> getCats() {
        return cats;
    }

    public void setCats(List<Cat>cats) {
        this.cats= cats;
    }
}

The Cats bean is like:

@XmlRootElement(name = "Cat")
public class Cat {
    private String zId;

    @XmlAttribute(name = "z:Id", namespace="http://schemas.microsoft.com/2003/10/Serialization/")
    public String getzId() {
        return zId;
    }
    public void setzId(String zId) {
        this.zId = zId;
    }

    private String name;
    @XmlElement(name = "name")
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
}

At runtime, I get an empty object. I tried to remove "z:" from the attribute and I got this exception:

org.xml.sax.SAXParseException; The prefix "z" for attribute "z:Id" associated with an element type "Cat" is not bound.]

If I remove namespaces from cat and Animal, I get this exception:

javax.xml.bind.UnmarshalException: unexpected element (uri:"http://allmycats.com/serviceplatform/1.0/", local:"Animal"). Expected elements are <{}Animal>

Final code to unmarshall is below. The last line gives a null pointer exception

File file = new File(filepath1);
System.out.println("file exists? : "+ file.exists()); // prints true

JAXBContext jaxbContext = JAXBContext.newInstance(Animal2.class);
Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller();
Animal2 animals = (Animal2)jaxbUnmarshaller.unmarshal( file );
System.out.println("--file size: "+animals.getCats().size());

I am not sure how to handle the namespaces and the z: attributes in my POJO classes. Any suggestions please ?

The code works fine if I do not have any namespace or any attribute with namespace in the XML but I cannot alter the XML.


回答1:


XMLAtribute has atribute namesape, so

@XmlAttribute(name = "Id", namespace="http://schemas.microsoft.com/2003/10/Serialization").

While judging by your xml, the cat is in the same namespace as the animal so

The following code works with JDK 7 (fixed the ns for animal and attribute name for zid).

@XmlRootElement(name = "Animal",namespace = "http://allmycats.com/serviceplatform/1.0/")
public class Animal2{
    List<Cat2> cats;

    @XmlElement(name = "Cat")
    public List<Cat2> getCats() {
        return cats;
    }

    public void setCats(List<Cat2>cats) {
        this.cats= cats;
    }
}
@XmlRootElement(name = "Cat")
public class Cat2 {
    private String zId;

    @XmlAttribute(name = "Id", namespace="http://schemas.microsoft.com/2003/10/Serialization/")
    public String getzId() {
        return zId;
    }
    public void setzId(String zId) {
        this.zId = zId;
    }

    private String name;

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


来源:https://stackoverflow.com/questions/28616895/issue-with-namespaces-in-xmls-in-jaxb-unmarshalling

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!