Thanks Steven! Interesting ;-) Included below is my own twist on the technique you demonstated that allows to encapsulate the SAX/TrAX code. Clients just implement the XmlContentProvider, probably as an anonymous inner class at the same time as calling XmlWriter.write().
I noticed though that with JDK 1.4.2, even when requesting indenting, the resulting file is not indented :-( package com.lgc.buildmagic.util; import java.io.File; import java.io.Writer; import java.io.OutputStream; import java.io.IOException; // SAX classes import org.xml.sax.InputSource; import org.xml.sax.SAXException; import org.xml.sax.ContentHandler; import org.xml.sax.helpers.AttributesImpl; import org.xml.sax.helpers.XMLFilterImpl; // TrAX classes import javax.xml.transform.OutputKeys; import javax.xml.transform.Transformer; import javax.xml.transform.TransformerFactory; import javax.xml.transform.TransformerException; import javax.xml.transform.TransformerConfigurationException; import javax.xml.transform.sax.SAXSource; import javax.xml.transform.stream.StreamResult; public class XmlWriter { /** The mirror image of SAX's ContentHandler that writes to a handler. */ public interface XmlContentProvider { void writeTo(ContentHandler to) throws SAXException; } /** Just a dummy impl of the content provider interface above for testing. */ public static class MyProvider implements XmlContentProvider { public void writeTo(ContentHandler to) throws SAXException { final AttributesImpl attributes = new AttributesImpl(); to.startDocument(); to.startElement("", "history-cache", "history-cache", attributes); to.startElement("", "entries", "entries", attributes); to.startElement("", "name", "name", attributes); String name = "Javah&cache"; to.characters(name.toCharArray(), 0, name.length()); to.endElement("", "name", "name"); to.startElement("", "tag", "tag", attributes); String tag = "<tag>text</tag>"; to.characters(tag.toCharArray(), 0, tag.length()); to.endElement("", "tag", "tag"); to.endElement("", "entries", "entries"); to.endElement("", "history-cache", "history-cache"); to.endDocument(); } } public void write(File file, XmlContentProvider provider) throws TransformerException { write(new StreamResult(file), provider); } public void write(OutputStream outputStream, XmlContentProvider provider) throws TransformerException { write(new StreamResult(outputStream), provider); } public void write(Writer writer, XmlContentProvider provider) throws TransformerException { write(new StreamResult(writer), provider); } /** * Writes SAX events sent by an XML provider using an identity transform. * * @param result The stream to write the result of the identity transform to. * @param provider The XML content provider. */ private void write(StreamResult result, final XmlContentProvider provider) throws TransformerException { TransformerFactory factory = TransformerFactory.newInstance(); Transformer transformer = factory.newTransformer(); transformer.setOutputProperty(OutputKeys.INDENT, "yes"); XMLFilterImpl reader = new XMLFilterImpl() { public void parse(InputSource input) throws IOException, SAXException { provider.writeTo(getContentHandler()); } }; SAXSource source = new SAXSource(reader, new InputSource()); transformer.transform(source, result); } public static void main(String[] args) throws Exception { new XmlWriter().write(new File("XmlWriter.xml"), new MyProvider()); } } -----Original Message----- From: [EMAIL PROTECTED] To: Ant Developers List Sent: 12/18/2003 7:36 AM Subject: RE: Bug 25564 - CVS tagdiff does not escape XML characters Hi, I have attached a file to the bug report. http://issues.apache.org/bugzilla/show_bug.cgi?id=25564 Steve Dominique Devienne <[EMAIL PROTECTED]> 17/12/2003 11:14 Please respond to "Ant Developers List" To: "'Antoine Levy-Lambert '" <[EMAIL PROTECTED]>, "'Ant Developers List '" <[EMAIL PROTECTED]> cc: Subject: RE: Bug 25564 - CVS tagdiff does not escape XML characters From: <[EMAIL PROTECTED]> > My favoured way of generating XML from a class is to extend > XMLFilterImpl and fire SAX events to a Transformer with no > stylesheet and StreamResult of the required output file, > inspired by Cocoon 2. Would you care to provide a concrete example please? Thanks, --DD --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]