/*
* Copyright 2011, 2012 Odysseus Software GmbH
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.synapse.commons.staxon.core.xml;
import java.io.IOException;
import java.io.Writer;
import javax.xml.XMLConstants;
import javax.xml.stream.XMLStreamConstants;
import javax.xml.stream.XMLStreamException;
import org.apache.synapse.commons.staxon.core.base.AbstractXMLStreamWriter;
/**
* Simple XML Stream Writer.
* <p/>
* The scope info is the element tag name.
*/
public class SimpleXMLStreamWriter extends AbstractXMLStreamWriter<String> {
private final Writer writer;
public SimpleXMLStreamWriter(Writer writer, boolean repairNamespaces) {
super(null, repairNamespaces);
this.writer = writer;
}
private void writeEscaped(String string, boolean attribute) throws IOException {
for (int i = 0; i < string.length(); i++) {
char c = string.charAt(i);
switch (c) {
case '<':
writer.write("<");
break;
case '>':
writer.write(">");
break;
case '&':
writer.write("&");
break;
default:
if (c == '"' && attribute) {
writer.write(""");
} else {
writer.write(c);
}
}
}
}
private String getTagName(String prefix, String localName) {
return XMLConstants.DEFAULT_NS_PREFIX.equals(prefix) ? localName : prefix + ':' + localName;
}
@Override
public void flush() throws XMLStreamException {
try {
writer.flush();
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
@Override
protected String writeStartElementTag(String prefix, String localName, String namespaceURI) throws XMLStreamException {
if (getScope().isRoot() && getScope().getLastChild() != null) {
throw new XMLStreamException("Multiple roots within document");
}
String tagName = getTagName(prefix, localName);
try {
writer.write('<');
writer.write(tagName);
} catch (IOException e) {
throw new XMLStreamException(e);
}
return tagName;
}
@Override
protected void writeStartElementTagEnd() throws XMLStreamException {
try {
if (getScope().isEmptyElement()) {
writer.write('/');
}
writer.write('>');
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
@Override
protected void writeEndElementTag() throws XMLStreamException {
try {
writer.write('<');
writer.write('/');
writer.write(getScope().getInfo());
writer.write('>');
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
@Override
protected void writeAttr(String prefix, String localName, String namespaceURI, String value) throws XMLStreamException {
try {
writer.write(' ');
if (!XMLConstants.DEFAULT_NS_PREFIX.equals(prefix)) {
writer.write(prefix);
writer.write(':');
}
writer.write(localName);
writer.write('=');
writer.write('"');
writeEscaped(value, true);
writer.write('"');
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
@Override
protected void writeNsDecl(String prefix, String namespaceURI) throws XMLStreamException {
try {
writer.write(' ');
writer.write(XMLConstants.XMLNS_ATTRIBUTE);
if (!XMLConstants.DEFAULT_NS_PREFIX.equals(prefix)) {
writer.write(':');
writer.write(prefix);
}
writer.write('=');
writer.write('"');
writer.write(namespaceURI);
writer.write('"');
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
@Override
protected void writeData(Object data, int type) throws XMLStreamException {
try {
switch (type) {
case XMLStreamConstants.CHARACTERS:
writeEscaped(data.toString(), false);
break;
case XMLStreamConstants.CDATA:
writer.write("<![CDATA[");
writer.write(data.toString());
writer.write("]]>");
break;
case XMLStreamConstants.COMMENT:
writer.write("<!--");
writeEscaped(data.toString(), false);
writer.write("-->");
break;
case XMLStreamConstants.ENTITY_REFERENCE:
writer.write('&');
writer.write(data.toString());
writer.write(';');
break;
default:
throw new UnsupportedOperationException("Cannot write data of type " + type);
}
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
@Override
protected void writePI(String target, String data) throws XMLStreamException {
try {
writer.write("<?");
writer.write(target);
if (data != null) {
writer.write(' ');
writer.write(data);
}
writer.write("?>");
} catch (IOException e) {
throw new XMLStreamException(e);
}
}
}