具有绑定属性的 MVC 操作方法需要指南行

本文关键字:操作方法 MVC 绑定 属性 | 更新日期: 2023-09-27 18:36:08

我正在浏览一个操作方法代码,我看到那里使用了一个属性,但我真的不明白它的用法。 这是代码

public ActionResult User([Bind(Include = "Username,FullName,Email")]User user)
{
   if (!ModelState.IsValid()) return View(user);
   try
   {
     user.save()
     // return the view again or redirect the user to another page
   }
   catch(Exception e)
   {
     ViewData["Message"] = e.Message;
     return View(user)
   }
}
([Bind(Include = "Username,FullName,Email")]User user)

我只是不明白上面的行绑定包含等

所以请帮助我理解使用的这种属性以及当人们在 MVC 中编写这种代码时,如果有人用示例小代码让我了解他们将使用这种Bind attribute,那将是非常有帮助的。

更新:假设我有表单,用户只能输入名字,姓氏和性别,那么我的操作方法看起来像

public ActionResult Edit(string FirstName,string LastName,string Gender)
{
    // ...
}

我认为这将起作用。 那么为什么我应该使用 Bind 属性,因为我上面的操作方法可以正常工作。

具有绑定属性的 MVC 操作方法需要指南行

Bind属性允许您"微调"某些参数 Type 的模型绑定过程,而无需注册特定于 Type 的自定义ModelBinder

例如,假设您的操作需要按如下方式定义的Person参数:

public class Person
{
    public Person(string firstName, string lastName, Gender gender)
    {
        this.FirstName = firstName;
        this.LastName = lastName;
        if (gender == Gender.Male)
            this.FullName = "Mr. " + this.FirstName + " " + this.LastName;
        else
            this.FullName = "Mrs. " + this.FirstName + " " + this.LastName;
    }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public Gender Gender { get; set; }
    // 'FullName' is a computed column:
    public string FullName { get; set; }
}

和行动:

public ActionResult Edit(Person person)
{
    ...
}

现在,如果有人发布以下 JSON:

{
    "FirstName":"John",
    "LastName":"Smith",
    "Gender":"Male",
    "FullName":"Mrs. John Smith"
}

您的操作现在将有一个错误FullNameperson("夫人"而不是"先生")。

若要避免此类行为,可以使用 Bind 属性并从绑定过程中显式排除 FullName 属性("黑名单"):

public ActionResult Edit([Bind(Exclude="FullName")] Person person)
{
    ...
}

或者,您可以使用Include忽略("黑名单")所有属性,而仅包含("白名单")指定的属性:

public ActionResult Edit([Bind(Include="FirstName,LastName,Gender")] Person person)
{
    ...
}

有关 MSDN 的详细信息。

执行此操作时,MVC 模型绑定器将使用请求参数来填充user参数的属性,您可能已经知道。但是,Bind 属性告知模型绑定程序使用指定的名称填充属性。

因此,在这种情况下,只会填充UsernameFullNameEmail属性。所有其他将被忽略。

有关更多详细信息,请参阅此处:http://ittecture.wordpress.com/2009/05/01/tip-of-the-day-199-asp-net-mvc-defining-model-binding-explicitly/

Bind 属性是在创建方案中防止过度发布的一种方法。例如,假设 Student 实体包含一个您不希望此网页设置的 Secret 属性。

public class Student
{
  public int ID { get; set; }
  public string LastName { get; set; }
  public string FirstMidName { get; set; }
  public DateTime EnrollmentDate { get; set; }
  public string Secret { get; set; }
  public virtual ICollection<Enrollment> Enrollments { get; set; }
}

即使您的网页上没有 Secret 字段,黑客也可以使用 fiddler 等工具或编写一些 JavaScript 来发布 Secret 表单值。如果没有 Bind 属性限制模型绑定程序在创建 Student 实例时使用的字段,模型绑定程序将选取该 Secret 表单值并使用它来创建 Student 实体实例。然后,黑客为"秘密表单"字段指定的任何值都将在您的数据库中更新。下图显示了小提琴工具将"机密"字段(值为"OverPost")添加到已发布的表单值。然后,值"OverPost"将成功添加到插入行的 Secret 属性中,尽管您从未希望网页能够设置该属性。

Include 参数与 Bind 属性用于白名单字段是一种安全最佳做法。也可以使用排除参数将要排除的字段列入黑名单。"包含"更安全的原因是,当您向实体添加新属性时,新字段不会自动受"排除"列表的保护。