Search code examples
javaxmloutputstreamfileoutputstreamclass-members

When OutputStream is stored as a member, it doesn't seem to work when writing to it using an XmlStreamWriter, can it not be passed as a member?


I am trying to store an OutputStream as a member of a class so that I can write to it from multiple methods. I put together this jUnit test to demonstrate the problem I have.

public class XmlStreamWriterTest {

private OutputStream outputStream;

@Before
public void setUp() throws Exception {
    File file = new File("xmltester.xml");
    this.outputStream = new FileOutputStream(file);
}

@After
public void tearDown() throws Exception {
    this.outputStream.close();
}

//This doesn't work.
@Test
public void testOutputStream() throws Exception {
    XMLOutputFactory xmlOutputFactory = XMLOutputFactory.newInstance();
    XMLStreamWriter xmlStreamWriter = xmlOutputFactory.createXMLStreamWriter(this.outputStream);

    xmlStreamWriter.writeStartElement("test");
    xmlStreamWriter.writeCharacters("This is a test.");
    xmlStreamWriter.writeEndElement();

    xmlStreamWriter.flush();
}


//This works
@Test
public void testOutputStreamLocal() throws Exception {
    File file = new File("xmltester2.xml");
    OutputStream outputStreamLocal = new FileOutputStream(file);
    XMLOutputFactory xmlOutputFactory = XMLOutputFactory.newInstance();
    XMLStreamWriter xmlStreamWriter = xmlOutputFactory.createXMLStreamWriter(outputStreamLocal);

    xmlStreamWriter.writeStartElement("test");
    xmlStreamWriter.writeCharacters("This is a test.");
    xmlStreamWriter.writeEndElement();

    xmlStreamWriter.close();
    }
}

Of the resulting files, only the second method pushes any values to the file. Do I have to pass the OutputStream to every method directly? Why doesn't the testOutputStream() method work?

I'm using the jrockit jdk 1.6.0_29, but I tried running on JDK 8 and it worked the same.


Solution

  • If you step through this test in a debugger and put a breakpoint on the "flush/close" (i.e. last) line in each test, when you step over it you can see that the file is written in both cases.

    The problem is your setup method.

    This is what is happening...

    1. Setup is called, outputStream created (this will overwrite any existing file!!)
    2. testOutputStream DOES work and outputs the file
    3. Setup is called again, as an outputstream is created here, the file from the first test will be overwritten
    4. The second test sets up another output stream

    Basically, move the code out of your setup method into the first test case