编组和解组使用moxy更改xml

时间:2013-05-15 08:10:31

标签: java xml moxy

我正在尝试创建this kind(xsd inside)个文档。一些例子是here。由于root-element和其他常量元素中的常量值,我使用eclipse生成了一个模板:

<?xml version="1.0" encoding="UTF-8"?>
<invoice:response xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:ds="http://www.w3.org/2000/09/xmldsig#" xmlns:xenc="http://www.w3.org/2001/04/xmlenc#" xmlns:invoice="http://www.forum-datenaustausch.ch/invoice" xmlns="http://www.forum-datenaustausch.ch/invoice" xsi:schemaLocation="http://www.forum-datenaustausch.ch/invoice generalInvoiceResponse_440.xsd" language="de">
  <invoice:processing>
    <invoice:transport from="" to="">
      <invoice:via sequence_id="0" via=""/>
    </invoice:transport>
  </invoice:processing>
  <invoice:payload response_timestamp="0">
    <invoice:invoice request_date="2001-12-31T12:00:00" request_id="" request_timestamp="0"/>
  </invoice:payload>
</invoice:response>

但简单的解组和编组改变了内容:

<?xml version="1.0" encoding="UTF-8"?>
<response xmlns="http://www.forum-datenaustausch.ch/invoice" xmlns:ns1="http://www.w3.org/2000/09/xmldsig#" xmlns:ns0="http://www.w3.org/2001/04/xmlenc#" language="de">
   <processing>
      <transport from="" to="">
         <via via="" sequence_id="0"/>
      </transport>
   </processing>
   <payload response_timestamp="0">
      <invoice request_timestamp="0" request_date="2001-12-31T12:00:00.0" request_id=""/>
   </payload>
</response>

由于某种原因,架构位置属性消失了。这可以在编组之前手动添加。第二个问题是,所有前缀都消失了。 我不知道是谁消耗了生成的xml(他们是否用手写代码解组?有没有验证?)。因此,我想要一个与给定示例最相似且有效的输出。 那么是否有一种方法可以保持现有元素和属性不变,并让moxy为每个元素添加名称空间前缀?

1 个答案:

答案 0 :(得分:2)

以下内容应该有所帮助。这个问题也在EclipseLink论坛上处理:


  

由于某种原因,架构位置属性消失了。

您可以在Marshaller上指定以下属性以输出架构位置:

marshaller.setProperty(Marshaller.JAXB_SCHEMA_LOCATION, "http://www.forum-datenaustausch.ch/invoice generalInvoiceResponse_440.xsd");

  

第二个问题是,所有前缀都消失了。

名称空间前缀消失了,但名称空间限定是相同的(所有元素都具有相同的本地名称和名称空间URI)。在第一个文档中,invoice前缀分配给http://www.forum-datenaustausch.ch/invoice名称空间,第二个文档中名称空间被分配为默认名称空间


在设计时控制NAMESPACE PREFIXES

您可以通过利用@XmlSchema注释来提供应使用的命名空间前缀的MOXy提示(请参阅:http://blog.bdoughan.com/2011/11/jaxb-and-namespace-prefixes.html)。

<强>包信息

@XmlSchema(
    elementFormDefault=XmlNsForm.QUALIFIED,
    namespace="http://www.forum-datenaustausch.ch/invoice",
    xmlns={
        @XmlNs(prefix="invoice", namespaceURI="http://www.forum-datenaustausch.ch/invoice"),
        @XmlNs(prefix="ds", namespaceURI="http://www.w3.org/2000/09/xmldsig#"),
        @XmlNs(prefix="xenc", namespaceURI="http://www.w3.org/2001/04/xmlenc#")
    }
)
package forum16559889;

import javax.xml.bind.annotation.*;

<强>响应

package forum16559889;

import javax.xml.bind.annotation.XmlRootElement;

@XmlRootElement
public class Response {
}

<强>演示

package forum16559889;

import javax.xml.bind.*;

public class Demo {

    public static void main(String[] args) throws Exception {
        JAXBContext jc = JAXBContext.newInstance(Response.class);

        Response response = new Response();

        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.setProperty(Marshaller.JAXB_SCHEMA_LOCATION, "http://www.forum-datenaustausch.ch/invoice generalInvoiceResponse_440.xsd");
        marshaller.marshal(response, System.out);
    }

}

<强>输出

<?xml version="1.0" encoding="UTF-8"?>
<invoice:response xsi:schemaLocation="http://www.forum-datenaustausch.ch/invoice generalInvoiceResponse_440.xsd" xmlns:xenc="http://www.w3.org/2001/04/xmlenc#" xmlns:invoice="http://www.forum-datenaustausch.ch/invoice" xmlns:ds="http://www.w3.org/2000/09/xmldsig#" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"/>

在RUNTIME中控制NAMESPACE PREFIXES

您可以利用MOXy的NamespacePrefixMapper扩展来控制运行时使用的名称空间前缀。

package forum16559889;

import javax.xml.bind.*;
import org.eclipse.persistence.jaxb.MarshallerProperties;
import org.eclipse.persistence.oxm.NamespacePrefixMapper;

public class Demo {

    public static void main(String[] args) throws Exception {
        JAXBContext jc = JAXBContext.newInstance(Response.class);

        Response response = new Response();

        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.setProperty(Marshaller.JAXB_SCHEMA_LOCATION, "http://www.forum-datenaustausch.ch/invoice generalInvoiceResponse_440.xsd");

        marshaller.setProperty(MarshallerProperties.NAMESPACE_PREFIX_MAPPER, new NamespacePrefixMapper() {

            @Override
            public String getPreferredPrefix(String namespaceUri,
                    String suggestion, boolean requirePrefix) {
                if("http://www.forum-datenaustausch.ch/invoice".equals(namespaceUri)) {
                    return "invoice";
                } else if("http://www.w3.org/2000/09/xmldsig#".equals(namespaceUri)) {
                    return "ds";
                } else if("http://www.w3.org/2001/04/xmlenc#".equals(namespaceUri)) {
                    return "xenc";
                } else {
                    return null;
                }
            }

        });

        marshaller.marshal(response, System.out);
    }

}