MVC中BeginForm提交后GeneralViewModel.Customers为null问题求助
解决ASP.NET MVC通用视图表单提交时列表模型绑定为null的问题
问题原因
当前视图中的<input>标签没有设置符合MVC模型绑定规则的name属性,导致表单提交时,框架无法识别字段与GeneralViewModel中列表属性的对应关系,最终Customers属性为null。
MVC模型绑定识别列表的命名规则为:列表属性名[索引].实体属性名,例如Customers[0].CustomerID、Customers[0].CustomerName。
解决方案
修改视图代码,动态生成符合规则的name属性,同时保留通用型设计:
修改后的视图核心代码
@model MVC.Models.GeneralViewModel @{ ViewBag.Title = "Index"; Layout = "~/Views/Shared/_Layout.cshtml"; } @section Styles { <link href="@Url.Content("~/Content/Home.css")" rel="stylesheet" type="text/css" /> } @{ var generalProps = Model.GetType().GetProperties(); } <div class="container"> <h2>Index</h2> @using (Html.BeginForm("Export", "Home", FormMethod.Post)) { <input type="submit" value="Export" /> <button type="button">Import</button> <button type="button">Approve Changes</button> <table> @foreach (var generalProp in generalProps) { var itemList = (System.Collections.IList)generalProp.GetValue(Model); if (itemList == null || itemList.Count == 0) continue; var entityType = itemList[0].GetType(); var entityProps = entityType.GetProperties(); <!-- 表头 --> <tr> @foreach (var prop in entityProps) { var displayNameAttr = (System.ComponentModel.DisplayNameAttribute)Attribute.GetCustomAttribute(prop, typeof(System.ComponentModel.DisplayNameAttribute)); <th>@(displayNameAttr != null ? displayNameAttr.DisplayName : prop.Name)</th> } </tr> <!-- 表体:生成带正确name的input --> @for (int i = 0; i < itemList.Count; i++) { <tr> @foreach (var prop in entityProps) { var fieldValue = prop.GetValue(itemList[i], null); // 拼接符合模型绑定规则的name属性:列表属性名[索引].实体属性名 var inputName = $"{generalProp.Name}[{i}].{prop.Name}"; <td> <input type="text" name="@inputName" value="@fieldValue" readonly /> </td> } </tr> } } </table> } </div>
关键修改点说明
- 移除表单路由参数
new { app = @Model }:该参数会生成冗余的URL查询字符串,对模型绑定无帮助。 - 为非提交按钮添加
type="button":避免点击Import或Approve Changes时意外触发表单提交。 - 动态生成
name属性:通过$"{generalProp.Name}[{i}].{prop.Name}"拼接出符合MVC模型绑定要求的字段名,确保框架能正确识别列表中的每个实体及其属性。 - 增加空值判断:避免
itemList为null时抛出异常。
验证效果
修改后提交表单,控制器的Export方法中table.Customers将正确接收到列表数据,不再为null。
内容的提问来源于stack exchange,提问作者Manib
相关产品推荐
相关产品推荐

