我有一个大型实体(组织),我已经将一些字段划分为单独的视图,其中一个较小的字段子集具有多个ViewModel。如果用户以后需要更新这些字段,我也想使用这些相同的视图。
我对如何填充数据感到困惑。例如,我(可能是愚蠢地)认为如果我使用整个实体填充Get,那么将自动填充字段 - 就像我使用与整个实体关联的编辑视图一样。
有人能告诉我ViewModels是不是应该以这种方式使用,还是我只是不考虑明显的事情?
这是我当前的Get / Post基于我(可能很差)的假设。 CompanyInfo是组织内的字段的子集。这给了我令人沮丧的“动态代理”错误。
// GET: /Organization/CompanyInfo
public ActionResult CompanyInfo(ManageMessageId? message)
{
ViewBag.StatusMessage =
message == ManageMessageId.ConfirmEmail ? "Please confirm your email address to log in again." : "";
var member = GetUserMember();
var org = db.Organizations.Single(x => x.OrgId == member.OrgId);
return View(org);
}
//
// POST: /Organization/CompanyInfo
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<ActionResult> CompanyInfo(CompanyInfoViewModel model)
{
if (ModelState.IsValid)
{
var member = GetUserMember();
var org = await db.Organizations.SingleAsync(x => x.OrgId == member.OrgId);
org.StreetAddress = model.StreetAddress;
org.Suite = model.Suite;
org.City = model.City;
org.State = model.State;
org.Zip = model.Zip;
org.Country = model.Country;
db.Entry(org).State = EntityState.Modified;
db.SaveChanges();
return RedirectToAction("CompanyInfo", "Organization");
}
return View();
}
答案 0 :(得分:0)
在ASP.NET MVC中拥有一个ViewModel的唯一真正问题是,当您将其发回时,您不知道View已填充了哪些属性,因为正如您所说,您只是在各种视图上填充它们的子集。理想情况下你应该遵循的模式是每个View都有一个ViewModel(并且正如这篇文章的第一条评论所说,你应该将它传递给你的View,而不是你的模型)。
您使用内置注释验证肯定会发现有问题,因为每个View都会有不同的验证要求,因为它们处理的是实体的不同部分。
另外我想提一下,当我们在ASP.NET MVC中讨论ViewModel时,我们不是在基于XAML的UI框架中讨论与ViewModel相同的东西,甚至是像Knockout这样的JavaScript库。或者Angular 2.这些ViewModel可以在视图甚至应用程序之间共享,因为它们存在于客户端上:这就是可以在消费时针对View执行业务逻辑。
答案 1 :(得分:0)
您的问题是,CompanyInfo(ManageMessageId? message)
操作方法返回db.Organizations.Single(x => x.OrgId == member.OrgId)
,我打赌的类型为Organization
(或其他),但肯定不是类型CompanyInfoViewModel
。
您应该做的是在CompanyInfoViewModel
对象数据中的第一个方法中构建org
。
____ViewModel
个动作命名View
,____EditModel
动作命名Edit
等等。他们不是只是< / em> ViewModel
个对象,它们也用于其他操作。 (有时我们有真正复杂的事情需要他们自己的DTO。)