ASP.NET MVC 中的模型关系

问题描述 投票:0回答:3

我最近开始评估 ASP.NET MVC。虽然为仅具有原始属性的模型创建控制器和视图非常简单快捷(如官方页面的入门视频所示),但我没有找到任何处理复杂类型引用的好方法。假设我有这些模型:

public class Customer {  
    public int Id { get; set; }  
    public string Name { get; set; }  
    public Address Address { get; set; }  
    public IList<Order> Orders { get; set; }  
}

public class Address {  
    public int Id { get; set; }  
    public string .....  
    .....  
}

public class Order {  
    public int Id { get; set; }  
    public Customer Customer { get; set; }  
    public string OrderName { get; set; }  
    .....  
}

请注意,我在模型中没有外键(就像典型的 LINQ to SQL,示例视频中也使用了外键),但有对象引用。

如何在 ASP.NET MVC 中处理此类引用?有人有关于这个问题的一些好的提示或教程链接吗?也许包括复杂类型的自动绑定。

c# .net asp.net-mvc model entity-relationship
3个回答
3
投票

您可以使用数据传输对象来解决此问题,也可以在实体上使用扩展方法 - 在 EF 中包含方法 -

与原始属性没有什么不同。如果那不是你的意思,请纠正我,然后我会再次帮助你

谢谢

DTO:

public class OrderDTO
{
    public int Id { get; set; }
    public int CustomerId { get; set; }
    public string CustomerName { get; set; }
}

NHibernate 存储库:

public IList<OrderDTO> GetOrders()
{
    return Session.Linq<Order>()
                    .Select(o => new OrderDTO {
                                        Id = o.Id
                                        CustomerId = o.Customer.Id
                                        CustomerName = o.Customer.Name
                                        ...
                    }).ToList();
}

查看:

展开 - 包含 - 模型类型为“订单”:

<%= Model.Customer.Name %>

使用 DTO - 模型类型为“OrderDTO”:

<%= Model.CustomerName %>

编辑:

好吧,首先您可能想使用 FormViewModel 进行创建/编辑操作。像这样;

控制器:

public ActionResult Edit(int id)
{
    Order order = null; // OrderService.Get(id);
    IList<Customer> customers = null; // CustomerService.GetAll();

    OrderFormViewModel model = OrderFormViewModel.Create(order);
    model.Customers = customers.Select(c => new SelectListItem {
        Value = c.Id,
        Text = c.Name
    });

    return View(model);
}

[HttpPost]
public ActionResult Edit(int customerId, Order order)
{
    //customerId - selected from dropdown.
}

public class OrderFormViewModel
{
    public static OrderFormViewModel Create(Order order)
    {
        return new OrderFormViewModel {
            Order = order
        };
    }

    public Order Order { get; internal set; }
    public IEnumerable<SelectListItem> Customers { get; internal set; }
    public int CustomerId { get; internal set; }
}

查看:

<%= Html.DropDownListFor(o => o.CustomerId, Model.Customers) %>

1
投票

我会将所有内容合并到我的视图模型中:

CustomerViewModel.Customer
CustomerViewModel.Address
CustomerViewModel.Orders // maybe an IEnumerable<Order>
CustomerViewMode.CurrentOrder

您应该能够使用一些输入助手来绑定复杂的对象,而不会遇到太多麻烦:

//.. begin form
<%=Html.HiddenFor(m=>m.Customer.Id)%>
<%=Html.TextboxFor(m=>m.Customer.FirstName)%>
<%=Html.TextBoxFor(m=>m.Address.City)%>
<%=Html.TextBoxFor(m=>m.ActiveOrder.OrderName%>
//.. submit ..
//.. end form ..

如果你的操作方法如下所示,应该可以绑定回来:

[HttpPost]
public ActionResult UpdateComplexObject(string id, CustomerViewModel customerViewModel) {
// if (!id.Equals(customerViewModel.Customer.Id) throw something
// just one of my own conventions to ensure that I am working on the correct active
// entity - string id is bound from the route rules.
ValidateModel(customerViewModel);
service.UpdateCustomer(customerViewModel.Customer);
serviceOrder.UpdateOrder(customerViewModel.ActiveOrder);
serviceAddress.UpdateAddress(customerViewModel.Address);
return RedirectToAction("DisplayComplexObject"); // or whatever
}

哈尔


1
投票

我更喜欢让我的视图尽可能“哑”,所以我喜欢创建用于绑定的自定义视图模型。

在控制器中,您可以将丰富的域对象映射到视图模型的扁平模型。例如:

public class ChooseCustomerModel {

    public Order Order { get; set; }

    // Project Customer objects into this container, which is easy to bind to
    public IDictionary<int, string> PotentialCustomers { get; set; }
}

如果您正在寻找有关此主题的好材料,我推荐 ASP.NET MVC 视图模型模式

© www.soinside.com 2019 - 2024. All rights reserved.