ASP.Net Core returns a 500 server error from a FileStreamResult

Posted by Blake on 12/28/2018
)

Scenario

You have created a Stream of some sort successfully but upon trying to return that stream the server throws a 500 error.

Explanation

If you have verified that the stream you created is valid there is a good chance that the position of the stream has not been reset to the start of the stream. The result of this is that the FileStreamResult tries to create a stream but starts from it's end position and finds no additional data and thus tries to write a blank stream out which is the cause of the error (this is not thrown as an Exception).

Solution

The fix this problem you will want to reset the stream you're using to it's start position. In the below IActionResult a MemoryStream containing a wave file of synthesized speech is created. The ms.Position = 0; line then resets the MemoryStream before it is written out to the FileStreamResult.

[HttpPost]
public IActionResult Post([FromBody] string value)
{
    // Don't process what wasn't provided.
    if (string.IsNullOrWhiteSpace(value))
    {
        return StatusCode(500, "No text was provided to convert to speech.");
    }

    // Create the speech synthesizer, write the contents to a MemoryStream then send that
    // MemoryStream back to the client as a wave file.
    var synth = new SpeechSynthesizer();
    var ms = new MemoryStream();
    synth.SetOutputToWaveStream(ms);
    synth.Speak(value);
            
    // Reset the position on the MemoryStream to the beginning.
    ms.Position = 0;

    // Dispose of the synth object... we can't Dispose of the MemoryStream or it can't be written out
    // to the FileStreamResult.
    synth.Dispose();

    return File(ms, "audio/wav");
}

Additional Note

The above example was written for ASP.Net Core 2.2 targeting the full .Net Framework 4.7 (which contains the speech synthesis classes).