1

When I use colon in the tag name like in the example below, it ends up in error (there is no problem with tags without the colon).

package test;

import java.io.StringReader;
import java.io.StringWriter;

import javax.xml.stream.XMLOutputFactory;
import javax.xml.stream.XMLStreamException;
import javax.xml.stream.XMLStreamWriter;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamSource;

public class SomeClass{

    public StringWriter test() throws XMLStreamException, TransformerConfigurationException, TransformerException {
        StringWriter stringOut = new StringWriter();
        XMLStreamWriter xmlWriter = XMLOutputFactory.newInstance().createXMLStreamWriter(stringOut);
        xmlWriter.writeStartDocument("UTF-8", "1.0");
        xmlWriter.writeStartElement("SomeWordHere");
        {
            xmlWriter.writeStartElement("SomeName:enable");//<--- notice the colon
            xmlWriter.writeCharacters("true");
            xmlWriter.writeEndElement();
        }
        xmlWriter.writeEndElement();
        xmlWriter.writeEndDocument();
        xmlWriter.flush();
        xmlWriter.close();

        Transformer transformer = TransformerFactory.newInstance().newTransformer();
        transformer.setOutputProperty(OutputKeys.STANDALONE, "no");
        transformer.setOutputProperty(OutputKeys.INDENT, "yes");
        transformer.setOutputProperty(OutputKeys.METHOD, "xml");
        transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4");

        StringWriter formattedStringWriter = new StringWriter();

        transformer.transform(new StreamSource(new StringReader(stringOut.toString())), new StreamResult(formattedStringWriter));

        return formattedStringWriter;
    }
}

How to write the tag that would still conain the colon and would not end up in error?

I am trying to emulate the XML output (Collada DAE) produced by LEGO Stud.io software, there are sections like the one below containing tag names with colons.

<library_materials>
    <material id="material_id_7" name="SOLID-BLUE">
        <instance_effect url="#effect_id_7-fx" />
        <extra>
            <technique profile="eyesight">
                <ScratchBump:enable> true </ScratchBump:enable>
                <MinScratchStrength:value> 0 </MinScratchStrength:value>
                <MaxScratchStrength:value> 0.2 </MaxScratchStrength:value>
                <BigScratch:enable> true </BigScratch:enable>
                <SmallScratch:enable> true </SmallScratch:enable>
            </technique>
        </extra>
    </material>
</library_materials>
Christopher Moore
  • 15,626
  • 10
  • 42
  • 52
qraqatit
  • 492
  • 4
  • 14
  • Is `SomeName` intended as a namespace here? If so, you need to write namespaces correctly, e.g. with `writeStartElement(String prefix, String localName, String namespaceURI)` (there might be better ways though). If not, then you can't do this, because a colon in the name is invalid. – Mark Rotteveel Mar 24 '22 at 17:03
  • Actually I was trying to do that already but always end up in error – qraqatit Mar 24 '22 at 17:05

1 Answers1

2

Colon is used for namespaces and per "Namespaces in XML" specification, it cannot be used in entity names.

The specification states:

[Definition: A document is namespace-well-formed if it conforms to this specification. ]

It follows that in a namespace-well-formed document:

  • All element and attribute names contain either zero or one colon;
  • No entity names, processing instruction targets, or notation names contain any colons.

You can use a trick that is to declare "SomeName" as a namespace as it is suggested in this question: xml schema validation error "prefix is not bound".

On the other hand, "Extensible Markup Language" Specification state that:

Note:

The Namespaces in XML Recommendation [XML Names] assigns a meaning to names containing colon characters. Therefore, authors should not use the colon in XML names except for namespace purposes, but XML processors must accept the colon as a name character.

If you change the parser you can get what you want:

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

public class CreateXmlFileDemo {

  public static void main(String[] args) {

    try {
      DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
      DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
      Document doc = dBuilder.newDocument();
      Element rootElement = doc.createElement("SomeName:enable");

      doc.appendChild(rootElement);

      TransformerFactory transformerFactory = TransformerFactory.newInstance();
      Transformer transformer = transformerFactory.newTransformer();
      DOMSource source = new DOMSource(doc);

      StreamResult consoleResult = new StreamResult(System.out);
      transformer.transform(source, consoleResult);
    } catch (Exception e) {
      e.printStackTrace();
    }
  }
}

Reference: https://www.w3.org/TR/REC-xml-names/

pringi
  • 3,987
  • 5
  • 35
  • 45
  • But it is used like that with Blenders Cycles clone renderer from LEGO software Stud.io called Eyesight. Its own xml files (actually Collada dae file) have it written that way...and everything works there. I am trying to write similiar XML output. Could you post a example according to my example code, please (I am talking about the trick)? – qraqatit Mar 24 '22 at 17:07
  • 1
    I found a parser that does what you want. See the updated answer. – pringi Mar 24 '22 at 17:18
  • 1
    yes, it seems working...gee, I will have to rewrite a lot of code now, haha. – qraqatit Mar 24 '22 at 17:28