zoukankan      html  css  js  c++  java
  • 使用Controller.UpdateModel方法来更新ViewModel

    2011-09-11 13:10 by Fred_Xu, 217 阅读, 0 评论, 收藏, 编辑

    原文(En):http://www.joe-stevens.com/2010/02/17/asp-net-mvc-using-controller-updatemodel-when-using-a-viewmodel/

    在MVC中,更新Model的时候,我们通常使用Controller.UpdateModel方法。我最近在项目中使用了自定义ViewModel,在使用UpdateModel方法的时候无法映射到Post的数据到Model对象里。这个解决方案是一个简单的,但并不像它应该的IntelliSense不拾取方法的重载泛型类型推断时。

    当不使用ViewModel的时候,我可以像这样使用Controller方法:

    public ActionResult Edit(int id)

    {

    Student student = context.Student.FirstOrDefault(s => s.ID.Equals(id));

    return View(student);

    }

    前端View中使用强类型视图:

    <div>

    <%= Html.LabelFor(model => model.Forename) %>

    </div>

    <div>

    <%= Html.TextBoxFor(model => model.Forename)%>

    <%= Html.ValidationMessageFor(model => model.Forename)%>

    </div>

    <div>

    <%= Html.LabelFor(model => model.Surname)%>

    </div>

    <div>

    <%= Html.TextBoxFor(model => model.Surname)%>

    <%= Html.ValidationMessageFor(model => model.Surname)%>

    </div>

    Controller中可以用这样的方法来保存Student数据:

    [HttpPost]

    public ActionResult Edit(int id, FormCollection formValues)

    {

    try

    {

    Student student = context.Student.FirstOrDefault(s => s.ID.Equals(id));

    UpdateModel(student);

    context.SaveChanges();

    return RedirectToAction("Details", new { id = student.ID });

    }

    catch

    {

    throw;

    }

    }

    UpdateModel会遍历formValues集合并且映射post过来的数据到student model对象中。如果我去检查这个集合的Keys,我可以看到formValues匹配了student model的属性,使得映射成功。

    现在来看看如果使用ViewModel会发生什么,这是一个很好的MVC练习。

    下面是一个Student ViewModel的代码示例:

    public class StudentModel

    {

    public Student Student { get; set; }

    public SelectList Titles { get; set; }

    public StudentModel()

    {

    }

    public StudentModel(Student student, IEnumerable<Title> titles)

    {

    Student = student;

    Titles = new SelectList(titles, "ID", "Name", student.TitleID);

    }

    }

    接下来是如何使用ViewModel来编辑的方法:

    public ActionResult Edit(int id)

    {

    Student student = context.Student.FirstOrDefault(s => s.ID.Equals(id));

    return View(new StudentModel(student, context.Title));

    }

    前端View视图页代码:

    <div>

    <%= Html.LabelFor(model => model.Student.Title) %>

    </div>

    <div>

    <%= Html.DropDownListFor(model => model.Student.TitleID, Model.Titles)%>

    </div>

    <div>

    <%= Html.LabelFor(model => model.Student.Forename) %>

    </div>

    <div>

    <%= Html.TextBoxFor(model => model.Student.Forename)%>

    <%= Html.ValidationMessageFor(model => model.Student.Forename)%>

    </div>

    我们设断点来看下这次Post到Edit方法的formValues集合,Keys如图所示:

    可以看到Keys中包含了Student这个Model对象,这是因为ViewModel使用了这个Student Model,但增加了“Student”作为前缀,和前面直接使用Model不一样。如果按照前面的UpdateModel方法,程序会获取不到post过来的值,也会报错。在这里,UpdateModel有重载方法,第二参数是Prefix,也就是"Student"前缀。

    我们这下写这个UpdateModel方法:

    ?

    1

    UpdateModel<Student>(student, "Student");

    你可以看到使用了“Student”作为前缀,映射正确。

    [HttpPost]

    public ActionResult Edit(int id, FormCollection formValues)

    {

    try

    {

    Student student = context.Student.FirstOrDefault(s => s.ID.Equals(id));

    UpdateModel(student, "Student");

    context.SaveChanges();

    return RedirectToAction("Details", new { id = student.ID });

    }

    catch

    {

    throw;

    }

    }

    程序运行成功!

    特别注意:在增加了Prefix后,如果Post过来Form中有不等于Prefix的Name,UpdateModel的时候会报错。一旦增加Prefix前缀后,Post过来的FormCollection必须都含有该前缀对象才可以Work。

    物流,配货,货运,网站,论坛,交流,信息发布
    网站建设QQ:471226865QQ:471226865

  • 相关阅读:
    简单二分求解(木板补漏问题)
    switch语句和for循环
    JAVA运算符和优先级
    JAVA数据类型
    JAVA基础
    JAVA开发环境
    linux配置IP地址
    LVM逻辑分区
    用户和用户组
    第一天
  • 原文地址:https://www.cnblogs.com/suizhikuo/p/2635463.html
Copyright © 2011-2022 走看看