2014-01-15 27 views
4

我使用ViewModel卡住了。假设我想给一个登录人员一个编辑表单,其中只有一些来自我的Person域模型的字段(也许我想在ViewModel中自定义注释验证)。MVC中ViewModel只使用模型中的几个属性

我被困在控制器的两个独立的地方(我标记为“< < < < >>>”)。

当我将整个Person对象作为属性传递给ViewModel时,我知道该怎么做。我可以让我的代码只更新名称字段,但后来我失去了验证ViewModel中各个属性的能力。如果我将ViewModel中的属性限制为只有几个属性,那么我在GET部分中的代码无法使用vm.Person,因为我没有传递Person。

我扫描了很多关于SO的例子,但他们都使用了AutoMapper。我可以在没有映射器的情况下完成这个任务吗?和/或我该如何编写我自己的?并提前致谢!

Model: 

public class Person() 
{ 
    public int PersonId { get; set; } 
    public string LastName { get; set; } 
    public string FirstName { get; set; } 
    public string MiddleName { get; set; } 
    public string Email { get; set; } 
} 

ViewModel: 

public class LoggedInPersonViewModel() 
{ 
    public int PersonId { get; set; } 
    [Required(ErrorMessage = "Last Name is required")]  
    public string LastName { get; set; } 
    public string FirstName { get; set; } 
} 

Repository: 

public Person GetLoggedInPerson() 
{ 
    var user = HttpContext.Current.User.Identity; 
    var userid = user.GetUserId(); 
    return db.People.SingleOrDefault(i => i.UserId == userid); 
} 

Controller: 

public class RegistrationController : Controller 
{ 
    //Get Logged in User, Edit Form 
    public ActionResult UpdateDetails() 
    { 
     LoggedInPersonViewModel vm = new LoggedInPersonViewModel(); 

     <<<Do I also need a Person property in my ViewModel>>> 

     vm.Person = repository.GetLoggedInPerson(); 
     return View(vm); 
    } 

    //POST 
    [HttpPost] 
    [ValidateAntiForgeryToken] 
    public ActionResult UpdateDetails(LoggedInPersonViewModel loggedinpersonviewmodel) 
    { 

     if (ModelState.IsValid) 
     { 

      <<<what do i do here? is this correct? Again I cannot use Person if not in my VM.>>> 

      //Person person = db.People.Find(loggedinpersonviewmodel.PersonId); 
      //Person.FirstName = loggedinpersonviewmodel.FirstName; 
      //Person.LastName = loggedinpersonviewmodel.LastName; 

      //db.Entry(person).State = EntityState.Modified; 
      db.SaveChanges(); 
      return RedirectToAction("Index", "Person"); 
     } 
     return View(loggedinpersonviewmodel); 
    } 
} 

} 

有没有办法......或者我必须使用AutoMapper来做这件事吗?

回答

4

我想你需要映射LoggedInPersonViewModelPerson。示例

public ActionResult UpdateDetails() 
{ 
    var person = repository.GetLoggedInPerson(); 
    LoggedInPersonViewModel vm = new LoggedInPersonViewModel(); 

    vm.PersonId = person.PersonId; 
    //Rest of properties 
    ... 

    //return view model 
    return View(vm); 
} 

我会推荐AutoMapper这种类型的工作。即AutoMapper是一个简单的小型库,用于解决看似复杂的问题 - 摆脱将一个对象映射到另一个对象的代码。

+0

谢谢,我会试试看。上次我使用AutoMapper的时候,我的整个项目都变得很时髦。我正在使用DBFirst的第一种方法。如果我的课程在EDMX中,Automapper仍然可以工作吗? – SKale

+0

是的。 EDMX产生POCO类,Automapper可以正常工作。 –