请求在Asp.net核心自定义中间件中读取后为空
本文关键字:读取 中间件 自定义 Asp net 核心 请求 | 更新日期: 2023-09-27 18:18:14
我发现asp.net核心自定义中间件中的请求只能读取一次,之后我必须手动将请求设置回request . body。这是推荐的阅读请求的方式吗?
public async Task Invoke(HttpContext context)
{
var request = context.Request;
string xmlstring;
using (System.IO.MemoryStream m = new System.IO.MemoryStream())
{
try
{
if (request.Body.CanSeek == true) request.Body.Position = 0;
request.Body.CopyTo(m);
xmlstring = System.Text.Encoding.UTF8.GetString(m.ToArray());
}
catch (Exception ex)
{
throw ex;
}
}
context.Request.Body = new MemoryStream(Encoding.UTF8.GetBytes(xmlstring));
await _next.Invoke(context);
}
我试着"copy"流到另一个,但没有帮助。我怀疑所有自定义中间件都有设置请求体的这一步,所以在这里问一下我是否以正确的方式做了。
正确的步骤应该是:
- enablerewind
- 读取正文
- 做倒带
请注意:如果没有将set body返回到originalRequestBody,它将只工作一次,如果你试图再次调用相同的web api,它将失败。
请参见下面的示例代码
public async Task Invoke(HttpContext context)
{
var originalRequestBody = context.Request.Body;
context.Request.EnableRewind();
try
{
using (System.IO.MemoryStream m = new MemoryStream())
{
context.Request.Body.CopyTo(m);
var s = System.Text.Encoding.UTF8.GetString(m.ToArray());
}
//this line will rewind the request body, so it could be read again
context.Request.Body.Position = 0;
await _next(context);
}
catch (Exception ex)
{
}
finally
{
//important, otherwise, even current request will succeed, following request will fail
context.Request.Body = originalRequestBody;
}
}