如何从使用JAXB生成的XML中删除默认的根元素名称空间前缀

时间:2012-10-21 02:47:36

标签: spring-mvc jaxb

我正在使用带有spring-mvc框架的JAXB来生成XML。这是根元素的示例:

<ns2:urlset xmlns:ns2="http://www.example.com">

但是,这就是我想要的(没有XML名称空间前缀ns2):

<urlset xmlns="http://www.example.com">

我尝试使用以下package-info.java删除默认前缀ns2

@javax.xml.bind.annotation.XmlSchema(  
    namespace = "http://www.example.com",   
    xmlns = {@javax.xml.bind.annotation.XmlNs(namespaceURI = "http://www.example.com", prefix="")},  
    elementFormDefault = javax.xml.bind.annotation.XmlNsForm.UNQUALIFIED)  
package com.example.code

如果我将ns2设置为另一个字符串,则前缀可以更改为其他值(而不是prefix)。但是,通过将prefix值设置为“”,无法删除前缀。它仍然显示默认值ns2。有没有办法删除默认前缀ns2

另一个问题是,如果XML标题中的standalone属性也可以删除吗?如果是,可以通过package-info.java吗?

完成
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>

3 个答案:

答案 0 :(得分:2)

试试这个:

package-info.java

    @XmlSchema(
    namespace="http://www.sitemaps.org/schemas/sitemap/0.9", 
    elementFormDefault=XmlNsForm.QUALIFIED)
package com.example.model;
import javax.xml.bind.annotation.XmlSchema;
import javax.xml.bind.annotation.XmlNsForm;

XmlUrlSet.java

@XmlAccessorType(value = XmlAccessType.NONE)
@XmlRootElement(name = "urlset", namespace = "http://www.sitemaps.org/schemas/sitemap/0.9")
public class XmlUrlSet {...}

答案 1 :(得分:0)

如果@alex's answer不起作用,您可能在JAXB的参考实现中发现了一个错误(至少,我认为它是一个错误)。我只是遇到了同样的问题 - 如果我将JaxbElement添加到我的模型类中,JAXB RI开始忽略我的默认命名空间。我找不到另一种解决方案而不是切换到Eclipse MOXy(没有任何其他修改)并且它有效。 (注意:在moxy中注意another bug

另外,对于第二个问题,请使用:

JAXBContext jc = JAXBContext.newInstance(...);
Marshaller m = jc.createMarshaler();
m.setProperty(Marshaller.JAXB_FRAGMENT, Boolean.TRUE);

答案 2 :(得分:0)

每个Java对象和其中的嵌套字段都将被编写为XML元素,并具有与其关联的命名空间。如果封送处理程序在要封送的对象树中检测到多个名称空间,它将添加适当的名称空间前缀以在封送处理的XML中消除歧义。

以下讨论适用于Java 1.6及更高版本。

Example 1


该类的实例

@XmlRootElement(name = "Message")
class Message {
  @XmlAttribute(name = "Version")
  public int getVersion() { return 1; }
}

将序列化为:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<Message Version="1"/>

因为XML消息具有单个元素(Message),并且具有默认名称空间("")。

Example 2


该类的实例

@XmlRootElement(name = "Message", namespace = "http://example.com/schema/message")
class Message {
  @XmlAttribute(name = "Version")
  public int getVersion() { return 1; }
}

(将自定义命名空间添加到@XmlRootElement中)将被序列化为:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<Message xmlns="http://example.com/schema/message" Version="1"/>

因为XML消息仍然只有一个元素(Message),尽管它具有自定义名称空间(http://example.com/schema/message),而不是默认名称空间。

Example 3


该类的实例

@XmlRootElement(name = "Message", namespace = "http://example.com/schema/message")
class Message {
  @XmlElement(name = "Version")
  public int getVersion() { return 1; }
}

({@XmlAttribute更改为@XmlElement)将被序列化为:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ns2:Message xmlns:ns2="http://example.com/schema/message">
    <Version>1</Version>
</ns2:Message>

因为XML消息现在具有两个元素(MessageVersion),并且具有不同的命名空间(分别为http://example.com/schema/message"")。因此,封送人员被迫通过它们自己的名称空间消除这两个元素的歧义。

Example 4

该类的实例

@XmlRootElement(name = "Message", namespace = "http://example.com/schema/message")
class Message {
  @XmlElement(name = "Version", namespace = "http://example.com/schema/message")
  public int getVersion() { return 1; }
}

(将自定义命名空间添加到@XmlElement中)将被序列化为:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ns2:Message xmlns:ns2="http://example.com/schema/message">
    <Version>1</Version>
</ns2:Message>

因为XML消息具有两个元素(MessageVersion),所以它们共享相同的名称空间(http://example.com/schema/message)。因此,在确定每个元素所属的名称空间时不再存在歧义,因此在结果XML中只有一个名称空间声明。

相关问题