1. 程式人生 > 程式設計 >手把手教你AspNetCore WebApi資料驗證的實現

手把手教你AspNetCore WebApi資料驗證的實現

前言

小明最近又遇到麻煩了,小紅希望對接介面傳送的資料進行驗證,既然是小紅要求,那小明說什麼都得滿足呀,這還不簡單嘛。

傳統驗證

[HttpPost]
public async Task<ActionResult<Todo>> PostTodo(Todo todo)
{
  if (string.IsNullOrEmpty(todo.Name))
  {
    return Ok("名稱不能為空");
  }
  context.Todo.Add(todo);
  await context.SaveChangesAsync();

  return CreatedAtAction("GetTodo",new { id = todo.Id },todo);
}

小明寫著寫著發現這樣寫,很多介面相同得地方都要寫,使得程式碼比較臃腫。

使用模型驗證

在引數模型上打上註解

namespace App001.Models
{
  /// <summary>
  /// 待辦事項
  /// </summary>
  public class Todo
  {
    /// <summary>
    /// ID
    /// </summary>
    public Guid Id { get; set; }
    /// <summary>
    /// 名稱
    /// </summary>
    [Required(ErrorMessage = "名稱不能為空")]
    public string Name { get; set; }
  }
}

Postman測試Name傳值未空時,則返回:

{
  "type": "https://tools.ietf.org/html/rfc7231#section-6.5.1","title": "One or more validation errors occurred.","status": 400,"traceId": "|df184e36-4e11844dfd38a626.","errors": {
    "Name": [
      "名稱不能為空"
    ]
  }
}

注意Web API 控制器具有 [ApiController] 特性,則它們不必檢查ModelState.IsValid。在此情況下,如果模型狀態無效,將返回包含錯誤詳細資訊的自動 HTTP 400 響應。

內建特性

  • [CreditCard]:驗證屬性是否具有信用卡格式。
  • [Compare]:驗證模型中的兩個屬性是否匹配。
  • [EmailAddress]:驗證屬性是否具有電子郵件格式。
  • [Phone]:驗證屬性是否具有電話號碼格式。
  • [Range]:驗證屬性值是否在指定的範圍內。
  • [RegularExpression]:驗證屬性值是否與指定的正則表示式匹配。
  • [Required]:驗證欄位是否不為 null。
  • [StringLength]:驗證字串屬性值是否不超過指定長度限制。
  • [Url]:驗證屬性是否具有 URL 格式。
  • [Remote]:通過在伺服器上呼叫操作方法來驗證客戶端上的輸入。

Error messages

通過驗證特性可以指定要為無效輸入顯示的錯誤訊息。 例如:

[Required(ErrorMessage = "名稱不能為空")]

使用自定義返回訊息格式

有兩種方式:

  • 使用自定義過濾器
  • 使用預設模型驗證,需要在控制器上面加上【ApiController】。

使用自定義過濾器

首先,建立ModelValidateActionFilterAttribute過濾器。

public class ModelValidateActionFilterAttribute : ActionFilterAttribute
{
  public override void OnActionExecuting(ActionExecutingContext context)
  {
    if (!context.ModelState.IsValid)
    {
      //獲取驗證失敗的模型欄位
      var errors = context.ModelState
        .Where(e => e.Value.Errors.Count > 0)
        .Select(e => e.Value.Errors.First().ErrorMessage)
        .ToList();

      var str = string.Join("|",errors);

      //設定返回內容
      var result = new
      {
        Code = 10000,Msg = "未通過資料驗證。",FullMsg = str
      };

      context.Result = new BadRequestObjectResult(result);
    }

  }
}

然後,Startup.ConfigureServices將過濾器新增到控制器中並關閉預設模型驗證,另外我們還添加了AddNewtonsoftJson。

//關閉預設模型驗證
services.Configure<ApiBehaviorOptions>(opt => opt.SuppressModelStateInvalidFilter = true);
services.AddControllers(opt =>
{
  //新增過濾器
  opt.Filters.Add(typeof(ModelValidateActionFilterAttribute));
}).AddNewtonsoftJson(opt =>
{
  //json字串大小寫原樣輸出
  opt.SerializerSettings.ContractResolver = new DefaultContractResolver();
});

最後,我們看一下返回效果:

{
  "Code": 10000,"Msg": "未通過資料驗證。","FullMsg": "名稱不能為空。"
}

使用預設模型驗證

services.Configure<ApiBehaviorOptions>(opt =>
{
  opt.InvalidModelStateResponseFactory = actionContext =>
  {
    //獲取驗證失敗的模型欄位 
    var errors = actionContext.ModelState
      .Where(e => e.Value.Errors.Count > 0)
      .Select(e => e.Value.Errors.First().ErrorMessage)
      .ToList();

    var str = string.Join("|",errors);

    //設定返回內容
    var result = new
    {
      Code = 10000,FullMsg = str
    };

    return new BadRequestObjectResult(result);
  };
});

小結

目前為止,小明把資料驗證也搞定了,是不是so easy!

到此這篇關於手把手教你AspNetCore WebApi資料驗證的實現的文章就介紹到這了,更多相關AspNetCore WebApi資料驗證內容請搜尋我們以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援我們!