一、模型驗證的作用
在ASP.NET Web API中,我們可以使用 System.ComponentModel.DataAnnotations 命名空間中的屬性為模型上的屬性設置驗證規則。
一個模型驗證栗子
using System.ComponentModel.DataAnnotations; namespace MyApi.Models { public class Product { public int Id { get; set; } [Required] public string Name { get; set; } public decimal Price { get; set; } [Range(0, 999)] public double Weight { get; set; } } }
和ASP.NET MVC中中的模型驗證十分相似,上邊的驗證規則是:Name屬性不能為空,Weight必須在0與999之間。關於驗證屬性的用法可以參考.NET MVC的驗證屬性。
客戶端(沒有必須的Name):
<form action="api/Product" method="post"> Id:<input type="text" name="Id" value="4" /><br /> Price:<input type="text" name="Price" value="1.99" /><br /> Weight:<input type="text" name="Weight" value="2.99" /><br /> <input type="submit" value="Submit" /> </form>
控制器代碼:
public class ProductsController : ApiController { public HttpResponseMessage Post(Product product) { if (ModelState.IsValid) { // Do something with the product (not shown). return new HttpResponseMessage(HttpStatusCode.OK); } else { return Request.CreateErrorResponse(HttpStatusCode.BadRequest, ModelState); } } }
當我們提交表格時,google中返回的內容如下
兩個小問題:
“Under-Posting”:客戶端提交的模型缺少字段,如果是[required]修飾的字段,ModelState不通過驗證,如果是數字類型的,用0補充。
“Over-Posting”:客戶端也可以發送更多的數據,JSON格式化器只是忽略此值(XML格式化程序也是如此)。
二 、WebApi中的處理驗證錯誤
第一步 添加過濾器
驗證失敗時,Web API不會自動向客戶端返回錯誤,這就需要控制器來做出適當的響應。我們可以創建action filter用於在Action執行之前檢查模型狀態。和MVC中的用法一樣,代碼顯示了一個示例:
public class ValidateModelAttribute : ActionFilterAttribute { public override void OnActionExecuting(HttpActionContext actionContext) { if (!actionContext.ModelState.IsValid) { //返回第一個異常的錯誤消息 actionContext.Response = actionContext.Request.CreateResponse( HttpStatusCode.InternalServerError, new { code = 0, msg = actionContext.ModelState.Values.First().Errors.First().ErrorMessage }); } } }
如果模型驗證失敗,則此過濾器返回包含驗證錯誤的HTTP響應,這樣就不再執行Action了。
第二步 使用過濾器
如果我們想在全局使用這種方案,我們可以設置一個全局的過濾器,在配置階段把上邊的過濾器添加到 HttpConfiguration.Filters 集合中。
public static class WebApiConfig { public static void Register(HttpConfiguration config) { config.Filters.Add(new ValidateModelAttribute()); } }
如果不想使用全局過濾器,我們也可以把filter設置為各個Controller或Action的屬性:
public class ProductsController : ApiController { [ValidateModel] public HttpResponseMessage Post(Product product) { // ... } }
這里主要總結了WebApi中的模型驗證,了解更多可查看官網。