c# - 将任何字段前缀绑定(bind)到 C# MVC 4/5 中的操作参数

标签 c# asp.net-mvc model-view-controller

我正在使用 C# ASP.Net MVC 4 和 MVC 5。

我使用聚合模型 VmVehicleGroup,它看起来有点像:

public class VmVehicleGroup {
    public VehicleTypeEnum Type { get; set; }
    public List<VmVehicle> Vehicles { get; set; }
    public VmVehicle Editable { get; set;}
}

主视图对每个组都有局部 View ,例如,

@Html.Partial(x => x.Cars, "_VehicleEditor")

@Html.Partial(x => x.Bus, "_VehicleEditor")

@Html.Partial(x => x.Truck, "_VehicleEditor")

每个组部分显示 Model.Vehicles 并为 Model.Editable 提供一个编辑器模板

我的问题来自 ModelState。每个部分将为 Model.Editable 呈现相同的输入字段名称/ID。当存在 ModelState 验证错误时,“Car”部分的验证错误将出现在所有其他表单上,而不仅仅是 Car。我通过在编辑器 paritial 中为模型添加前缀来解决这个问题,例如:

ViewData.TemplateInfo.HtmlFieldPrefix = Model.Type.ToString(); // VehicleTypeEnum

添加/编辑表单现在将提交带有字段发布数据前缀的 Model.Editable,即:Car.Reg、Car.Name、Car.Type 和 Car.Id。我的问题出现在 MVC 操作上。我的操作目前看起来像这样:

[ValidateAntiForgeryToken]
[AcceptVerbs(HttpVerbs.Post)]
[Route("Edit", Name = "EditVehicle")]
public ActionResult Edit([Bind(Prefix = "Car")] VmVehicle car, [Bind(Prefix = "Bus")] VmVehicle bus, [Bind(Prefix = "Truck")] VmVehicle truck, ....)
{
    var model = car ?? bus ?? truck;

    ...
}

我的问题是,这是维护方面的噩梦——对于每个 VehicleTypeEnum,我都需要添加额外的绑定(bind)参数。我不能对带前缀的模型执行单个操作。

我试过使用 public ActionResult Edit(VmVehicle model) {},但前缀阻碍了 MVC 绑定(bind)。不幸的是,MVC 似乎也不允许您绑定(bind)通配符或以逗号分隔的前缀,即:*.Car 或 Car,Bus,Truck。

是否可以鼓励 MVC 操作接受任何前缀,同时为 ModelState 验证错误保留前缀?

最佳答案

我发现在您看来,您对不同类型的车辆有不同的偏爱。这意味着您事先知道有哪些不同的车辆类型。

如您所知,您只需在创建 View 模型时对组进行分离即可。 IE。创建一个 View 模型,其中包含汽车、卡车、公共(public)汽车的不同列表...这样您就可以在客户端获得所需的前缀。

帖子操作怎么样?好吧,不是接收列表作为单独的参数,而是接收一个类似于您用来呈现编辑器的类,即

使用具有此属性的类来创建编辑器(将其用作您的 View 模型):

public class VehiclesViewModel
{
  public List<Vehicle> Cars { get; set;}
  public List<Vehicle> Buses { get; set;}
  // other stuff here!
}

如果你使用像这样的类,它也有汽车、公共(public)汽车等列表,数据将自动绑定(bind),即插入使用:

public ActionResult Edit([Bind(Prefix = "Car")] VmVehicle car, 
     [Bind(Prefix = "Bus")] VmVehicle bus, ...)

使用这样的 Action :

public ActionResult Edit(VehiclesViewModel vehicles)

模型绑定(bind)器将为您处理前缀,并将每辆车绑定(bind)到其对应的列表。

显示和编辑模板

但是,如果您为每种类型的车辆使用不同的类,您可以使用自定义显示和编辑模板,这可以让您的生活更轻松。 IE。您可以定义适用于给定数据类型的显示和编辑模板。因此,如果您对每种车辆都有不同的类别,您可以为每个不同的类别使用显示和编辑模板,并使用“DisplayFor”或 EditorFor,您将自动获得所需的 View 。此链接中的一些示例:

(我不明白你到底在做什么,所以我可以对此给出更具体的解释)

绑定(bind)复杂对象列表的模型

人们在 MVC 中发现的另一个经典问题是,当他们想要绑定(bind)一个必须编辑的复杂对象列表时,他们不知道如何去做才能在服务器中取回对象列表在后期 Action 中。

explanation by Phil Haack是您能找到的最好的之一。

关于c# - 将任何字段前缀绑定(bind)到 C# MVC 4/5 中的操作参数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24777582/

相关文章:

c# - 从 CSV 文件中删除空行和空列 - C#

c# - 如何强制 WPF 启动窗口到特定屏幕?

jquery - 如何通过 View 中的 Json 访问 Controller 值并在 jquery 中循环?

java - 从文本字段中提取空数据。表已填充,但无法检索对象。 Java/JavaFX

c# - 带有匿名方法的 EventHandler 是如何工作的?

c# - 如何默认生成类型为 'Text' 而不是 'General' 的 Excel 文件

javascript - 从 Razor 调用的 javascript 中的分离函数

c# - 代码块内的 MVC Razor 括号

将 mvc_pattern 库更新到最新版本 6.4.0 后,Flutter 获取上下文时出错

java - 关于为什么使用 jsp :include tag into another jsp isn't working in this scenario? 传递对象的任何原因