Stream was not readable
TL;DR - flush & reset, see:
I recently started writing some tests (in xUnit using Moq + StructureMap) for a service that calls a class -- let's call it LogWriter -- that simply writes formatted logging data to a Stream. After creating an interface for the logging class, ILogWriter, I wanted to write some tests on LogWriter to see if it was working as expected (before testing out my service which depends on ILogWriter).
After the ILogWriter was done, I used StreamReader to check out it's input. The Stream I told it to write to was a MemoryStream (this is unit testing).
The "BaseStream_Is_Not_Empty" test always failed. The Stream was always empty. Hmmm...how about if we try closing the Stream?
Now we would expect to get: Stream was not readable. The Stream has been closed -- you can't read from it. The trick now is to reset the position of the Stream and set the BaseStream of LogWriter to AutoFlush.
And now our test passes. Moving on...
[Fact] public void BaseStream_Is_Not_Empty() { MemoryStream stream = new MemoryStream(); LogWriter logWriter = new LogWriter(stream); logWriter.WriteLine(new[] { DateTime.Now.ToString("yyyy-MM-dd"), "Log data" }); logWriter.BaseStream.AutoFlush = true; stream.Seek(0, SeekOrigin.Begin); using (StreamReader sr = new StreamReader(stream)) { Assert.NotEmpty(sr.ReadToEnd()); } }
I recently started writing some tests (in xUnit using Moq + StructureMap) for a service that calls a class -- let's call it LogWriter -- that simply writes formatted logging data to a Stream. After creating an interface for the logging class, ILogWriter, I wanted to write some tests on LogWriter to see if it was working as expected (before testing out my service which depends on ILogWriter).
After the ILogWriter was done, I used StreamReader to check out it's input. The Stream I told it to write to was a MemoryStream (this is unit testing).
public class LogWriterTests { [Fact] public void BaseStream_Is_Not_Empty() { MemoryStream stream = new MemoryStream(); LogWriter logWriter = new LogWriter(stream); logWriter.WriteLine(new[] { DateTime.Now.ToString("yyyy-MM-dd"), "Log data" }); using (StreamReader sr = new StreamReader(stream)) { Assert.NotEmpty(sr.ReadToEnd()); } } } // A basic example public class LogWriter { public LogWriter(Stream stream) { BaseStream = new StreamWriter(stream); } public StreamWriter BaseStream { get; set; } public void WriteLine(params object[] logObjects) { BaseStream.WriteLine(DoSomeFormatting(logObjects)); } }
The "BaseStream_Is_Not_Empty" test always failed. The Stream was always empty. Hmmm...how about if we try closing the Stream?
[Fact] public void BaseStream_Is_Not_Empty() { MemoryStream stream = new MemoryStream(); LogWriter logWriter = new LogWriter(stream); logWriter.WriteLine(new[] { DateTime.Now.ToString("yyyy-MM-dd"), "Log data" }); logWriter.BaseStream.Close(); using (StreamReader sr = new StreamReader(stream)) { Assert.NotEmpty(sr.ReadToEnd()); } }
Now we would expect to get: Stream was not readable. The Stream has been closed -- you can't read from it. The trick now is to reset the position of the Stream and set the BaseStream of LogWriter to AutoFlush.
[Fact] public void BaseStream_Is_Not_Empty() { MemoryStream stream = new MemoryStream(); LogWriter logWriter = new LogWriter(stream); logWriter.WriteLine(new[] { DateTime.Now.ToString("yyyy-MM-dd"), "Log data" }); logWriter.BaseStream.AutoFlush = true; stream.Seek(0, SeekOrigin.Begin); using (StreamReader sr = new StreamReader(stream)) { Assert.NotEmpty(sr.ReadToEnd()); } }
And now our test passes. Moving on...