C# 对下拉列表的验证已中断
这与从两个下拉列表向局部视图传递模型数据有关,用户必须在视图中选择部门和年份。然后,数字数据显示在局部视图的表格中。该视图包含下拉列表和表格标题。局部视图包含包含数字数据的行。现在,验证失败了。这两个下拉列表都是必需的。如果在未选择下拉列表的情况下提交表单,则会出现以下错误:C# 对下拉列表的验证已中断,c#,asp.net,asp.net-mvc,asp.net-mvc-5,C#,Asp.net,Asp.net Mvc,Asp.net Mvc 5,这与从两个下拉列表向局部视图传递模型数据有关,用户必须在视图中选择部门和年份。然后,数字数据显示在局部视图的表格中。该视图包含下拉列表和表格标题。局部视图包含包含数字数据的行。现在,验证失败了。这两个下拉列表都是必需的。如果在未选择下拉列表的情况下提交表单,则会出现以下错误: There is no ViewData item of type 'IEnumerable<SelectListItem>' that has the key 'SelectedDepartment' 当它
There is no ViewData item of type 'IEnumerable<SelectListItem>' that has
the key 'SelectedDepartment'
当它击中控制器时,模型状态无效
查看:
@model BudgetDemo.Models.BudgetsActualsViewModel
@using (Html.BeginForm("GetBudgetsActuals", "BudgetsActuals", FormMethod.Post))
{
@Html.AntiForgeryToken()
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="col-md-6">
<div class="form-group">
@Html.DropDownListFor(m => m.SelectedDepartment, Model.Departments,
"Select Department", new { @class = "form-control" })
@Html.ValidationMessageFor(model => model.SelectedDepartment, "",
new { @class = "text-danger" })
</div>
</div>
<div class="col-md-6">
<div class="form-group">
@Html.DropDownListFor(m => m.SelectedYear, Model.Years, "Select Year",
new { @class = "form-control" })
@Html.ValidationMessageFor(model => model.SelectedYear, "",
new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-lg-7">
<input type="submit" value="Submit" class="btn btn-info" />
</div>
</div>
@if (Model.SelectedDepartment != null && Model.SelectedYear != null)
{
// table headers, etc
@if (Model != null)
{
Html.RenderPartial("_BudgetsActuals", Model.BudgetActualCollection);
}
}
}
public class BudgetsActualsViewModel
{
// Cost Center / Department Drop Down
[Display(Name = "Cost Center/Department")]
[Required(ErrorMessage = "Cost Center/Department is required.")]
[StringLength(62)]
public string SelectedDepartment { get; set; }
public List<SelectListItem> Departments { get; set; }
// Year Drop Down
[Display(Name = "Year")]
[Required(ErrorMessage = "Year is required.")]
public string SelectedYear { get; set; }
public List<SelectListItem> Years { get; set; }
// Account and Name fields
[Display(Name = "Account")]
[StringLength(9)]
public string Account { get; set; }
[Display(Name = "Name")]
[StringLength(12)]
public string CostCenter { get; set; }
// Seven calculated fields: Oct Actual, Oct Budget, YTD Actual, YTD
// Budget, YTD Variance, Est To Complete, Est at Complete
[Display(Name = "TotalCurrentMonthActualConversion",
ResourceType = typeof(DynamicDisplayAttributeNames))]
public int TotalCurrentMonthActual { get; set; }
[Display(Name = "TotalCurrentMonthBudgetConversion",
ResourceType = typeof(DynamicDisplayAttributeNames))]
public int TotalCurrentMonthBudget { get; set; }
[Display(Name = "YTD Actual", AutoGenerateFilter = false)]
public int TotalYTDActual { get; set; }
[Display(Name = "YTD Budget", AutoGenerateFilter = false)]
public int TotalYTDBudget { get; set; }
[Display(Name = "YTD Variance", AutoGenerateFilter = false)]
public int TotalVariance { get; set; }
[Display(Name = "Est to Complete", AutoGenerateFilter = false)]
public int TotalETCBudget { get; set; }
[Display(Name = "Est at Complete", AutoGenerateFilter = false)]
public int TotalEAC { get; set; }
}
public class DynamicDisplayAttributeNames
{
public static string TotalCurrentMonthActualConversion { get; set; }
= DateTime.Now.AddMonths(-1).ToString("MMM") + " Actual";
public static string TotalCurrentMonthBudgetConversion { get; set; }
= DateTime.Now.AddMonths(-1).ToString("MMM") + " Budget";
}
// POST: Grab data for department and year
[HttpPost]
public ActionResult GetBudgetsActuals(BudgetsActualsViewModel model)
{
try
{
if (ModelState.IsValid)
{
var repo = new BudgetDemoRepository();
ModelState.Clear();
model.Departments = repo.GetBudgetsActuals().Departments;
model.Years = repo.GetBudgetsActuals().Years;
model.BudgetActualCollection = repo.GetBudgetsActualsData(model);
}
else
{
// Execution gets to here before returning to view
model.BudgetActualCollection = new
List<BudgetDemo.Models.BudgetsActualsViewModel>();
}
return View(model);
}
catch
{
return View("Error");
}
}
@model BudgetDemo.Models.BudgetsActualsViewModel
@使用(Html.BeginForm(“GetBudgetActuals”,“BudgetActuals”,FormMethod.Post))
{
@Html.AntiForgeryToken()
@Html.ValidationSummary(true,“,new{@class=“text danger”})
@Html.DropDownListFor(m=>m.SelectedDepartment,Model.Departments,
“选择部门”,新建{@class=“表单控制”})
@Html.ValidationMessageFor(model=>model.SelectedDepartment,“,
新建{@class=“text danger”})
@DropDownListFor(m=>m.SelectedYear,Model.Years,“选择年份”,
新的{@class=“表单控制”})
@Html.ValidationMessageFor(model=>model.SelectedYear,“,
新建{@class=“text danger”})
@如果(Model.SelectedDepartment!=null&&Model.SelectedYear!=null)
{
//表格标题等
@如果(型号!=null)
{
RenderPartial(“_BudgetActuals”,Model.BudgetTualCollection);
}
}
}
型号:
@model BudgetDemo.Models.BudgetsActualsViewModel
@using (Html.BeginForm("GetBudgetsActuals", "BudgetsActuals", FormMethod.Post))
{
@Html.AntiForgeryToken()
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="col-md-6">
<div class="form-group">
@Html.DropDownListFor(m => m.SelectedDepartment, Model.Departments,
"Select Department", new { @class = "form-control" })
@Html.ValidationMessageFor(model => model.SelectedDepartment, "",
new { @class = "text-danger" })
</div>
</div>
<div class="col-md-6">
<div class="form-group">
@Html.DropDownListFor(m => m.SelectedYear, Model.Years, "Select Year",
new { @class = "form-control" })
@Html.ValidationMessageFor(model => model.SelectedYear, "",
new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-lg-7">
<input type="submit" value="Submit" class="btn btn-info" />
</div>
</div>
@if (Model.SelectedDepartment != null && Model.SelectedYear != null)
{
// table headers, etc
@if (Model != null)
{
Html.RenderPartial("_BudgetsActuals", Model.BudgetActualCollection);
}
}
}
public class BudgetsActualsViewModel
{
// Cost Center / Department Drop Down
[Display(Name = "Cost Center/Department")]
[Required(ErrorMessage = "Cost Center/Department is required.")]
[StringLength(62)]
public string SelectedDepartment { get; set; }
public List<SelectListItem> Departments { get; set; }
// Year Drop Down
[Display(Name = "Year")]
[Required(ErrorMessage = "Year is required.")]
public string SelectedYear { get; set; }
public List<SelectListItem> Years { get; set; }
// Account and Name fields
[Display(Name = "Account")]
[StringLength(9)]
public string Account { get; set; }
[Display(Name = "Name")]
[StringLength(12)]
public string CostCenter { get; set; }
// Seven calculated fields: Oct Actual, Oct Budget, YTD Actual, YTD
// Budget, YTD Variance, Est To Complete, Est at Complete
[Display(Name = "TotalCurrentMonthActualConversion",
ResourceType = typeof(DynamicDisplayAttributeNames))]
public int TotalCurrentMonthActual { get; set; }
[Display(Name = "TotalCurrentMonthBudgetConversion",
ResourceType = typeof(DynamicDisplayAttributeNames))]
public int TotalCurrentMonthBudget { get; set; }
[Display(Name = "YTD Actual", AutoGenerateFilter = false)]
public int TotalYTDActual { get; set; }
[Display(Name = "YTD Budget", AutoGenerateFilter = false)]
public int TotalYTDBudget { get; set; }
[Display(Name = "YTD Variance", AutoGenerateFilter = false)]
public int TotalVariance { get; set; }
[Display(Name = "Est to Complete", AutoGenerateFilter = false)]
public int TotalETCBudget { get; set; }
[Display(Name = "Est at Complete", AutoGenerateFilter = false)]
public int TotalEAC { get; set; }
}
public class DynamicDisplayAttributeNames
{
public static string TotalCurrentMonthActualConversion { get; set; }
= DateTime.Now.AddMonths(-1).ToString("MMM") + " Actual";
public static string TotalCurrentMonthBudgetConversion { get; set; }
= DateTime.Now.AddMonths(-1).ToString("MMM") + " Budget";
}
// POST: Grab data for department and year
[HttpPost]
public ActionResult GetBudgetsActuals(BudgetsActualsViewModel model)
{
try
{
if (ModelState.IsValid)
{
var repo = new BudgetDemoRepository();
ModelState.Clear();
model.Departments = repo.GetBudgetsActuals().Departments;
model.Years = repo.GetBudgetsActuals().Years;
model.BudgetActualCollection = repo.GetBudgetsActualsData(model);
}
else
{
// Execution gets to here before returning to view
model.BudgetActualCollection = new
List<BudgetDemo.Models.BudgetsActualsViewModel>();
}
return View(model);
}
catch
{
return View("Error");
}
}
公共类BudgetActualViewModel
{
//成本中心/部门下拉列表
[显示(Name=“成本中心/部门”)]
[必需(ErrorMessage=“需要成本中心/部门”)]
[行政长官(62)]
公共字符串SelectedDepartment{get;set;}
公共列表部门{get;set;}
//年份下拉列表
[显示(Name=“Year”)]
[必需(ErrorMessage=“需要年份”)]
公共字符串SelectedYear{get;set;}
公共列表年份{get;set;}
//帐户和名称字段
[显示(Name=“Account”)]
[第(9)条]
公共字符串帐户{get;set;}
[显示(Name=“Name”)]
[条次建议修正案(12)]
公共字符串成本中心{get;set;}
//七个计算字段:十月实际、十月预算、年初至今实际、年初至今
//预算,年初至今差异,预计完工时间,预计完工时间
[显示(Name=“TotalCurrentMonthActualConversion”,
ResourceType=typeof(DynamicDisplayAttributeNames))]
公共int TotalCurrentMonthActual{get;set;}
[显示(Name=“TotalCurrentMonthBudgetConversion”,
ResourceType=typeof(DynamicDisplayAttributeNames))]
公共int TotalCurrentMonthBudget{get;set;}
[显示(Name=“YTD实际”,AutoGenerateFilter=false)]
公共整数TotalYTDActual{get;set;}
[显示(Name=“年初至今预算”,AutoGenerateFilter=false)]
公共整数TotalYTDBudget{get;set;}
[显示(Name=“YTD方差”,AutoGenerateFilter=false)]
公共整数总方差{get;set;}
[显示(Name=“Est to Complete”,AutoGenerateFilter=false)]
public int TotalETCBudget{get;set;}
[显示(Name=“Est at Complete”,AutoGenerateFilter=false)]
公共整数TotalEAC{get;set;}
}
公共类DynamicDisplayAttributeName
{
公共静态字符串TotalCurrentMonthActualConversion{get;set;}
=DateTime.Now.AddMonths(-1).ToString(“MMM”)+实际值;
公共静态字符串TotalCurrentMonthBudgetConversion{get;set;}
=DateTime.Now.AddMonths(-1).ToString(“MMM”)+“Budget”;
}
控制器:
@model BudgetDemo.Models.BudgetsActualsViewModel
@using (Html.BeginForm("GetBudgetsActuals", "BudgetsActuals", FormMethod.Post))
{
@Html.AntiForgeryToken()
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="col-md-6">
<div class="form-group">
@Html.DropDownListFor(m => m.SelectedDepartment, Model.Departments,
"Select Department", new { @class = "form-control" })
@Html.ValidationMessageFor(model => model.SelectedDepartment, "",
new { @class = "text-danger" })
</div>
</div>
<div class="col-md-6">
<div class="form-group">
@Html.DropDownListFor(m => m.SelectedYear, Model.Years, "Select Year",
new { @class = "form-control" })
@Html.ValidationMessageFor(model => model.SelectedYear, "",
new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-lg-7">
<input type="submit" value="Submit" class="btn btn-info" />
</div>
</div>
@if (Model.SelectedDepartment != null && Model.SelectedYear != null)
{
// table headers, etc
@if (Model != null)
{
Html.RenderPartial("_BudgetsActuals", Model.BudgetActualCollection);
}
}
}
public class BudgetsActualsViewModel
{
// Cost Center / Department Drop Down
[Display(Name = "Cost Center/Department")]
[Required(ErrorMessage = "Cost Center/Department is required.")]
[StringLength(62)]
public string SelectedDepartment { get; set; }
public List<SelectListItem> Departments { get; set; }
// Year Drop Down
[Display(Name = "Year")]
[Required(ErrorMessage = "Year is required.")]
public string SelectedYear { get; set; }
public List<SelectListItem> Years { get; set; }
// Account and Name fields
[Display(Name = "Account")]
[StringLength(9)]
public string Account { get; set; }
[Display(Name = "Name")]
[StringLength(12)]
public string CostCenter { get; set; }
// Seven calculated fields: Oct Actual, Oct Budget, YTD Actual, YTD
// Budget, YTD Variance, Est To Complete, Est at Complete
[Display(Name = "TotalCurrentMonthActualConversion",
ResourceType = typeof(DynamicDisplayAttributeNames))]
public int TotalCurrentMonthActual { get; set; }
[Display(Name = "TotalCurrentMonthBudgetConversion",
ResourceType = typeof(DynamicDisplayAttributeNames))]
public int TotalCurrentMonthBudget { get; set; }
[Display(Name = "YTD Actual", AutoGenerateFilter = false)]
public int TotalYTDActual { get; set; }
[Display(Name = "YTD Budget", AutoGenerateFilter = false)]
public int TotalYTDBudget { get; set; }
[Display(Name = "YTD Variance", AutoGenerateFilter = false)]
public int TotalVariance { get; set; }
[Display(Name = "Est to Complete", AutoGenerateFilter = false)]
public int TotalETCBudget { get; set; }
[Display(Name = "Est at Complete", AutoGenerateFilter = false)]
public int TotalEAC { get; set; }
}
public class DynamicDisplayAttributeNames
{
public static string TotalCurrentMonthActualConversion { get; set; }
= DateTime.Now.AddMonths(-1).ToString("MMM") + " Actual";
public static string TotalCurrentMonthBudgetConversion { get; set; }
= DateTime.Now.AddMonths(-1).ToString("MMM") + " Budget";
}
// POST: Grab data for department and year
[HttpPost]
public ActionResult GetBudgetsActuals(BudgetsActualsViewModel model)
{
try
{
if (ModelState.IsValid)
{
var repo = new BudgetDemoRepository();
ModelState.Clear();
model.Departments = repo.GetBudgetsActuals().Departments;
model.Years = repo.GetBudgetsActuals().Years;
model.BudgetActualCollection = repo.GetBudgetsActualsData(model);
}
else
{
// Execution gets to here before returning to view
model.BudgetActualCollection = new
List<BudgetDemo.Models.BudgetsActualsViewModel>();
}
return View(model);
}
catch
{
return View("Error");
}
}
//POST:获取部门和年度的数据
[HttpPost]
公共行动结果GetBudgetActuals(BudgetActualsViewModel模型)
{
尝试
{
if(ModelState.IsValid)
{
var repo=新预算存储库();
ModelState.Clear();
model.Departments=repo.getBudgetActuals().Departments;
model.Years=repo.getBudgetActuals().Years;
model.BudgetActualCollection=repo.getbudgetsactualdata(model);
}
其他的
{
//执行在返回视图之前到达此处
model.BudgetActualCollection=新建
List();
}
返回视图(模型);
}
抓住
{
返回视图(“错误”);
}
}
这似乎是HttpPost方法的一个问题。提交表单时,集合没有传递,因此我们将丢失其中的数据。现在,HttpPost
方法返回相同的视图,但它只分配if
块中的集合,因此当任何一个下拉列表丢失时,if
状态将为false,执行将进入else
块,并返回带有模型的视图。在这种情况下,从未为集合分配数据。将HttpPost
更新到下面,以便在不考虑其他条件的情况下填充集合
// POST: Grab data for department and year
[HttpPost]
public ActionResult GetBudgetsActuals(BudgetsActualsViewModel model)
{
try
{
// assign collections before returning view
var repo = new BudgetDemoRepository();
model.Departments = repo.GetBudgetsActuals().Departments;
model.Years = repo.GetBudgetsActuals().Years;
if (ModelState.IsValid)
{
ModelState.Clear();
model.BudgetActualCollection = repo.GetBudgetsActualsData(model);
}
else
{
model.BudgetActualCollection = new
List<BudgetDemo.Models.BudgetsActualsViewModel>();
}
return View(model);
}
catch
{
return View("Error");
}
}
//POST:获取部门和年度的数据
[HttpPost]
公共行动结果GetBudgetActuals(BudgetActualsViewModel模型)
{
尝试
{
//在返回视图之前分配集合
var repo=新预算存储库();
model.Departments=repo.getBudgetActuals().Departments;
model.Years=repo.getBudgetActuals().Years;
if(ModelState.IsValid)
{
ModelState.Clear();
model.BudgetActualCollection=repo.getbudgetsactualdata(model);
}