Java Transformer outputs < and > instead of <> - java

I am editing an XML file in Java with a Transformer by adding more nodes. The old XML code is unchanged but the new XML nodes have < and > instead of <> and are on the same line. How do I get <> instead of < and > and how do I get line breaks after the new nodes. I already read several similar threads but wasn't able to get the right formatting. Here is the relevant portion of the code:
// Read the XML file
DocumentBuilderFactory dbf= DocumentBuilderFactory.newInstance();
DocumentBuilder db = dbf.newDocumentBuilder();
Document doc=db.parse(xmlFile.getAbsoluteFile());
Element root = doc.getDocumentElement();
// create a new node
Element newNode = doc.createElement("Item");
// add it to the root node
root.appendChild(newNode);
// create a new attribute
Attr attribute = doc.createAttribute("Name");
// assign the attribute a value
attribute.setValue("Test...");
// add the attribute to the new node
newNode.setAttributeNode(attribute);
// transform the XML
Transformer transformer = TransformerFactory.newInstance().newTransformer();
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
transformer.setOutputProperty(OutputKeys.METHOD, "xml");
StreamResult result = new StreamResult(new FileWriter(xmlFile.getAbsoluteFile()));
DOMSource source = new DOMSource(doc);
transformer.transform(source, result);
Thanks

To replace the &gt and other tags you can use org.apache.commons.lang3:
StringEscapeUtils.unescapeXml(resp.toString());
After that you can use the following property of transformer for having line breaks in your xml:
transformer.setOutputProperty(OutputKeys.INDENT, "yes");

based on a question posted here:
public void writeToOutputStream(Document fDoc, OutputStream out) throws Exception {
fDoc.setXmlStandalone(true);
DOMSource docSource = new DOMSource(fDoc);
Transformer transformer = TransformerFactory.newInstance().newTransformer();
transformer.setOutputProperty(OutputKeys.METHOD, "xml");
transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
transformer.setOutputProperty(OutputKeys.INDENT, "no");
transformer.transform(docSource, new StreamResult(out));
}
produces:
<?xml version="1.0" encoding="UTF-8"?>
The differences I see:
fDoc.setXmlStandalone(true);
transformer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");

Try passing InputStream instead of Writer to StreamResult.
StreamResult result = new StreamResult(new FileInputStream(xmlFile.getAbsoluteFile()));
The Transformer documentation also suggests that.

Related

Java XML api removes whitespace before self closing tag

I've XML file which contains only one element
<Message>
<Location URI ="XXX:XXX:XXX" />
</Message>
I want to read and print same XML using Java, but after print it loses white space before />
<Message>
<Location URI ="XXX:XXX:XXX"/>
</Message>
I have tried different configuration of DocumentBuilderFactory and Transformer but the result is same.
Any Idea?
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document requestDocument = builder.parse(this.getClass().getResourceAsStream("/message-template.xml"));
TransformerFactory tf = TransformerFactory.newInstance();
Transformer transformer = tf.newTransformer();
transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");
DOMSource domSource = new DOMSource(requestDocument);
StringWriter writer = new StringWriter();
StreamResult result = new StreamResult(writer);
transformer.transform(domSource, result);
System.out.println(writer.toString());
Here :
DOMSource domSource = new DOMSource(requestDocument);
...
transformer.transform(domSource, result);
You transform a DOMSource into a StreamResult . A DOMSource is not not a textual representation of the XML file but a Document Object Model (DOM) tree.
So whitespaces that are not considered as relevant to represent the content of the tree are not kept in the DOMSource :
URI ="XXX:XXX:XXX" />
|-------> not preserved
Most of APIs to represent and manipulate XML work in this way.
If you need to keep not significant whitespace in your result, you should probably do yourself the parsing of the XML file.

Unable to add doctype tag to xml file using java

I seek your help, I have an automatically generated XML File that I need to validate against a DTD, so I have to modify the generated XML to add the doctype tag isn't added when I use the following code, I have consulted many threads but no positive result.
Here is the concerned part in my code:
InputStream inputStream= new FileInputStream(extractedFileURL);
Reader reader = new InputStreamReader(inputStream,"UTF-8");
InputSource is = new InputSource(reader);
is.setEncoding("UTF-8");
Document doc = docBuilder.parse(is);
///Add Doctype declaration to the extracted XML File
TransformerFactory transformerFactory = TransformerFactory.newInstance();
Transformer transformer = transformerFactory.newTransformer();
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "no");
transformer.setOutputProperty(OutputKeys.METHOD, "xml");
org.w3c.dom.DOMImplementation domImpl = doc.getImplementation();
DocumentType doctype = domImpl.createDocumentType("doctype",
"SYSTEM"
,
"registry\\ixb\\dtds\\extractor.dtd\\generatedDTD1.dtd");
//transformer.setOutputProperty(OutputKeys.DOCTYPE_PUBLIC, doctype.getPublicId());
transformer.setOutputProperty(OutputKeys.DOCTYPE_SYSTEM, doctype.getSystemId());
DOMSource source = new DOMSource(doc);
StreamResult result = new StreamResult(new File(extractedFileURL));
transformer.transform(source, result);

Get XML corresponding to node [duplicate]

Hi I want to convert XML node and its child into a string with its node names.
For example I get a node from XML document which is look like this:
<Name>
<Work>*86</Work>
<Home>*86</Home>
<Mobile>*80</Mobile>
<Work>0</Work>
</Name>
I want to convert whole node into string. With nodenames, not only text. Any help in this regards is greatly appreciated. Thanks.
you can use JDom XMLOutputter subject to the condition that your Element is an org.jdom.Element:
XMLOutputter outp = new XMLOutputter();
String s = outp.outputString(your_jdom_element);
You can use a transformer for that:
Transformer transformer = TransformerFactory.newInstance().newTransformer();
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
StreamResult result = new StreamResult(new StringWriter());
DOMSource source = new DOMSource(node);
transformer.transform(source, result);
String xmlString = result.getWriter().toString();
System.out.println(xmlString);

How to remove standalone attribute declaration in xml document?

Im am currently creating an xml using Java and then I transform it into a String. The xml declaration is as follows:
DocumentBuilderFactory dbfac = DocumentBuilderFactory.newInstance();
DocumentBuilder docBuilder = dbfac.newDocumentBuilder();
Document doc = docBuilder.newDocument();
doc.setXmlVersion("1.0");
For transforming the document into String, I include the following declaration:
TransformerFactory transfac = TransformerFactory.newInstance();
Transformer trans = transfac.newTransformer();
trans.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "no");
trans.setOutputProperty(OutputKeys.VERSION, "1.0");
trans.setOutputProperty(OutputKeys.ENCODING,"UTF-8");
trans.setOutputProperty(OutputKeys.INDENT, "yes");
And then I do the transformation:
StringWriter sw = new StringWriter();
StreamResult result = new StreamResult(sw);
DOMSource source = new DOMSource(doc);
trans.transform(source, result);
String xmlString = sw.toString();
The problem is that in the XML Declaration attributes, the standalone attribute is included and I don't want that, but I want the version and encoding attributes to appear:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
Is there any property where that could be specified?
From what I've read you can do this by calling the below method on Document before creating the DOMSource:
doc.setXmlStandalone(true); //before creating the DOMSource
If you set it false you cannot control it to appear or not. So setXmlStandalone(true) on Document. In transformer if you want an output use OutputKeys with whatever "yes" or "no" you need. If you setXmlStandalone(false) on Document your output will be always standalone="no" no matter what you set (if you set) in Transformer.
Read the thread in this forum

Indent XML made with Transformer [duplicate]

This question already has answers here:
Pretty-printing output from javax.xml.transform.Transformer with only standard java api (Indentation and Doctype positioning)
(4 answers)
Closed 5 years ago.
I am trying to create XML from Java and am having problems with indenting. In the following code you can see OutputKeys.INDENT set to yes...
//set up a transformer
TransformerFactory transfac = TransformerFactory.newInstance();
Transformer trans = transfac.newTransformer();
trans.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");
trans.setOutputProperty(OutputKeys.INDENT, "yes");
//create string from xml tree
StringWriter sw = new StringWriter();
StreamResult result = new StreamResult(sw);
DOMSource source = new DOMSource(doc);
trans.transform(source, result);
String xmlString = sw.toString();
//print xml
System.out.println(xmlString);
but it seems to have no affect, the output is:
<dataset id="1"><br>
<path></path><br>
<session id="1"><br>
<method><br>
<timestamp>a timestamp</timestamp><br>
<signiture><br>
<classPath></classPath><br>
<name>methodName</name><br>
<declarationType>String</declarationType><br>
<parameters><br>
<parameter>String</parameter><br>
<parameter>int</parameter><br>
</parameters><br>
</signiture><br>
<arguments><br>
<argument>SomeValue</argument><br>
<argument>AnotherValue</argument><br>
</arguments><br>
<return>ReturnValue</return><br>
</method><br>
</session><br>
</dataset><br>
Try to set indent-amount, AFAIK the default is 0.
trans.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4")
Document doc;
.....
TransformerFactory factory = TransformerFactory.newInstance();
Transformer transformer = factory.newTransformer();
transformer.setOutputProperty(OutputKeys.INDENT, "yes");
transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4");
transformer.transform(new DOMSource(doc), new StreamResult(new File("filename.xml")));
transformer.transform(new DOMSource(doc), new StreamResult(System.out));

Categories