Details
-
Bug
-
Status: Open
-
Major
-
Resolution: Unresolved
-
None
-
None
-
PatchAvailable
Description
This isn't exacly a bug, but it is against the serialization "philosophy".
The serializer stage tries to write out a minimal set of namespace mappings. For example if <a> has child <b> and both elements have the namespace node that maps prefix "prex" to URI "uri-x" then it tries to serializer the document as:
<a xmlns:prex='uri-x'><b/></a>
rather than as:
<a xmlns:prex='uri-x'><b xmlns:prex='uri-x' /></a>
It isn't that the second form is wrong, it is just that due to the XML standard <b> inherits its parent namespace nodes or mappings. The problem with the second form is that things can get pretty messy when there are a number of namespace nodes and also a deep ancestor tree. Messy and potentially a preformance problem with large (lots of characters) output XML.
Here is a testcase showing this problem:
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.Transformer;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.dom.DOMSource;
import org.w3c.dom.Node;
import org.xml.sax.InputSource;
import java.io.*;
import java.util.Properties;
public class Test {
private static final String XML_SOURCE =
"<doc xmlns:foo='foo'>" +
"<a xmlns:foo='foo'/>" +
"</doc>";
public static void main(String[] args) throws Exception
{ DocumentBuilderFactory dfactory = DocumentBuilderFactory.newInstance(); dfactory.setNamespaceAware(true); DocumentBuilder docBuilder = dfactory.newDocumentBuilder(); Node xmlDOM = docBuilder.parse(new InputSource(new StringReader(XML_SOURCE))); String key = "javax.xml.transform.TransformerFactory"; String value = org.apache.xalan.processor.TransformerFactoryImpl.class.getName(); Properties props = System.getProperties(); props.put(key, value); System.setProperties(props); Transformer t = TransformerFactory.newInstance().newTransformer(); t.transform(new DOMSource(xmlDOM), new StreamResult(System.out)); }}
Expected result:
<?xml version="1.0" encoding="UTF-8"?><doc xmlns:foo="foo"><a/></doc>
Actual result:
<?xml version="1.0" encoding="UTF-8"?><doc xmlns:foo="foo"><a xmlns:foo="foo"/></doc>