gpt4 book ai didi

c# - MVC 模型绑定(bind)与动态集合

转载 作者:行者123 更新时间:2023-12-03 18:35:15 25 4
gpt4 key购买 nike

根据 Scott Hanselman 关于 ASP.NET Wire Format for Model Binding to Arrays, Lists, Collections, Dictionaries 复杂性的开创性文章:

We read in the properties by looking for parameterName[index].PropertyName
The index must be zero-based and unbroke



所以这个HTML:

<input type="text" name="People[0].FirstName" value="George" />
<input type="text" name="People[1].FirstName" value="Abraham" />
<input type="text" name="People[2].FirstName" value="Thomas" />

这将像这样发布:

Post Data - People%5B0%5D.FirstName=George&People%5B1%5D.FirstName=Abraham&People%5B2%5D.FirstName=Thomas

但是,如果我通过 AJAX 将一个新人加载到我的模型中,我会丢失将该人构建到模型中的上下文并获得以下输出:

<input type="text" name="FirstName" value="New" />

Post Data - People%5B0%5D.FirstName=George&People%5B1%5D.FirstName=Abraham&People%5B2%5D.FirstName=Thomas&FirstName=John

模型活页夹不会拾取它。

: 通过 AJAX 动态添加新元素时,如何保留表达式树?

这是一个 MVCE

型号:/Model/Person.cs

public class PersonViewModel
{
public List<Person> People { get; set; }
}
public class Person
{
public String FirstName { get; set; }
public String LastName { get; set; }
}

Controller :Controllers/PersonController.cs

[HttpGet]
public ActionResult Index()
{
List<Person> people = new List<Person> {
new Person { FirstName = "George" , LastName = "Washington"},
new Person { FirstName = "Abraham" , LastName = "Lincoln"},
new Person { FirstName = "Thomas" , LastName = "Jefferson"},
};
PersonViewModel model = new PersonViewModel() {People = people};
return View(model);
}

[HttpPost]
public ActionResult Index(PersonViewModel model)
{
return View(model);
}

public ActionResult AddPerson(String first, String last)
{
Person newPerson = new Person { FirstName = first, LastName = last };
return PartialView("~/Views/Person/EditorTemplates/Person.cshtml", newPerson);
}

查看:Views/Person/Index.cshtml

@model PersonViewModel

@using (Html.BeginForm()) {
<table id="table">
<thead>
<tr>
<th>@Html.DisplayNameFor(model => model.People.First().FirstName)</th>
<th>@Html.DisplayNameFor(model => model.People.First().LastName)</th>
</tr>
</thead>
<tbody>
@for (int i = 0; i < Model.People.Count; i++)
{
@Html.EditorFor(model => model.People[i])
}
</tbody>
</table>

<input type="button" value="Add Person" id="add"/>
<input type="submit" value="Save" />
}

<script type="text/javascript">

$("#add").click(function() {
var url = "@Url.Action("AddPerson")?" + $.param({ first: "", last: "" });
$.ajax({
type: "GET",
url: url,
success: function(data) {
$("#table tbody").append(data);
}
});
});

</script>

查看:Views/Person/EditorTemplates/Person.cshtml

@model Person

<tr>
<td>@Html.EditorFor(model => model.FirstName)</td>
<td>@Html.EditorFor(model => model.LastName)</td>
</tr>

注意 :删除一个我不想在这里解决的项目时,还有其他复杂性。我只想添加一个元素并知道它与其他属性一起属于嵌套上下文。

最佳答案

您可以install Html.BeginCollectionItem 像这样的实用程序:

PM> Install-Package BeginCollectionItem

然后像这样包装您的收藏项部分 View :

@model Person
<tr>
@using (Html.BeginCollectionItem("people"))
{
<td>@Html.EditorFor(model => model.FirstName)</td>
<td>@Html.EditorFor(model => model.LastName)</td>
}
</tr>

这将生成一个 GUID 驱动的集合,如下所示:

<tr>
<input type="hidden" name="people.index" autocomplete="off"
value="132bfe2c-75e2-4f17-b54b-07e011971d78">
<td><input class="text-box single-line" type="text" value="Abraham"
id="people_132bfe2c-75e2-4f17-b54b-07e011971d78__FirstName"
name="people[132bfe2c-75e2-4f17-b54b-07e011971d78].FirstName"></td>
<td><input class="text-box single-line" type="text" value="Lincoln"
id="people_132bfe2c-75e2-4f17-b54b-07e011971d78__LastName"
name="people[132bfe2c-75e2-4f17-b54b-07e011971d78].LastName"></td>
</tr>

现在我们得到如下所示的已发布表单数据:

Form Data - with GUIDs

这利用了 DefaultModelBinder 允许 非序列索引 作为 explained by Phil Haack :

The good news is that by introducing an extra hidden input, you can allow for arbitrary indices. Just provide a hidden input with the .Index suffix for each item we need to bind to the list. The name of each of these hidden inputs is the same, which will give the model binder a nice collection of indices to look for when binding to the list.



马上,您的模型应该构建得很好,但您也可以添加和删除项目。

进一步阅读
  • A Partial View passing a collection using the Html.BeginCollectionItem helper
  • Submit same Partial View called multiple times data to controller?
  • Model Binding To A List - Phil Haack
  • 关于c# - MVC 模型绑定(bind)与动态集合,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40681707/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com