I am trying to write an ApiController
that streams JSON data in the response. It goes something like this;
public class MyController : ApiController
{
IDocumentWriter _writer;
public MyController(IDocumentWriter writer)
{
_writer = writer;
}
[HttpGet]
public async Task<HttpResponseMessage> Get()
{
var response = Request.CreateResponse(HttpStatusCode.OK);
using (var stream = new MemoryStream())
{
response.Content = new StreamContent(stream);
await _writer.WriteAsync(stream);
response.Content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
response.Content.Headers.ContentLength = stream.Length;
}
return response;
}
}
The IDocumentWriter
accepts a stream and writes the JSON data to it. A call to Get
fails with a System.Threading.Tasks.TaskCanceledException
, which I don't understand because I am awaiting the WriteAsync
. Surely it finishes writing before returning? What am I doing wrong?
I figured it out thanks to this post. Turns out I was over complicating things. Here is the final solution;
[HttpGet]
public async Task<HttpResponseMessage> Get()
{
var response = Request.CreateResponse(HttpStatusCode.OK);
response.Content = new PushStreamContent(async (stream, content, context) =>
{
await _writer.WriteAsync(stream);
stream.Close();
}, "application/json");
return response;
}