package stax2.typed;
import java.io.*;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.util.Random;
import java.util.StringTokenizer;
import javax.xml.namespace.QName;
import javax.xml.stream.*;
import org.codehaus.stax2.*;
import org.codehaus.stax2.typed.*;
import stax2.BaseStax2Test;
/**
* Base class that contains set of simple unit tests to verify implementation
* of {@link TypedXMLStreamWriter}. Concrete sub-classes are used to
* test both native and wrapped Stax2 implementations.
*
* @author Tatu Saloranta
*/
public abstract class WriterTestBase
extends BaseStax2Test
{
final static int[] ARRAY_TEST_LENGTHS = new int[] {
3, 8, 25, 120, 16, 99, 253, 1099, 2866, 37242
};
/*
////////////////////////////////////////
// Tests for numeric/enum types
////////////////////////////////////////
*/
public void testSimpleBooleanElem()
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 w = getTypedWriter(bos);
writeBooleanElem(w, true);
byte[] data = closeWriter(w, bos);
checkBooleanElem(data, true);
w = getTypedWriter(bos);
writeBooleanElem(w, false);
data = closeWriter(w, bos);
checkBooleanElem(data, false);
}
public void testSimpleBooleanAttr()
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 w = getTypedWriter(bos);
writeBooleanAttr(w, true);
byte[] data = closeWriter(w, bos);
checkBooleanAttr(data, true);
w = getTypedWriter(bos);
writeBooleanAttr(w, false);
data = closeWriter(w, bos);
checkBooleanAttr(data, false);
}
public void testMultipleBooleanAttr()
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 w = getTypedWriter(bos);
w.writeStartDocument();
w.writeStartElement("root");
w.writeBooleanAttribute(null, null, "a1", true);
w.writeBooleanAttribute(null, null, "xyz", false);
w.writeBooleanAttribute(null, null, "_attr3", true);
w.writeEndElement();
w.writeEndDocument();
byte[] data = closeWriter(w, bos);
XMLStreamReader2 sr = getRootReader(data);
assertEquals(3, sr.getAttributeCount());
int ix1 = sr.getAttributeIndex("", "a1");
int ix2 = sr.getAttributeIndex("", "xyz");
int ix3 = sr.getAttributeIndex("", "_attr3");
if (ix1 < 0 || ix2 < 0 || ix3 < 0) {
fail("Couldn't find indexes of attributes: a1="+ix1+", xyz="+ix2+", _attr3="+ix3);
}
assertTrue(sr.getAttributeAsBoolean(ix1));
assertFalse(sr.getAttributeAsBoolean(ix2));
assertTrue(sr.getAttributeAsBoolean(ix3));
sr.close();
}
public void testSimpleIntElem()
throws XMLStreamException
{
int[] values = new int[] {
0, 3, -9, 999, -77, 1000000000, -1000000000,
Integer.MIN_VALUE, Integer.MAX_VALUE
};
for (int i = 0; i < values.length; ++i) {
int value = values[i];
assertXML("<root>"+value+"</root>", writeIntElemDoc("root", value));
}
}
public void testSimpleIntAttr()
throws XMLStreamException
{
int[] values = new int[] {
0, 3, -7, 123, -102, 1000000, -999999,
Integer.MIN_VALUE, Integer.MAX_VALUE
};
for (int i = 0; i < values.length; ++i) {
int value = values[i];
assertXML("<a attr='"+value+"'></a>", writeIntAttrDoc("a", "attr", value));
}
}
public void testMultipleIntAttr()
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 w = getTypedWriter(bos);
w.writeStartDocument();
w.writeStartElement("root");
w.writeIntAttribute(null, null, "a", 0);
w.writeIntAttribute(null, null, "bz", Integer.MAX_VALUE);
w.writeIntAttribute(null, null, "___", -1200300400);
w.writeEndElement();
w.writeEndDocument();
byte[] data = closeWriter(w, bos);
XMLStreamReader2 sr = getRootReader(data);
assertEquals(3, sr.getAttributeCount());
int ix1 = sr.getAttributeIndex("", "a");
int ix2 = sr.getAttributeIndex("", "bz");
int ix3 = sr.getAttributeIndex("", "___");
if (ix1 < 0 || ix2 < 0 || ix3 < 0) {
fail("Couldn't find indexes of attributes: a="+ix1+", bz="+ix2+", ___="+ix3);
}
assertEquals(0, sr.getAttributeAsInt(ix1));
assertEquals(Integer.MAX_VALUE, sr.getAttributeAsInt(ix2));
assertEquals(-1200300400, sr.getAttributeAsInt(ix3));
sr.close();
}
public void testSimpleLongElem()
throws XMLStreamException
{
long[] values = new long[] {
0, 3, -9, 999, -77, 1000000000, -1000000000,
123456789012345678L,
-987654321098765423L,
Long.MIN_VALUE, Long.MAX_VALUE
};
for (int i = 0; i < values.length; ++i) {
long value = values[i];
assertXML("<root>"+value+"</root>", writeLongElemDoc("root", value));
}
}
public void testSimpleLongAttr()
throws XMLStreamException
{
long[] values = new long[] {
0, 3, -9, 999, -77, 1000000002, -2000000004,
123456789012345678L,
-987654321098765423L,
Long.MIN_VALUE, Long.MAX_VALUE
};
for (int i = 0; i < values.length; ++i) {
long value = values[i];
assertXML("<a attr='"+value+"'></a>", writeLongAttrDoc("a", "attr", value));
}
}
public void testMultipleLongAttr()
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 w = getTypedWriter(bos);
w.writeStartDocument();
w.writeStartElement("root");
w.writeLongAttribute(null, null, "a", 0L);
w.writeLongAttribute(null, null, "bz", Long.MAX_VALUE);
w.writeLongAttribute(null, null, "___", -1200300400L);
w.writeEndElement();
w.writeEndDocument();
byte[] data = closeWriter(w, bos);
XMLStreamReader2 sr = getRootReader(data);
assertEquals(3, sr.getAttributeCount());
int ix1 = sr.getAttributeIndex("", "a");
int ix2 = sr.getAttributeIndex("", "bz");
int ix3 = sr.getAttributeIndex("", "___");
if (ix1 < 0 || ix2 < 0 || ix3 < 0) {
fail("Couldn't find indexes of attributes: a="+ix1+", bz="+ix2+", ___="+ix3);
}
assertEquals(0L, sr.getAttributeAsLong(ix1));
assertEquals(Long.MAX_VALUE, sr.getAttributeAsLong(ix2));
assertEquals(-1200300400L, sr.getAttributeAsLong(ix3));
sr.close();
}
public void testSimpleFloatElem()
throws XMLStreamException
{
float[] values = new float[] {
0.0f, 10.47f, (float) (1.0 / 3.0), -0.25f,
Float.MIN_VALUE, Float.MAX_VALUE,
Float.NaN, Float.POSITIVE_INFINITY, Float.NEGATIVE_INFINITY
};
for (int i = 0; i < values.length; ++i) {
float value = values[i];
assertXML("<root>"+value+"</root>", writeFloatElemDoc("root", value));
}
}
public void testSimpleFloatAttr()
throws XMLStreamException
{
float[] values = new float[] {
0.0f, 10.47f, (float) (1.0 / 3.0), -0.25f,
Float.MIN_VALUE, Float.MAX_VALUE,
Float.NaN, Float.POSITIVE_INFINITY, Float.NEGATIVE_INFINITY
};
for (int i = 0; i < values.length; ++i) {
float value = values[i];
assertXML("<a attr='"+value+"'></a>", writeFloatAttrDoc("a", "attr", value));
}
}
public void testSimpleDoubleElem()
throws XMLStreamException
{
double[] values = new double[] {
0.0f, 10.47f, (1.0 / 3.0), -0.25f,
Double.MIN_VALUE, Double.MAX_VALUE,
Double.NaN, Double.POSITIVE_INFINITY, Double.NEGATIVE_INFINITY
};
for (int i = 0; i < values.length; ++i) {
double value = values[i];
assertXML("<root>"+value+"</root>", writeDoubleElemDoc("root", value));
}
}
public void testSimpleDoubleAttr()
throws XMLStreamException
{
double[] values = new double[] {
0.0f, 10.47f, (1.0 / 3.0), -0.25f,
Double.MIN_VALUE, Double.MAX_VALUE,
Double.NaN, Double.POSITIVE_INFINITY, Double.NEGATIVE_INFINITY
};
for (int i = 0; i < values.length; ++i) {
double value = values[i];
assertXML("<a attr='"+value+"'></a>", writeDoubleAttrDoc("a", "attr", value));
}
}
public void testBigInteger()
throws XMLStreamException
{
BigInteger I = BigInteger.valueOf(3);
Random rnd = new Random(2);
for (int i = 1; i < 200; ++i) {
assertXML("<root>"+I+"</root>", writeIntegerElemDoc("root", I));
assertXML("<a attr='"+I+"'></a>", writeIntegerAttrDoc("a", "attr", I));
I = I.multiply(BigInteger.valueOf(10)).add(BigInteger.valueOf(rnd.nextInt() & 0xF));
}
}
public void testBigDecimal()
throws XMLStreamException
{
BigDecimal D = BigDecimal.valueOf(1L);
Random rnd = new Random(9);
for (int i = 1; i < 200; ++i) {
assertXML("<root>"+D+"</root>", writeDecimalElemDoc("root", D));
assertXML("<a attr='"+D+"'></a>", writeDecimalAttrDoc("a", "attr", D));
// Ok, then, add a small integer, divide by 10 to generate digits
D = D.add(BigDecimal.valueOf(rnd.nextInt() & 0xF)).divide(BigDecimal.valueOf(10L));
}
}
public void testQNameNonRepairing()
throws XMLStreamException
{
doTestQName(false);
}
public void testQNameRepairing()
throws XMLStreamException
{
doTestQName(true);
}
private void doTestQName(boolean repairing)
throws XMLStreamException
{
final String URI = "http://my.uri";
QName n = new QName(URI, "elem", "ns");
assertXML("<root xmlns:ns='"+URI+"'>ns:elem</root>", writeQNameElemDoc("root", n, repairing));
assertXML("<root xmlns:ns='"+URI+"' attr='ns:elem'></root>",
writeQNameAttrDoc("root", "attr", n, repairing));
}
public void testIntArraysElem()
throws XMLStreamException
{
doTestIntArrays(false);
}
public void testIntArraysAttr()
throws XMLStreamException
{
doTestIntArrays(true);
}
private void doTestIntArrays(boolean testAttr)
throws XMLStreamException
{
for (int i = 0; i <= ARRAY_TEST_LENGTHS.length; ++i) {
int[] data;
if (i == 0) {
data = new int[] {
0, -139, 29, Integer.MAX_VALUE, 1, Integer.MIN_VALUE };
} else {
Random rnd = new Random(9);
int len = ARRAY_TEST_LENGTHS[i-1];
data = new int[len];
for (int ix = 0; ix < len; ++ix) {
data[ix] = rnd.nextInt();
}
}
String contents;
if (testAttr) {
contents = getAttributeContent(writeIntArrayAttrDoc("root", "attr", data));
} else {
contents = getElementContent(writeIntArrayElemDoc("root", data));
}
StringTokenizer st = new StringTokenizer(contents);
int count = 0;
while (st.hasMoreTokens()) {
String exp = String.valueOf(data[count]);
String act = st.nextToken();
if (!exp.equals(act)) {
fail("Incorrect entry #"+count+"/"+data.length+": act = '"+act+"' (exp '"+exp+"')");
}
++count;
}
assertEquals(data.length, count);
}
}
public void testLongArraysElem()
throws XMLStreamException
{
doTestLongArrays(false);
}
public void testLongArraysAttr()
throws XMLStreamException
{
doTestLongArrays(true);
}
private void doTestLongArrays(boolean testAttr)
throws XMLStreamException
{
for (int i = 0; i <= ARRAY_TEST_LENGTHS.length; ++i) {
long[] data;
if (i == 0) {
data = new long[] {
0, -139, 29, Long.MAX_VALUE, 1, Long.MIN_VALUE };
} else {
Random rnd = new Random(9);
int len = ARRAY_TEST_LENGTHS[i-1];
data = new long[len];
for (int ix = 0; ix < len; ++ix) {
data[ix] = rnd.nextLong();
}
}
String contents;
if (testAttr) {
contents = getAttributeContent(writeLongArrayAttrDoc("root", "attr", data));
} else {
contents = getElementContent(writeLongArrayElemDoc("root", data));
}
StringTokenizer st = new StringTokenizer(contents);
int count = 0;
while (st.hasMoreTokens()) {
String exp = String.valueOf(data[count]);
String act = st.nextToken();
if (!exp.equals(act)) {
fail("Incorrect entry #"+count+"/"+data.length+": act = '"+act+"' (exp '"+exp+"')");
}
++count;
}
assertEquals(data.length, count);
}
}
public void testFloatArraysElem()
throws XMLStreamException
{
doTestFloatArrays(false);
}
public void testFloatArraysAttr()
throws XMLStreamException
{
doTestFloatArrays(true);
}
@SuppressWarnings("cast")
private void doTestFloatArrays(boolean testAttr)
throws XMLStreamException
{
for (int i = 0; i <= ARRAY_TEST_LENGTHS.length; ++i) {
float[] data;
if (i == 0) {
data = new float[] {
0, -139, 29, Float.MAX_VALUE, 1, Float.MIN_VALUE };
} else {
Random rnd = new Random(9);
int len = ARRAY_TEST_LENGTHS[i-1];
data = new float[len];
for (int ix = 0; ix < len; ++ix) {
// Need to scale: nextFloat is [0.0, 1.0[
float value = rnd.nextFloat();
if (rnd.nextBoolean()) {
value = (float) (value * rnd.nextInt());
}
if (rnd.nextBoolean()) {
value = -value;
}
data[ix] = value;
}
}
String contents;
if (testAttr) {
contents = getAttributeContent(writeFloatArrayAttrDoc("root", "attr", data));
} else {
contents = getElementContent(writeFloatArrayElemDoc("root", data));
}
StringTokenizer st = new StringTokenizer(contents);
int count = 0;
while (st.hasMoreTokens()) {
String exp = String.valueOf(data[count]);
String act = st.nextToken();
if (!exp.equals(act)) {
fail("Incorrect entry #"+count+"/"+data.length+": act = '"+act+"' (exp '"+exp+"')");
}
++count;
}
assertEquals(data.length, count);
}
}
public void testDoubleArraysElem()
throws XMLStreamException
{
doTestDoubleArrays(false);
}
public void testDoubleArraysAttr()
throws XMLStreamException
{
doTestDoubleArrays(true);
}
private void doTestDoubleArrays(boolean testAttr)
throws XMLStreamException
{
for (int i = 0; i <= ARRAY_TEST_LENGTHS.length; ++i) {
double[] data;
if (i == 0) {
data = new double[] {
0, -139, 29, Double.MAX_VALUE, 1, Double.MIN_VALUE };
} else {
Random rnd = new Random(9);
int len = ARRAY_TEST_LENGTHS[i-1];
data = new double[len];
for (int ix = 0; ix < len; ++ix) {
// Need to scale: nextDouble is [0.0, 1.0[
double value = rnd.nextDouble();
if (rnd.nextBoolean()) {
value = (value * rnd.nextLong());
}
if (rnd.nextBoolean()) {
value = -value;
}
data[ix] = value;
}
}
String contents;
if (testAttr) {
contents = getAttributeContent(writeDoubleArrayAttrDoc("root", "attr", data));
} else {
contents = getElementContent(writeDoubleArrayElemDoc("root", data));
}
StringTokenizer st = new StringTokenizer(contents);
int count = 0;
while (st.hasMoreTokens()) {
String exp = String.valueOf(data[count]);
String act = st.nextToken();
if (!exp.equals(act)) {
fail("Incorrect entry #"+count+"/"+data.length+": act = '"+act+"' (exp '"+exp+"')");
}
++count;
}
assertEquals(data.length, count);
}
}
/*
////////////////////////////////////////
// Private methods, checking typed doc
////////////////////////////////////////
*/
private void checkBooleanElem(byte[] data, boolean expState)
throws XMLStreamException
{
XMLStreamReader2 sr = getRootReader(data);
assertEquals(expState, sr.getElementAsBoolean());
sr.close();
}
private void checkBooleanAttr(byte[] data, boolean expState)
throws XMLStreamException
{
XMLStreamReader2 sr = getRootReader(data);
assertEquals(expState, sr.getAttributeAsBoolean(0));
sr.close();
}
private void writeBooleanElem(TypedXMLStreamWriter sw, boolean b)
throws XMLStreamException
{
sw.writeStartDocument();
sw.writeStartElement("root");
sw.writeBoolean(b);
sw.writeEndElement();
sw.writeEndDocument();
}
private void writeBooleanAttr(TypedXMLStreamWriter sw, boolean b)
throws XMLStreamException
{
sw.writeStartDocument();
sw.writeStartElement("root");
sw.writeBooleanAttribute(null, null, "attr", b);
sw.writeEndElement();
sw.writeEndDocument();
}
private String writeIntElemDoc(String elem, int value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
// Let's not write start doc, to avoid getting xml declaration
//sw.writeStartDocument();
sw.writeStartElement(elem);
sw.writeInt(value);
sw.writeEndElement();
sw.writeEndDocument();
return getUTF8(sw, bos);
}
private String writeIntAttrDoc(String elem, String attr, int value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
// Let's not write start doc, to avoid getting xml declaration
//sw.writeStartDocument();
sw.writeStartElement(elem);
sw.writeIntAttribute(null, null, attr, value);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
// One twist: need to ensure quotes are single-quotes (for the test)
return str.replace('"', '\'');
}
private String writeLongElemDoc(String elem, long value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
// Let's not write start doc, to avoid getting xml declaration
//sw.writeStartDocument();
sw.writeStartElement(elem);
sw.writeLong(value);
sw.writeEndElement();
sw.writeEndDocument();
return getUTF8(sw, bos);
}
private String writeLongAttrDoc(String elem, String attr, long value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
// Let's not write start doc, to avoid getting xml declaration
//sw.writeStartDocument();
sw.writeStartElement(elem);
sw.writeLongAttribute(null, null, attr, value);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
// One twist: need to ensure quotes are single-quotes (for the test)
return str.replace('"', '\'');
}
private String writeFloatElemDoc(String elem, float value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
// Let's not write start doc, to avoid getting xml declaration
//sw.writeStartDocument();
sw.writeStartElement(elem);
sw.writeFloat(value);
sw.writeEndElement();
sw.writeEndDocument();
return getUTF8(sw, bos);
}
private String writeFloatAttrDoc(String elem, String attr, float value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
// Let's not write start doc, to avoid getting xml declaration
//sw.writeStartDocument();
sw.writeStartElement(elem);
sw.writeFloatAttribute(null, null, attr, value);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
// One twist: need to ensure quotes are single-quotes (for the test)
return str.replace('"', '\'');
}
private String writeDoubleElemDoc(String elem, double value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeDouble(value);
sw.writeEndElement();
sw.writeEndDocument();
return getUTF8(sw, bos);
}
private String writeDoubleAttrDoc(String elem, String attr, double value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeDoubleAttribute(null, null, attr, value);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
// One twist: need to ensure quotes are single-quotes (for the test)
return str.replace('"', '\'');
}
private String writeIntegerElemDoc(String elem, BigInteger value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeInteger(value);
sw.writeEndElement();
sw.writeEndDocument();
return getUTF8(sw, bos);
}
private String writeIntegerAttrDoc(String elem, String attr, BigInteger value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeIntegerAttribute(null, null, attr, value);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
// One twist: need to ensure quotes are single-quotes (for the test)
return str.replace('"', '\'');
}
private String writeDecimalElemDoc(String elem, BigDecimal value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeDecimal(value);
sw.writeEndElement();
sw.writeEndDocument();
return getUTF8(sw, bos);
}
private String writeDecimalAttrDoc(String elem, String attr, BigDecimal value)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeDecimalAttribute(null, null, attr, value);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
// One twist: need to ensure quotes are single-quotes (for the test)
return str.replace('"', '\'');
}
private String writeQNameElemDoc(String elem, QName n, boolean repairing)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos, repairing);
sw.writeStartElement(elem);
if (!repairing) {
sw.writeNamespace(n.getPrefix(), n.getNamespaceURI());
}
sw.writeQName(n);
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
return str.replace('"', '\'');
}
private String writeQNameAttrDoc(String elem, String attr, QName n, boolean repairing)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos, repairing);
sw.writeStartElement(elem);
if (!repairing) {
sw.writeNamespace(n.getPrefix(), n.getNamespaceURI());
}
sw.writeQNameAttribute(null, null, attr, n);
sw.writeCharacters(""); // to avoid empty elem
sw.writeEndElement();
sw.writeEndDocument();
String str = getUTF8(sw, bos);
return str.replace('"', '\'');
}
private byte[] writeIntArrayElemDoc(String elem, int[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
if ((values.length % 2) == 1) { // odd -> single write
sw.writeIntArray(values, 0, values.length);
} else { // even -> split in halves
int offset = values.length / 2;
sw.writeIntArray(values, 0, offset);
sw.writeIntArray(values, offset, values.length - offset);
}
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeIntArrayAttrDoc(String elem, String attr, int[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeIntArrayAttribute(null, null, attr, values);
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeLongArrayElemDoc(String elem, long[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
if ((values.length % 2) == 1) { // odd -> single write
sw.writeLongArray(values, 0, values.length);
} else { // even -> split in halves
int offset = values.length / 2;
sw.writeLongArray(values, 0, offset);
sw.writeLongArray(values, offset, values.length - offset);
}
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeLongArrayAttrDoc(String elem, String attr, long[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeLongArrayAttribute(null, null, attr, values);
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeFloatArrayElemDoc(String elem, float[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
if ((values.length % 2) == 1) { // odd -> single write
sw.writeFloatArray(values, 0, values.length);
} else { // even -> split in halves
int offset = values.length / 2;
sw.writeFloatArray(values, 0, offset);
sw.writeFloatArray(values, offset, values.length - offset);
}
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeFloatArrayAttrDoc(String elem, String attr, float[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeFloatArrayAttribute(null, null, attr, values);
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeDoubleArrayElemDoc(String elem, double[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
if ((values.length % 2) == 1) { // odd -> single write
sw.writeDoubleArray(values, 0, values.length);
} else { // even -> split in halves
int offset = values.length / 2;
sw.writeDoubleArray(values, 0, offset);
sw.writeDoubleArray(values, offset, values.length - offset);
}
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
private byte[] writeDoubleArrayAttrDoc(String elem, String attr, double[] values)
throws XMLStreamException
{
ByteArrayOutputStream bos = new ByteArrayOutputStream();
XMLStreamWriter2 sw = getTypedWriter(bos);
sw.writeStartElement(elem);
sw.writeDoubleArrayAttribute(null, null, attr, values);
sw.writeEndElement();
sw.writeEndDocument();
return closeWriter(sw, bos);
}
/*
////////////////////////////////////////
// Abstract methods
////////////////////////////////////////
*/
protected abstract XMLStreamWriter2 getTypedWriter(ByteArrayOutputStream out,
boolean repairing)
throws XMLStreamException;
protected abstract byte[] closeWriter(XMLStreamWriter sw, ByteArrayOutputStream out)
throws XMLStreamException;
/*
////////////////////////////////////////
// Private methods, constructing writers
////////////////////////////////////////
*/
private XMLStreamWriter2 getTypedWriter(ByteArrayOutputStream out)
throws XMLStreamException
{
return getTypedWriter(out, false);
}
// XMLStreamReader2 extends TypedXMLStreamReader
private XMLStreamReader2 getRootReader(byte[] data)
throws XMLStreamException
{
XMLStreamReader2 sr = getReader(data);
assertTokenType(START_DOCUMENT, sr.getEventType());
while (sr.next() != START_ELEMENT) { }
assertTokenType(START_ELEMENT, sr.getEventType());
return sr;
}
private XMLStreamReader2 getReader(byte[] data)
throws XMLStreamException
{
XMLInputFactory f = getInputFactory();
setCoalescing(f, false); // shouldn't really matter
setNamespaceAware(f, true);
return (XMLStreamReader2) f.createXMLStreamReader(new ByteArrayInputStream(data));
}
private String getUTF8(XMLStreamWriter sw, ByteArrayOutputStream bos)
throws XMLStreamException
{
byte[] data = closeWriter(sw, bos);
try {
return new String(data, "UTF-8");
} catch (IOException ioe) {
throw new IllegalArgumentException(ioe);
}
}
private String getElementContent(byte[] data)
throws XMLStreamException
{
XMLStreamReader sr = getReader(data);
assertTokenType(START_DOCUMENT, sr.getEventType());
while (sr.next() != START_ELEMENT) { }
assertTokenType(START_ELEMENT, sr.getEventType());
String content = sr.getElementText();
sr.close();
return content;
}
private String getAttributeContent(byte[] data)
throws XMLStreamException
{
XMLStreamReader sr = getReader(data);
assertTokenType(START_DOCUMENT, sr.getEventType());
while (sr.next() != START_ELEMENT) { }
assertTokenType(START_ELEMENT, sr.getEventType());
assertEquals(1, sr.getAttributeCount());
String content = sr.getAttributeValue(0);
sr.close();
return content;
}
/**
* Helper method to contain modifications we may need to
* reliably compare equivalency of result xml to expected
* results.
*/
void assertXML(String exp, String act)
{
// First: let's trim out xml decl, if any
act = act.trim();
if (act.startsWith("<?xml")) {
int ix = act.indexOf("?>");
act = act.substring(ix+2);
}
// Usually this is enough:
if (exp.equals(act)) {
return;
}
/* If not, let's see if we can still find them equal;
* given simplicity of docs, we only need to be concerned
* with '<a></a>' -> '<a/>' change it seems. Expected
* results seem to only differ by that much, for now...
*/
int ix = act.indexOf("/>");
if (ix > 0) {
// ugh. this is ugly, yes... if it breaks, should just rewrite completely
String prefix = act.substring(0, ix).trim();
String suffix = act.substring(ix+2); // probably empty tho
ix = prefix.lastIndexOf("<");
int ix2 = prefix.indexOf(' ', ix);
// If it was just name it'd be simpler, but there may be attr(s)
String name = (ix2 < 0) ? prefix.substring(ix+1) : prefix.substring(ix+1, ix2);
act = prefix + "></" + name + ">"+suffix;
}
assertEquals(exp, act);
}
}