Why is Request.BodyReader empty, when I add request parameters (ASP.NET Core 3.0)

Viewed 3988

I migrate from ASP.NET Core 2.2 to 3.0 and now have a problem. If I write code like this:

[HttpPost("test")]
public async Task Test(object o) {
    HttpContext.Request.EnableBuffering();
    var result = await HttpContext.Request.BodyReader.ReadAsync();
    var buffer = result.Buffer;
    Console.WriteLine(System.Text.Encoding.Default.GetString(buffer.FirstSpan));
    HttpContext.Request.BodyReader.AdvanceTo(buffer.End);
}

I will receive an empty message in console, but if I remove parameter

[HttpPost("test")]
public async Task Test() {
    HttpContext.Request.EnableBuffering();
    var result = await HttpContext.Request.BodyReader.ReadAsync();
    var buffer = result.Buffer;
    Console.WriteLine(System.Text.Encoding.Default.GetString(buffer.FirstSpan));
    HttpContext.Request.BodyReader.AdvanceTo(buffer.End);
}

, I receive message from body

curl -X POST \ http://localhost:5000/test \ -H 'Content-Type: application/json' \ -d '{ "test":123 }'

1 Answers

I had a similar problem, logging request bodies for webhook request bodies.

You need to first enable buffering for the request body, otherwise, it is a forward-only stream, which when consumed will be empty (and cannot be rewound).

In Startup.cs, add the following to the Configure() method:

app.Use((context, next) =>
        {
            context.Request.EnableBuffering();
            return next();
        });

I found the solution here: https://github.com/aspnet/AspNetCore/issues/15009#issuecomment-542291956 (Thratcher wrote it)

Related