【问题标题】:Display model in View在视图中显示模型
【发布时间】:2013-12-10 19:20:37
【问题描述】:

我是 MVC 新手,但我真的想获得一些使用 MVC 的经验,所以我正在尝试使用 MVC 重新创建一个 Asp Classic 项目。下面的代码不显示与膳食/索引页面上的菜单关联的膳食列表。

我已经阅读了几种不同的模式,ninject 和 auto mapper 然而,据我所知,在处理简单的关联时没有必要这样做。

我只想将餐食添加到菜单并汇总每个菜单的餐食价格。

型号:

public class Meal
{   [Key]
    public int MealId { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }
    public decimal Price { get; set; }
    public int MenuId { get; set; }
}


public class Menu
{
    [Key]
    public int MenuId { get; set; }
    public DateTime WeekendServed { get; set; }
    public decimal Price { get; set; }
    public List<Model> Meals { get; set; //Menus have meals. 
}

菜单控制器:

 public ViewResult Index()
 {
    return View(unitOfWork.MenuRepository.Get());
 }

Menu/Index/:

@model IEnumerable<Skimos.Models.Meal>
----

<Table Headers>

@foreach (var item in Model) {
    <tr>
        <td>
            @Html.DisplayFor(modelItem => item.WeekendServed)
        </td>
        <td>
            @Html.DisplayFor(modelItem => item.Price)
        </td>
        <td>
            @foreach (var meal in item.Meals)
            {
                @Html.Display(meal.Name)
                @Html.Display(meal.Description)
                @Html.Display(meal.Price.ToString())
            }
        </td>
        <td>
            @Html.ActionLink("Edit", "Edit", new { id=item.MenuId }) |
            @Html.ActionLink("Details", "Details", new { id=item.MenuId }) |
            @Html.ActionLink("Delete", "Delete", new { id=item.MenuId })
        </td>
    </tr>
}

MenuRepository public IQueryable Menus { get { return context.Menus; } } 编辑:

【问题讨论】:

  • 你能显示unitOfWork.MenuRepository.Get() 的代码吗?另外,视图的强类型是什么?
  • 不要围绕实体框架实现存储库/工作单元模式。 EF已经采用这种模式(DbContext 是你的 UoW,你的 DbSets 是你的存储库)。如果您想抽象出使用 EF 的逻辑(这是一个好主意),那么请实现类似服务模式的东西。
  • @ChrisPratt 有关如何在 EF 中集成服务模式的任何链接? , EF by provind DBSet 和 DBContext 为您提供了如何更好地控制开发人员不允许向某些 dbsets 添加对象、不允许对 DBSet 进行某些操作的所有内容?
  • 服务模式是通用的:你可以找到比我在网上其他地方提供的更好的解释。不过,一般的想法是,您将选择逻辑包装到服务上的方法中。例如,如果你想做一些事情,比如获取上个月发布的所有帖子,在你的控制器中,你只需调用myService.GetPublishedPostsForLastMonth() 之类的东西,并在该方法中执行所有 EF 调用。当然,对于这样的事情,您可能想要创建一个稍微通用的方法来处理不同的月份,但您明白了。

标签: asp.net asp.net-mvc entity-framework code-first asp.net-mvc-5


【解决方案1】:

问题在于 EF 需要两个列表类型导航属性:1)ICollection 类型和 2)virtual 属性:

因此,如果您将Meals 属性更改为以下内容,您应该会很好:

public virtual ICollection<Meal> Meals { get; set; }

ICollection 的原因是 EF 的返回值将是 IQueryable 类型。虚拟的原因是 EF 实际上返回的是代理类而不是实际的模型类。这些代理对返回数据集的导航属性具有覆盖。如果你的属性不是虚拟的,EF 不能覆盖它。

【讨论】:

  • 我之前可能没有问过正确的问题。我什至从来没有考虑过尝试使用包含菜单的构造函数对 Meal 类进行建模……这个 EF 是否实现了 IoC?如果您能提供一些关于我如何“修复/破解”解决我遇到的问题的方法的见解,我很乐意选择您的答案是正确的。感谢收听。
  • 我不确定你在说什么。但是,您的“修复”是非常糟糕的设计。也就是说,你有 6 个独立的 Menu 导航属性,6 个不同的外键到 Meal 上的 Menu。如果你只吃 6 顿饭也没关系,因为这很明显是一种 M2M 关系,应该这样建模。如果明天,你实际上需要 7 顿饭怎么办。现在你必须打开类来添加另一个类,你已经打破了开闭原则。如果你发现自己在做Something1, Something2, Something3, ...你做错了
  • 我了解,我已将其从我的解决方案和此页面中删除。感谢您的意见。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-17
  • 1970-01-01
  • 1970-01-01
  • 2013-05-15
  • 1970-01-01
相关资源
最近更新 更多