如何在ASP.NET MVC中保留/保护Edit中的某些字段

时间:2011-09-25 14:53:52

标签: asp.net asp.net-mvc entity-framework

在ASP.NET MVC的“编辑”操作中,可以使用HiddenFieldFor向用户隐藏某些字段。但是,这不会保护字段(例如ID,数据创建日期)不被编辑。

例如,模型学生有字段ID,姓名和生日。我想允许用户更新名称,但不能更新Id或生日。

对于像这样的编辑动作

public ActionResult Edit(Student student)
{
    if (ModelState.IsValid)
    {
        db.Entry(student).State = EntityState.Modified;
        db.SaveChanges();
        return RedirectToAction("Index");
    }
    return View(student);
}

如何防止编辑Id和Birthday?谢谢!

2 个答案:

答案 0 :(得分:11)

您应该使用仅包含要编辑的属性的视图模型:

public class EditStudentViewModel
{
    public string Name { get; set; }
}

然后:

public ActionResult Edit(StudentViewModel student)
{
    ...
}

另一种我不建议的技术是从绑定中排除某些属性:

public ActionResult Edit([Bind(Exclude = "Id,Birthday")]Student student)
{
    ...
}

或包括:

public ActionResult Edit([Bind(Include = "Name")]Student student)
{
    ...
}

答案 1 :(得分:1)

我假设您必须拥有模型中的属性,以便在View中可以使用它们来呈现有用的信息,例如:带有ID或一些只读文本的ActionLink。

在这种情况下,您可以使用显式绑定来定义模型:

[Bind(Include = "Name")]
public class Student
{
    int Id { get; set; }
    int Name { get; set; }
    DateTime Birthday { get; set; }
}

这种方式在更新模型时,如果用户提交额外的ID,则不会绑定。

我喜欢的另一个想法是让你的模型知道每个场景的绑定并让它们经过编译验证:

public class ModelExpression<T>
{
    public string GetExpressionText<TResult>(Expression<Func<T, TResult>> expression)
    {
        return ExpressionHelper.GetExpressionText(expression);
    }
}

public class Student
{
    public static string[] EditBinding = GetEditBinding().ToArray();

    int Id { get; set; }
    int Name { get; set; }
    DateTime Birthday { get; set; }

    static IEnumerable<string> GetEditBinding()
    {
        ModelExpression<Student> modelExpression = new ModelExpression<Student>();
        yield return modelExpression.GetExpressionText(s => s.Name);
    }
}

这种方式在您调用TryUpdateModel时的Action中,您可以传递此信息。