首页 > 解决方案 > 如何规范化 ASP.NET Core API 结果中的 BadRequest(ModelState) 大小写

问题描述

我正在从 ASP.NET 控制器操作返回 BadRequest(ModelState),如下所示:

public class Person{
   [MaxLength(40)]
   public string Name{get;set;}
   public double Height{get;set;}
}

public Put([FromBody]Person item){
    if(!ModelState.IsValid) return BadRequest(ModelState);
    //save to db
    return Ok(item);
}

这可行,但是当 BadRequest 被序列化为 JSON 时,大小写似乎不一致。首先,对象序列化为 camelCase,正如预期的那样:

GET /api
{ name:'foo',
  height: 11
}

如果错误是模型绑定失败,则外壳为驼峰式:

PUT /api {name:'bob',height:'foo'}
{
    height:['Could not convert 'foo' to double']
}

如果错误是验证失败,则大小写为 PascalCased:

PUT /api {name:'morethan40characters', height:12}
{
    Name:['Name should be between 0 and 40 characters']
}

我想我明白为什么会这样:模型绑定是从发布的以驼峰命名的 JSON 开始的,而验证是直接针对 .NET 类(即 PascalCased)进行的。

但是,API 消费者不会关心这种区别,并且会期望一致的大小写。尤其是在带有 Vue 或 Angular 之类的客户端 UI 中,让所有内容保持驼峰式或至少一致会更干净:

http.put('/api',item).then(x=>{...},e=>{ this.error=e.response.data });
...
<ul>
  <li v-for="message in error.height">{{message}}</li>
  <li v-for="message in error.Height">{{message}}</li>
  <!-- line above smells -->
</ul>
<input type="text" v-model="item.height">

显然,我可以在客户端按摩错误响应,但是是否有一个标志或一些中间件我可以在服务器端执行以使其保持一致。最好是始终如一的驼峰式?

标签: asp.net-corebad-requestmodelstate

解决方案


尝试CamelCasePropertyNamesContractResolver

services.AddMvc().AddJsonOptions(options => {
    options.SerializerSettings.ContractResolver =
        new Newtonsoft.Json.Serialization.CamelCasePropertyNamesContractResolver();
})

所以如果发送PUT /api {name: "xxxxx",height: 1111},结果将是:{"errors":{"name":["


推荐阅读