Remove Ns2 as Default Namespace Prefix

Remove ns2 as default namespace prefix

Most likely you have multiple namespaces in the response. This will use the default convention of creating ns# namespace prefixes and one of them becomes the xmlns without a prefix. If you want to control this you can do the following:

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....

This will set the http://namespace as the default xmlns always and use ns# for all other namespaces when marshalling. You can also give them more descriptive prefixes if you want.

Remove ns2 prefix while JaxB marshalling an Element without @XmlRootElement annotation

First, you are creating the Foo element in the wrong namespace. Looking at your desired output, you also want the Foo element to be in the http://Foo/bar namespace. To fix this problem, specify that namespace URI when you create the QName, instead of passing an empty string as the first argument:

// Wrong
QName qName = new QName("", "Foo");

// Right
QName qName = new QName("http://Foo/bar", "Foo");

To get rid of the generated ns2 prefix for the namespace, you need to set the namespace prefix to an empty string. You probably have a package-info.java file with an @XmlSchema annotation. It should look like this:

@XmlSchema(namespace = "http://Foo/bar",
elementFormDefault = XmlNsForm.QUALIFIED,
xmlns = @XmlNs(prefix = "", namespaceURI = "http://Foo/bar"))
package com.mycompany.mypackage;

import javax.xml.bind.annotation.XmlNs;
import javax.xml.bind.annotation.XmlNsForm;
import javax.xml.bind.annotation.XmlSchema;

Note: Setting prefix = "" will cause JAXB to generate an xmlns attribute without a generated prefix name such as ns2 in your XML.

jaxb namespace gives unneeded ns2 prefix

The namespace prefix is needed, since you have elements like <subtag> without a namespace. Once you assign a namespace to them, the ns2 prefix will disappear and JAXB will use a default namespace as your required.

There is also a comment in NamespaceContextImpl#declareNsUri of JAXB RI that states:

// the default prefix is already taken.
// move that URI to another prefix, then assign "" to the default prefix.

Edit: If you cannot get rid of the unqualified elements, you can qualify them with the same namespace as the other elements. This is possible at least with JAXB RI and is equivalent to a <xsd:include> tag:

final Map<String, String> props = Collections.singletonMap(JAXBRIContext.DEFAULT_NAMESPACE_REMAP, "http://namespace");
final JAXBContext ctx = JAXBContext.newInstance(new Class[]{Create.class}, props);

How do I remove the ns2 prefixes from XML elements using JAXB 3 and a NamespacePrefixMapper?

I forgot to provide the namespace to the QName :

new QName("http://maven.apache.org/POM/4.0.0", "project")

And now the result looks good :

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<project xmlns="http://maven.apache.org/POM/4.0.0">
<modelVersion>4.0.0</modelVersion>
<dependencies>
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.11.0</version>
</dependency>
</dependencies>
</project>

There's no need for a prefix mapper, so the code can be simplified:

import org.apache.maven.pom.Dependency;
import org.apache.maven.pom.Model;
import org.apache.maven.pom.Model.Dependencies;

import javax.xml.namespace.QName;

import jakarta.xml.bind.JAXB;
import jakarta.xml.bind.JAXBElement;

public class Main {

public static void main(String[] args) {
Model model = new Model();
model.setModelVersion("4.0.0");
model.setDependencies(new Dependencies());
Dependency dependency = new Dependency();
dependency.setGroupId("commons-io");
dependency.setArtifactId("commons-io");
dependency.setVersion("2.11.0");
model.getDependencies().getDependency().add(dependency);
JAXBElement<Model> elem = new JAXBElement<>(new QName("http://maven.apache.org/POM/4.0.0", "project"), Model.class, model);
JAXB.marshal(elem, System.out);
}
}

JAXB Marshallingremove namespace prefix

yes replacing prefix as "empty" seems very tricky as you can see my question here. I did find the solution to do transformation using xslt after the XML generation as below. Hope it helps.

removenamespace.xslt

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output indent="yes"/>
<xsl:preserve-space elements="*"/>

<xsl:template match="@*|node()[not(self::*)]">
<xsl:copy />
</xsl:template>

<xsl:template match="*">
<xsl:element name="{local-name()}">
<xsl:apply-templates select="node()|@*" />
</xsl:element>
</xsl:template>

</xsl:stylesheet>

XSLT transformer

    File outputXML = new File(inputXML.getParentFile(), inputXML.getName() + "-ns.xml");

try{
TransformerFactory factory = TransformerFactory.newInstance();
Source xslt = new StreamSource(new File(REMOVE_NAMESPACE_XSL));
Transformer transformer = factory.newTransformer(xslt);

Source text = new StreamSource(inputXML);
transformer.transform(text, new StreamResult(outputXML));

}
catch(Exception e){
// something gone wrong. return original XML.
return inputXML;
}


Related Topics



Leave a reply



Submit