【问题标题】:ASP.NET MVC5 ModelState is always invalid while simultaneously not showing validationsASP.NET MVC5 ModelState 始终无效,同时不显示验证
【发布时间】:2021-09-10 04:27:33
【问题描述】:

我有一个带有一些验证规则的模型,例如最小字符串长度为 12。

public class Client{
    [Required("ID Cannot be empty")]
    [StringLength(12, ErrorMessage="ID must have 12 characters", MinimumLength = 12)]
    public string Id { get; set; }
    
    [Required("Name cannot be empty")]
    [StringLength(60, ErrorMessage="Must be between 10 and 60 characters", MinimumLength = 10)]
    public string FullName { get; set; }

    [Required("Phone cannot be empty")]
    [StringLength(9, ErrorMessage="Phone number must have 9 characters", MinimumLength = 9)]
    public string PhoneNumber { get; set; }

    [Required("Client needs a status")]
    public bool PremiumStatus { get; set; }
  
}

这些规则在我拥有的Registration 视图中起作用,这意味着我可以看到验证消息,并且如果模型无效,则不会注册模型。 但是,在我的搜索/编辑视图中,我应该能够查找 Id 并修改返回的模型,但没有任何更改正在注册,并且在调试应用程序时,我看到模型的 ModelState 始终无效,但是同时,我没有看到任何验证消息

@model MyApp.Models.Client
@{
    ViewBag.Title = "MyApp"
}

@using(Html.BeginForm("Search", "Search", FormMethod.Post)){
    Search for ID: @Html.TextBox("SearchId")
    <input type="submit" value="Search"/>
}
@using(Html.BeginForm("EditClient", "Search", FormMethod.Post)){
    @Html.LabelFor(m => m.Id)
    @Html.DisplayFor(m => m.Id)

    @Html.LabelFor(m => m.FullName)
    @Html.EditorFor(m => m.FullName)
    @Html.ValidationMessageFor(m => m.FullName)

    @Html.LabelFor(m => m.PhoneNumber)
    @Html.EditorFor(m => m.PhoneNumber)
    @Html.ValidationMessageFor(m => m.PhoneNumber)

    @Html.LabelFor(m => m.PremiumStatus)
    @Html.EditorFor(m => m.PremiumStatus)
    @Html.ValidationMessageFor(m => m.PremiumStatus)

    <input type="submit" value="Save Changes"/>

}

请注意,我只想编辑姓名、电话和状态。我不想编辑 ID,因此它只是一个显示字段

现在在我的控制器上

public class SearchController : Controller {
    public ActionResult Search() {
        return View();
    }


    [HttpPost]
    public ActionResult Search(string SearchId) {
        //Searching my Session variable to retrieve Client item related to the code searched.
        //I have validations in place in case the ID doesn't exist, but I'm not showing them to keep the code simple.
        Client clientFound = (Client) Session[SearchId];
        //Returns the view with the found model, populating all of the fields in the view.
        return View("Search", clientFound)
    }
     [HttpPost]
     //I just added these 2 annotations, but it wasn't working without them either
     [ValidateAntiForgeryToken]
     [ValidateInput(true)]
     public ActionResult EditClient(Client model) {
         if(ModelState.IsValid){
             Session[model.Id] = model;
             Debug.WriteLine("Client updated");
             
         } 
         return RedirectToAction("Search");
     }
}

通过设置断点,我可以看到一旦进入EditClient,模型确实分配了正确的、新更新的属性。只是它总是被认为是无效的。如前所述,即使我从可编辑字段中删除所有内容,我也不会收到显示它们无效的错误消息。

【问题讨论】:

  • 您是否在编辑时发送防伪令牌?

标签: c# asp.net asp.net-mvc razor


【解决方案1】:

在您的 Client 模型上,属性 Id 是必需的。

由于它是必需的,因此您需要确保有一个与您的 Id 属性相对应的输入字段,我在您的 .cshtml 上找不到任何与之对应的 input 字段。

您可以包含@Html.HiddenFor(m =&gt; m.Id)(这是一个隐藏类型的输入字段),这样当您提交表单时,Id 仍将包含在帖子中。

【讨论】:

  • 我通过从 TempData 检索最后一个客户端并在 edit 方法中用它替换不完整的模型来解决它,然后手动验证属性,但您的解决方案肯定要干净得多。谢谢!
【解决方案2】:

我认为您应该阅读更多关于 ASP.NET 中的 ModelState 的内容。

这里有一些 StackOverflow 答案,可能对微软官方文档有所帮助。

  1. What does ModelState.IsValid do?
  2. https://docs.microsoft.com/en-us/aspnet/web-api/overview/formats-and-model-binding/model-validation-in-aspnet-web-api
  3. https://www.exceptionnotfound.net/asp-net-mvc-demystified-modelstate/

现在稍微解释一下您的问题。您根据需要设置的字段之一没有您的操作期望的该字段的数据类型或内容尚未设置为适当的数据类型。我自然会建议对于编辑和搜索功能,您应该使用其他形式的验证而不是 ModelState。因此,对于假设的解决方案,您的编辑视图自然应该像模态视图一样,如果我选择详细信息,它会通过用户 ID 获取显示该用户信息的当前数据。然后我可以连同内容和用户 ID 一起提交我的编辑,然后这将使用 ID 匹配的新数据更新数据库,假设 ID 对于每个用户都是唯一的。

谢谢 请阅读分享的链接。

【讨论】:

  • 我阅读了您发布的所有文章,但我不确定我是否能想到解决方案。基本上,DisplayFor 字段实际上不会向编辑表单发送任何内容,因此EditClient 接收的客户端是不完整的,因此是无效的。即使我手动将属性添加到客户端,我也无法更改ModelState 的状态。我已经找到了数据保存问题的解决方案,只需将SearchId 保存在Temp 变量中并用它检索Session 客户端,但现在我不知道如何显示编辑表单的验证消息
  • 我将不得不尝试模仿您的代码,并与一个工作示例分享一个额外的更新。
猜你喜欢
  • 2011-02-09
  • 2018-02-15
  • 2011-12-31
  • 1970-01-01
  • 1970-01-01
  • 2021-02-12
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多