如何在ASP.NET Core WebAPI中获取转换为C#类前的JSON请求体
获取ASP.NET Core WebAPI的原始JSON请求体
如果你已经通过[FromBody]绑定了模型类,但还想拿到未被序列化前的原始JSON请求体,有两种实用方案:
方案一:在模型绑定后读取请求体(需启用缓冲)
默认情况下,ASP.NET Core的请求体流是只能读取一次的,所以要先配置允许重复读取:
- 在
Program.cs中添加中间件启用请求体缓冲:
app.Use(async (context, next) => { // 启用缓冲,让请求体可以被多次读取 context.Request.EnableBuffering(); await next(); });
- 在Action中重置流位置并读取原始JSON:
[HttpPost] public async Task<IActionResult> CreateUser([FromBody] UserInput userInput) { if (userInput == null) return BadRequest(); string rawJson = null; if (Request.Body.CanSeek) { // 将流指针重置到起始位置,因为模型绑定已经读取过一次 Request.Body.Position = 0; using var streamReader = new StreamReader(Request.Body); rawJson = await streamReader.ReadToEndAsync(); // 读完后再次重置指针,避免后续中间件读取异常 Request.Body.Position = 0; } // 这里可以使用rawJson做日志、校验等操作 var userOutput = await _userService.AddUser(userInput); return CreatedAtRoute("GetUser", new { userId = userOutput.UserId }, userOutput); }
方案二:手动读取请求体并自行序列化模型
如果不想依赖模型绑定的自动序列化,可以直接读取原始JSON,再手动反序列化为UserInput:
[HttpPost] public async Task<IActionResult> CreateUser() { using var streamReader = new StreamReader(Request.Body); string rawJson = await streamReader.ReadToEndAsync(); if (string.IsNullOrWhiteSpace(rawJson)) return BadRequest("请求体不能为空"); // 自行反序列化为UserInput var userInput = JsonSerializer.Deserialize<UserInput>(rawJson, new JsonSerializerOptions { PropertyNameCaseInsensitive = true // 忽略大小写匹配字段 }); if (userInput == null) return BadRequest("请求体格式不符合要求"); // 使用rawJson和userInput进行后续操作 var userOutput = await _userService.AddUser(userInput); return CreatedAtRoute("GetUser", new { userId = userOutput.UserId }, userOutput); }
注意事项
- 方案一中必须启用
EnableBuffering,否则请求体流无法重复读取,会抛出异常。 - 如果需要频繁获取原始请求体,可以封装成自定义中间件或过滤器,避免在每个Action中重复写读取逻辑。
内容的提问来源于stack exchange,提问作者Adam Wojnar
相关产品推荐
相关产品推荐

