【问题标题】:which is the best practices for exposing entity or DTO to view in mvc3?在 mvc3 中公开实体或 DTO 以查看的最佳实践是什么?
【发布时间】:2012-04-06 20:34:04
【问题描述】:

我创建了自己定制的大量架构,包括用于不同技术的 n 层。

目前正在使用 asp.net mvc 框架开发 n 层架构。问题是我在数据访问层有实体框架。由于实体将具有所有关系元数据和导航属性,因此它变得更重。我觉得直接在 mvc 视图上公开这些实体是不明智的。

我更倾向于公开自己定制的实体模型而不是 mvc 视图,哪个更轻。

但这也导致我将数据从原始实体转换为自定义模型的开销。

例如,我有 Employee 实体,它是从实体框架的 edmx 文件生成的。它总共包含 20 个具有所有导航属性的字段。

现在在 mvc 中查看我只需要显示 2 个字段进行编辑。

那么我们是否需要公开原始实体以查看或需要创建这两个字段的 DTO/自定义模型然后公开该视图?

【问题讨论】:

    标签: asp.net-mvc-3 viewmodel


    【解决方案1】:

    我会使用视图模型。我已经学会了不要将我的领域对象暴露给视图,我宁愿将我的领域对象映射到视图模型并将这个视图模型返回给视图。

    这是一个局部视图模型,如果您需要更多的员工数据来创建/编辑或显示,您可能会有更多的属性:

    public class EmployeeViewModel
    {
         public string FirstName { get; set; }
         public string LastName { get; set; }
    }
    

    在我的控制器的操作方法中,它看起来像这样:

    public ActionResult Edit(int id)
    {
         Employee employee = employeeRepository.GetById(id);
    
         // Mapping can be done here by using something like Auto Mapper, but I am
         // manually mapping it here for display purposes
    
         EmployeeViewModel viewModel = new EmployeeViewModel();
         viewModel.FirstName = employee.FirstName;
         viewModel.LastName = employee.LastName;
    
         return View(viewModel);
    }
    

    然后你的视图可能看起来像这样:

    <td>First Name:</td>
    <td>@Html.TextBoxFor(x => x.FirstName, new { maxlength = "15" })
        @Html.ValidationMessageFor(x => x.FirstName)
    </td>
    

    我更喜欢有一个视图模型,它只包含视图所需的员工值。假设您的员工有 20 个属性,而您只需要更新 2 个字段,为什么还要将所有 20 个字段都传递给视图? 只使用你需要的东西。

    【讨论】:

    • 是的,这就是我所相信的。此外,最好不要将完整的实体暴露给查看,而不是只传递你需要的东西。感谢您的回复。
    【解决方案2】:

    你可以暴露原始实体,这没什么不好。但是,一旦您需要有关视图的其他信息,例如您需要 FullName 而不是 Name 和 Lastname,那么您应该创建一个仅包含所需属性的 EmployeeViewModel。您在操作中使用所需的值对其进行初始化,然后将其传递给视图。

    【讨论】:

    • 当我在视图中公开原始实体然后发布我的表单时会发生什么行为? asp.net mvc 框架会尝试从 Request.Form[""] 中搜索原始实体对象中存在的所有字段以获取值吗?
    • 在您的发布操作中,您将拥有 Employee 对象作为参数。默认的 ModelBinder 将尝试绑定所有值。如果你有例如EmployeeId (Int32) 并且您在表单上没有这个值,那么 ModelBinder 将给它它的默认值 = 0。如果您更喜欢 null 那么您需要使 EmployeeId Int32? (可为空)。如果您不想要这种行为,那么您应该创建 EmployeeViewModel,只使用所需的字段将其传递给视图,并将其作为发布操作的参数。然后只会绑定所需的字段。
    猜你喜欢
    • 1970-01-01
    • 2021-07-24
    • 1970-01-01
    • 2010-11-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-19
    • 2019-08-22
    相关资源
    最近更新 更多