1

我已經看過了一些關於這個話題的帖子的 - 自定義服務器端驗證 - hereherehere(我相信這是MVC4),但似乎沒有爲我解決這個問題。自定義數據註解不是回傳顯示錯誤 - ASP.NET核心MVC6

我創建了一個基本的MVC6項目(兩個文本框)只是爲了測試dataannotations,仍然無法讓這個工作。作爲基礎,我正在使用這個tutorial並重新創建了他的數據驗證類,而且沒有任何更改。

我沒有使用實際的模型,而是一個viewModel,如果驗證成功,通過賦值給模型更新數據庫。

我對這裏的成功驗證不感興趣,但是當「(ModelState.IsValid)」等於「False」時,它是否在文本框下顯示錯誤消息。

我已經通過它,發現它確實通過實際的自定義驗證程序,它肯定給自定義驗證上的模型狀態爲false - 返回視圖 - 但不顯示錯誤消息。

但是,如果我從文本框中刪除所有內容 - 將其設置爲空 - 將返回視圖模型,但是這次它會出現紅色的「必需」錯誤..也就是說,錯誤消息僅適用於數據註釋自定義註釋。

OK so 爲什麼它顯示正常的註釋驗證錯誤而不是自定義驗證錯誤

這是ASP.NET核心的結果還是隻是我返回viewmodel的方式(例如,我更可能是一個錯誤)?

我已決定包括所有移動部件,因爲它們可能是其中任何一個都不正確或存在問題。這就是模型,基於模型的視圖模型,控制器和自定義校驗器類。

public class CompanyDetail 
    { 
     public int CompanyDetailId { get; set; } 
     public string CompanyName { get; set; } 
     public string ABN { get; set; } 
    } 

甲CompanyDetailViewModel與數據註解添加:

public class CompanyDetailsViewModel 
{ 
    public int CompanyDetailsId { get; set; } 

    [ExcludeChar("/")] 
    [Required(ErrorMessage = "A Company Name is required")] 
    [Display(Name = "Company Name:")] 
    [StringLength(100)] 
    public string CompanyName { get; set; } 

    [Required(ErrorMessage = "An ABN is required")] 
    [CheckValidABN(ErrorMessage = "This is not a valid ABN")] 
    [Display(Name = "ABN:")] 
    public string ABN { get; set; } 
} 

控制器: 公共類CompanyDetailsController:控制器 { 私人ApplicationDbContext _context;

public CompanyDetailsController(ApplicationDbContext context) 
    { 
     _context = context;  
    } 


    // GET: CompanyDetailsViewModels/Edit/5 
    public IActionResult Edit() 
    { 

     var Company = _context.CompanyDetails.First(); 
     if (Company == null) 
     { 
      return HttpNotFound(); 
     } 
     var CompanyDetails = new CompanyDetailsViewModel(); 

     CompanyDetails.CompanyDetailsId = Company.CompanyDetailId; 
     CompanyDetails.CompanyName = Company.CompanyName; 
     CompanyDetails.ABN = Company.ABN; 

     return View(CompanyDetails); 
    } 

    // POST: CompanyDetailsViewModels/Edit/5 
    [HttpPost] 
    [ValidateAntiForgeryToken] 
    public IActionResult Edit(CompanyDetailsViewModel companyDetailsViewModel) 
    { 
     if (ModelState.IsValid) 
     { 
      CompanyDetail Company = _context.CompanyDetails.First(); 
      var CompanyDetails = new CompanyDetailsViewModel(); 

      Company.CompanyName = CompanyDetails.CompanyName; 
      CompanyDetails.ABN = Company.ABN; 

      _context.CompanyDetails.Update(Company); 
      _context.SaveChanges(); 

      return RedirectToAction("Index"); 
     } 
     return View(companyDetailsViewModel); 
    } 

} 

與(香草腳手架)形式的視圖 - 它使用視圖模型作爲模型:

<form asp-action="Edit"> 
<div class="form-horizontal"> 
    <h4>CompanyDetailsViewModel</h4> 
    <hr /> 
    <div asp-validation-summary="ValidationSummary.ModelOnly" class="text-danger"></div> 
    <input type="hidden" asp-for="CompanyDetailsId" /> 
    <div class="form-group"> 
     <label asp-for="ABN" class="col-md-2 control-label"></label> 
     <div class="col-md-10"> 
      <input asp-for="ABN" class="form-control" /> 
      <span asp-validation-for="ABN" class="text-danger" /> 
     </div> 
    </div> 
    <div class="form-group"> 
     <label asp-for="CompanyName" class="col-md-2 control-label"></label> 
     <div class="col-md-10"> 
      <input asp-for="CompanyName" class="form-control" /> 
      <span asp-validation-for="CompanyName" class="text-danger" /> 
     </div> 
    </div> 
    <div class="form-group"> 
     <div class="col-md-offset-2 col-md-10"> 
      <input type="submit" value="Save" class="btn btn-default" /> 
     </div> 
    </div> 
</div> 

和實際定製驗證類:

public class ExcludeChar : ValidationAttribute 
{ 
    private readonly string _chars; 
    public ExcludeChar(string chars) 
    : base("{0} contains invalid character.") 
    { 
     _chars = chars; 
    } 


    protected override ValidationResult IsValid(object value, ValidationContext validationContext) 
    { 
     if (value != null) 
     { 
      for (int i = 0; i < _chars.Length; i++) 
      { 
       var valueAsString = value.ToString(); 
       if (valueAsString.Contains(_chars[i])) 
       { 
        var errorMessage = FormatErrorMessage(validationContext.DisplayName); 
        return new ValidationResult(errorMessage); 
       } 
      } 
     } 
     return ValidationResult.Success; 
    } 
} 
+0

如果我在視圖CSHTML爲「ValidationSummary.All」的錯誤消息顯示,但只在頁面頂部更改「

」 - 不是在文本框。如果我清除文本框那麼「requred」錯誤顯示在兩個地方...出於某種原因,自定義的驗證只顯示摘要且僅當其設置爲「所有」 – si2030

+0

難道這個功能甚至MVC6存在嗎? – si2030

+0

是否有一個特定的原因,你爲什麼不使用內置的HTML幫助器? – JDupont

回答

0

您必須做的是在視圖中指定您希望顯示自定義錯誤消息的位置。

例如:

<div> 
    @Html.ValidationMessage("CreditRating") 
</div> 

然後返回其涉及「成員」企業資信將在視圖的那部分表現出的ValidationResult。成員在引號中,因爲名稱實際上可以是任何名稱,不一定是真實的名稱。

results.Add(new ValidationResult("NO NO NO", new[] { "CreditRating" })); 

我同意這是令人驚訝的行爲。我覺得自定義錯誤處理方式不同。也許一些沒有記錄的命名約定。

1

我想它在你的代碼中使用

<span asp-validation-for="number" class="text-danger" /> 

由Visual Studio生成默認的那HTML(不知道爲什麼)。您需要添加結束標記。使用它像

<span asp-validation-for="number" class="text-danger" ></span> 

它會顯示正確的錯誤信息在該字段下。