8 Replies Latest reply: Nov 20, 2007 6:29 AM by 807603 RSS

    Generating XML with SAX includung namespaces declarations in JRE 5.0.12

    807603
      Hello I have this sample code, and the output it produces changed when I updated my JRE from 5.0.11 to 5.0.12:

      {color:#0000ff}*import*{color} javax.xml.transform.OutputKeys;
      {color:#0000ff}*import*{color} javax.xml.transform.Transformer;
      {color:#0000ff}*import*{color} javax.xml.transform.TransformerConfigurationException;
      {color:#0000ff}*import*{color} javax.xml.transform.TransformerFactoryConfigurationError;
      {color:#0000ff}*import*{color} javax.xml.transform.sax.SAXTransformerFactory;
      *{color:#0000ff}import{color}* javax.xml.transform.sax.TransformerHandler;
      *{color:#0000ff}import{color}* javax.xml.transform.stream.StreamResult;

      *{color:#0000ff}import{color}* org.xml.sax.SAXException;
      {color:#0000ff}*import*{color} org.xml.sax.helpers.AttributesImpl;

      {color:#0000ff}*public class*{color} XMLWriter {

      public static void writeXML() {color:#0000ff}*throws*{color} TransformerFactoryConfigurationError,
      TransformerConfigurationException, SAXException {

      SAXTransformerFactory tf = (SAXTransformerFactory) SAXTransformerFactory
      .newInstance();

      TransformerHandler hd = tf.newTransformerHandler();

      hd.setResult({color:#0000ff}*new*{color} StreamResult(System.out));

      Transformer t = hd.getTransformer();
      t.setOutputProperty(OutputKeys.ENCODING, {color:#ff0000}"UTF-8"{color});
      t.setOutputProperty(OutputKeys.METHOD, {color:#ff0000}"xml"{color});
      t.setOutputProperty(OutputKeys.INDENT, {color:#ff0000}"yes"{color});

      String qName = {color:#ff0000}"a:tag"{color};
      AttributesImpl atts = {color:#0000ff}*new*{color} AttributesImpl();
      atts.addAttribute({color:#0000ff}*null*{color}, {color:#0000ff}*null*{color}, {color:#ff0000}"xmlns:a"{color}, {color:#ff0000}"CDATA"{color},
      {color:#ff0000}"http://example.com/a"{color});

      hd.startDocument();

      hd.startElement({color:#0000ff}*null*{color}, {color:#0000ff}*null*{color}, qName, atts);
      hd.endElement({color:#0000ff}*null*{color}, {color:#0000ff}*null*{color}, qName);

      hd.endDocument();

      }

      {color:#0000ff}*public static void*{color} main(String[] args) {
      {color:#0000ff}*try*{color} {
      writeXML();
      } {color:#0000ff}*catch*{color} (Exception e) {
      e.printStackTrace();
      }
      }

      }

      Output:
      5.0.11:
      <?xml version="1.0" encoding="UTF-8"?><a:tag xmlns:a="http://example.com/a"/>
      5.0.12:
      <?xml version="1.0" encoding="UTF-8"?><a:tag/>
      What's going on?
      How to make SAX transofmer produce namespaces declarations in XML documents. Any ideas?

      Edited by: G.W. on Sep 18, 2007 9:18 AM
        • 2. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
          807603
          Here's the code with formatting:
          import javax.xml.transform.OutputKeys;
          import javax.xml.transform.Transformer;
          import javax.xml.transform.TransformerConfigurationException;
          import javax.xml.transform.TransformerFactoryConfigurationError;
          import javax.xml.transform.sax.SAXTransformerFactory;
          import javax.xml.transform.sax.TransformerHandler;
          import javax.xml.transform.stream.StreamResult;
          
          import org.xml.sax.SAXException;
          import org.xml.sax.helpers.AttributesImpl;
          
          public class XMLWriter {
          
               public static void writeXML() throws TransformerFactoryConfigurationError,
                         TransformerConfigurationException, SAXException {
          
                    SAXTransformerFactory tf = (SAXTransformerFactory) SAXTransformerFactory
                              .newInstance();
          
                    TransformerHandler hd = tf.newTransformerHandler();
          
                    hd.setResult(new StreamResult(System.out));
          
                    Transformer t = hd.getTransformer();
                    t.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
                    t.setOutputProperty(OutputKeys.METHOD, "xml");
                    t.setOutputProperty(OutputKeys.INDENT, "yes");
          
                    String qName = "a:tag";
                    AttributesImpl atts = new AttributesImpl();
                    atts.addAttribute(null, null, "xmlns:a", "CDATA",
                              "http://example.com/a");
          
                    hd.startDocument();
          
                    hd.startElement(null, null, qName, atts);
                    hd.endElement(null, null, qName);
          
                    hd.endDocument();
          
               }
          
               public static void main(String[] args) {
                    try {
                         writeXML();
                    } catch (Exception e) {
                         e.printStackTrace();
                    }
               }
          
          }
          • 3. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
            DrClap
            Read the documentation for the startElement() method again. Notice how you put null for the namespace-related components of the element name. Try putting the correct information in there.

            Looks like they fixed the bug wherein you could produce fake namespace declarations by using attributes that look like namespace declarations.
            • 4. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
              807603
              Hi, Dr Clap.

              I've read the documentation for
               startElement() 
              more that once. Here's a line from there:
              Note that the attribute list provided will contain only attributes with explicit values (specified or defaulted): #IMPLIED attributes will be omitted. The attribute list will contain attributes used for Namespace declarations (xmlns* attributes) only if the http://xml.org/sax/features/namespace-prefixes property is true (it is false by default, and support for a true value is optional).
              http://java.sun.com/webservices/docs/1.5/api/org/xml/sax/ContentHandler.html#startElement(java.lang.String,%20java.lang.String,%20java.lang.String,%20org.xml.sax.Attributes)
              And so I ask: where to set: http://xml.org/sax/features/namespace-prefixes?

              And a second thing - I want to produce the namespaces declaration only once for the whole document. If I provide information namespaces for each tag it will be in each tag. I don't need that as it'a a great redundancy of data..., and with 1k and more elements the document size will increase without any good reason...

              So any other ideas?

              Edited by: G.W. on Sep 24, 2007 7:56 AM
              • 5. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
                807603
                I'd really, really appreciate some help on this one...
                • 6. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
                  DrClap
                  G.W. wrote:
                  Hi, Dr Clap.

                  And so I ask: where to set: http://xml.org/sax/features/namespace-prefixes?
                  Well, you don't set it. It's the caller of SAX that sets it and the implementer that uses it. You're the implementer here so it's up to you to handle namespaces correctly according to your requirements. Right now you aren't doing that. Let me spell it out for you:
                  hd.startElement("http://example.com/a", "tag", "a:tag", atts);
                  And a second thing - I want to produce the namespaces declaration only once for the whole document. If I provide information namespaces for each tag it will be in each tag. I don't need that as it'a a great redundancy of data..., and with 1k and more elements the document size will increase without any good reason...
                  It's the transformer that takes care of that. Your duty as a SAX handler is to make sure that each of the elements is declared to be in the correct namespace, that's all. The transformer (if it is any good) will not output unnecessary namespace declarations.
                  So any other ideas?
                  I thought my ideas were perfectly good. I find it irritating to have them ignorantly thrown aside. But suit yourself.
                  • 7. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
                    807603
                    First of all - thanks for your replies. But still the problem araises. Maybe I wasn't clear enoug the last time, so I'll try again...
                    DrClap wrote:
                    G.W. wrote:
                    Hi, Dr Clap.

                    And so I ask: where to set: http://xml.org/sax/features/namespace-prefixes?
                    Well, you don't set it. It's the caller of SAX that sets it and the implementer that uses it. You're the implementer here so it's up to you to handle namespaces correctly according to your requirements. Right now you aren't doing that. Let me spell it out for you:
                    hd.startElement("http://example.com/a", "tag", "a:tag", atts);
                    I am the caller of the SAX. So I want to set it. In my code I use the default SAX implementation provided with the JRE, so the transformer class used is actually:

                    com.sun.org.apache.xalan.internal.xsltc.trax.TransformerHandlerImpl
                    And a second thing - I want to produce the namespaces declaration only once for the whole document. If I provide information namespaces for each tag it will be in each tag. I don't need that as it'a a great redundancy of data..., and with 1k and more elements the document size will increase without any good reason...
                    It's the transformer that takes care of that. Your duty as a SAX handler is to make sure that each of the elements is declared to be in the correct namespace, that's all. The transformer (if it is any good) will not output unnecessary namespace declarations.
                    But when I do this:
                    AttributesImpl atts = new AttributesImpl();
                              atts.addAttribute(null, null, "someAttr", "CDATA",
                                        "someValue");          
                    
                              hd.startDocument();
                    
                              hd.startElement("http://example.com/a", "tag", "a:tag", atts);
                              hd.startElement("http://example.com/a", "gat", "a:gat", null);
                              hd.startElement("http://example.com/b", "bbb", "b:bbb", null);
                              hd.endElement("http://example.com/b", "bbb", "b:bbb");
                              hd.startElement("http://example.com/b", "bbb", "b:bbb", null);
                              hd.endElement("http://example.com/b", "bbb", "b:bbb");
                              hd.endElement("http://example.com/aba", "gat", "a:gat");
                              hd.endElement("http://example.com/a", "tag", "a:tag");
                              
                              hd.endDocument();
                    the output is:
                    <?xml version="1.0" encoding="UTF-8"?>
                    <a:tag xmlns:a="http://example.com/a" someAttr="someValue">
                        <a:gat>
                            <b:bbb xmlns:b="http://example.com/b"/>
                            <b:bbb xmlns:b="http://example.com/b"/>
                        </a:gat>
                    </a:tag>
                    I still get the b namespace declaration for each <b:bbb> tag when I could have it placed in the <a:gat> tag making it visible to all it's children and that way reducing the size of the document itself...
                    So any other ideas?
                    I thought my ideas were perfectly good. I find it irritating to have them ignorantly thrown aside. But suit yourself.
                    So I really do not throw anything aside, I just politely ask for some advice.

                    Thanks in advance.
                    • 8. Re: Generating XML with SAX includung namespaces declarations in JRE 5.0.12
                      807603
                      I know that it was submitted some time ago but maybe now someone could give another advice on the problem.

                      Regards,