Форматирование StAX XML в Java

Можно ли использовать StAX (в частности, woodstox) для форматирования выходного xml с символами новой строки и вкладками, то есть в форме:

<element1>
  <element2>
   someData
  </element2>
</element1>

вместо:

<element1><element2>someData</element2></element1>

Если это невозможно в woodstox, есть ли другие облегченные библиотеки, которые могут это сделать?

Ответ 1

Через JDK: transformer.setOutputProperty(OutputKeys.INDENT, "yes");.

Ответ 2

Существует com.sun.xml.txw2.output.IndentingXMLStreamWriter

XMLOutputFactory xmlof = XMLOutputFactory.newInstance();
XMLStreamWriter writer = new IndentingXMLStreamWriter(xmlof.createXMLStreamWriter(out));

Ответ 3

Если вы используете API-интерфейс курсора StAX, вы можете отступать от вывода, обернув XMLStreamWriter в отступы для отступов. Я пробовал это в своем собственном проекте, и он работал хорошо.

Ответ 4

Как насчет StaxMate:

http://www.cowtowncoder.com/blog/archives/2006/09/entry_21.html

Хорошо работает с Woodstox, быстро, с низкой памятью (без встроенной памяти) и отступы вроде:


SMOutputFactory sf = new SMOutputFactory(XMLOutputFactory.newInstance());
SMOutputDocument doc = sf.createOutputDocument(new FileOutputStream("output.xml"));
doc.setIndentation("\n ", 1, 2); // for unix linefeed, 2 spaces per level    
// write doc like:    
SMOutputElement root = doc.addElement("element1");    
root.addElement("element2").addCharacters("someData");    
doc.closeRoot(); // important, flushes, closes output

Ответ 5

Вместо того, чтобы полагаться на класс com.sun..., который может уйти (или переименовать класс com.oracle...), я рекомендую загрузить Утилиты StAX от java.net. Этот пакет содержит класс IndentingXMLStreamWriter, который отлично работает. (Источник и javadoc включены в загрузку.)

Ответ 6

Использование JDK Transformer:

public String transform(String xml) throws XMLStreamException, TransformerException
{
    Transformer t = TransformerFactory.newInstance().newTransformer();
    t.setOutputProperty(OutputKeys.INDENT, "yes");
    t.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "2");
    Writer out = new StringWriter();
    t.transform(new StreamSource(new StringReader(xml)), new StreamResult(out));
    return out.toString();
}

Ответ 7

Если вы используете метод итерации (XMLEventReader), не можете ли вы просто прикрепить новый символ "\n" к соответствующим XMLEvents при записи в ваш XML файл?

Ответ 9

С Spring Batch для этого требуется подкласс, так как это JIRA BATCH-1867

public class IndentingStaxEventItemWriter<T> extends StaxEventItemWriter<T> {

  @Setter
  @Getter
  private boolean indenting = true;

  @Override
  protected XMLEventWriter createXmlEventWriter( XMLOutputFactory outputFactory, Writer writer) throws XMLStreamException {
    if ( isIndenting() ) {
      return new IndentingXMLEventWriter( super.createXmlEventWriter( outputFactory, writer ) );
    }
    else {
      return super.createXmlEventWriter( outputFactory, writer );
    }
  }

}

Но для этого требуется дополнительная зависимость, потому что Spring Batch не включает код для отступов вывода StAX:

<dependency>
  <groupId>net.java.dev.stax-utils</groupId>
  <artifactId>stax-utils</artifactId>
  <version>20070216</version>
</dependency>