36

我有一个使用默认命名空间打印的文件。元素以 ns2 前缀打印,我需要将其删除,我的代码如何:

<ns2:foo xmlns:ns2="http://namespace" />

我希望它是怎样的:

<foo xmlns="http://namespace" />

这就是我编写它的方式,我认为这应该足以让 ns2 消失:

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"
    xmlns:bar="http://namespace" targetNamespace="http://namespace"
    elementFormDefault="qualified">
...

生成的包信息是这样的:

@javax.xml.bind.annotation.XmlSchema(namespace = "http://namespace", 
    elementFormDefault = javax.xml.bind.annotation.XmlNsForm.QUALIFIED)
package com.foo.bar;

我创建这样的文件:

JAXBContext jaxbContext = JAXBContext.newInstance(generatedClassesPackage);
Marshaller marshaller = jaxbContext.createMarshaller();
marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
marshaller.marshal(new JAXBElement<Foo>(new QName("http://namespace", "Foo"),
Foo.class, rootFoo), outputStream);

generateClassesPackage 是 package-info.java 和元素所在的包。

Foo 对象已定义并具有如下元素:

@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "", propOrder = {
    "group"
})
@XmlRootElement(name = "Foo")
public class Foo {

    @XmlElement(name = "Group", required = true)
    protected List<Group> group;

我错过了什么吗?还是我误解了这是如何工作的?

4

7 回答 7

33

所有你需要做的2是当你打开一个新包时选择在包信息中创建包信息添加以下注释或根据需要更改它

@javax.xml.bind.annotation.XmlSchema(namespace = "http://www.sitemaps.org/schemas/sitemap/0.9", elementFormDefault = javax.xml.bind.annotation.XmlNsForm.QUALIFIED, xmlns = { @javax.xml.bind.annotation.XmlNs(namespaceURI = "http://www.sitemaps.org/schemas/sitemap/0.9", prefix = "") })

这将删除 ns2 前缀

于 2015-01-11T08:35:37.323 回答
11

您很可能在响应中有多个命名空间。这将使用创建 ns# 命名空间前缀的默认约定,其中一个成为没有前缀的 xmlns。如果您想控制它,您可以执行以下操作:

NamespacePrefixMapper mapper = new NamespacePrefixMapper() {
        public String getPreferredPrefix(String namespaceUri, String suggestion, boolean requirePrefix) {
            if ("http://namespace".equals(namespaceUri) && !requirePrefix)
                return "";
            return "ns";
        }
    };
    marshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", mapper);
    marshaller.mashal....

这将http://namespace始终将 设置为默认 xmlns,并在编组时将 ns# 用于所有其他命名空间。如果你愿意,你也可以给他们更多的描述性前缀。

于 2013-05-16T14:47:21.543 回答
7

从 JDK6u18 开始,不再使用 NamespacePrefixMapper 技术。

于 2014-08-07T02:39:28.967 回答
5

我解决了这个问题,将文件 package-info.java 删除到 jaxb 类包中并重新编译应用程序。

于 2015-04-16T15:10:41.623 回答
1

更改 elementFormDefault="unqualified" 中的属性值

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:bar="http://namespace" targetNamespace="http://namespace" elementFormDefault="qualified">
于 2020-02-19T11:08:58.710 回答
0

对于 Java 8:

我将前缀名称从“ ns2 ”更改为“故障”。

首先,创建您的 *DefaultNamespacePrefixMapper *。

import com.sun.xml.bind.marshaller.NamespacePrefixMapper;
import java.util.HashMap;
import java.util.Map;

public class DefaultNamespacePrefixMapper extends NamespacePrefixMapper {

    private static final String FAULT_PREFIX = "fault";

    private Map<String, String> namespaceMap = new HashMap<>();

    public DefaultNamespacePrefixMapper() {
        this.namespaceMap.put(NAMESPACE, FAULT_PREFIX);
    }

    @Override
    public String getPreferredPrefix(String namespaceUri, String suggestion, boolean requirePrefix) {
        return namespaceMap.getOrDefault(namespaceUri, suggestion);
    }
}

其次,将您的DefaultNamespacePrefixMapper添加到 Marshaller 属性。

@SuppressWarnings("unchecked")
private <T> void returnFault(T fault, SoapFault soapFault) {
    try {
        JAXBContext jaxbContext = JAXBContext.newInstance(fault.getClass());
        QName name = new QName(NAMESPACE, fault.getClass().getSimpleName());
        JAXBElement<T> element = new JAXBElement<>(name, (Class<T>) fault.getClass(), fault);

        Marshaller marshaller = jaxbContext.createMarshaller();
        marshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", new DefaultNamespacePrefixMapper());
        marshaller.marshal(element, soapFault.addFaultDetail().getResult());
    } catch (JAXBException e) {
        log.error("Exception when marshalling SOAP fault.", e);
    }
}

第三,在 gradle/maven 中添加以下依赖项。

compile 'com.sun.xml.bind:jaxb-impl:2.2.11'
compile 'com.sun.xml.bind:jaxb-core:2.2.11'
于 2018-08-30T11:27:48.510 回答
0

从 @XmlRootElement 中删除命名空间

前:XmlRootElement(name = "XXX", namespace = "abc.xsd")

后:@XmlRootElement(name = "XXX")

于 2021-02-05T17:56:39.310 回答