提交局部视图表单时触发InvalidOperationException:未找到AddValue视图
问题描述
我尝试在单个View页面中向两个数据表插入数据,使用了两个不同的ViewModel。为此我为第二个表的数据插入创建了Partial View。目前完整页面可正常打开,第一部分功能运行成功,Partial View也能正常显示,但提交数据时出现如下错误:
InvalidOperationException: The view 'AddValue' was not found. The following locations were searched:
/Views/Attribute/AddValue.cshtml
/Views/Shared/AddValue.cshtml
/Pages/Shared/AddValue.cshtml
控制器代码
public class AttributeController : Controller { private readonly AttributeInfoService _attributeService; private readonly AttributeValueService _valueService; public AttributeController(IAttributeInfoRepository attributeRepository, IAttributeValueRepository valueRepository) { this._attributeService= new AttributeInfoService(attributeRepository); this._valueService= new AttributeValueService(valueRepository); } [HttpGet] public IActionResult ViewAttribute() { return View(_attributeService.GetAttributeList()); } [HttpGet] public IActionResult AddAttribute() { ViewBag.attribute = _attributeService.AttributeDropDown(); return View(); } [HttpPost] public IActionResult AddAttribute(AttributeInfoViewModel avm) { if(ModelState.IsValid) { string status = _attributeService.Add(avm); if (status == "OK") { return RedirectToAction("AddAttribute"); } } else { string msg = "fail"; ViewBag.Message = msg; } return View(avm); } [HttpGet] public IActionResult EditAttribute() { return View(); } [HttpPost] public IActionResult EditAttribute(AttributeInfoViewModel avm) { if (ModelState.IsValid) { var status= _attributeService.Update(avm); if(status == "OK") { return RedirectToAction(""); } } return View(avm); } [HttpPost] public IActionResult DeleteAttribute(int id) { if (id != 0) { _attributeService.Delete(id); return RedirectToAction(""); } return View(); } [HttpGet] public IActionResult ViewValue() { return View(_valueService.GetAllAttributeValueList()); } [HttpPost] public IActionResult AddValue(AttributeValueViewModel avm) { if (ModelState.IsValid) { string status = _valueService.Add(avm); if (status == "OK") { return RedirectToAction("AddValue"); } } return View(avm); } [HttpGet] public IActionResult EditValue() { return View(); } [HttpPost] public IActionResult EditValue(AttributeValueViewModel vm) { if (ModelState.IsValid) { string status = _valueService.Update(vm); if( status == "OK") { return RedirectToAction(""); } } return View(vm); } [HttpPost] public IActionResult DeleteValue(int id) { if(id!=0) { _valueService.Delete(id); return RedirectToAction(""); } return View(); } }
主视图(AddAttribute.cshtml)代码
@model DL.ViewModels.Configuration.AttributeInfoViewModel @{ ViewData["Title"] = "AddAttribute"; Layout = "~/Views/Shared/_Layout.cshtml"; } <div class="d-flex justify-content-between mb-4"> <div class=""> <h4 class="text_primary fw-bold">Add Product Attribute</h4> </div> <div class="d-flex bg_primary rounded-2 overflow-hidden"> <a title="Sale Order List" asp-action="AddProductInfo" asp-controller="Inventory" class="my_button px-2 py-1 rounded-0"> Add Product </a> </div> </div> <form asp-action="AddAttribute" asp-controller="Attribute" method="post"> <div class="sale_order_container rounded-2 mb-4"> <div class=""> <h6 class="border-bottom border-secondary-subtle soc_title py-3 px-4"> Attribute @ViewBag.Message </h6> </div> <div class="grid_cols_2 p-4 "> <div class=""> <label asp-for="AttributeName" class="form-label text-secondary">Attribute Name</label> <input type="text" asp-for="AttributeName" id="AttributeName" class="form-control shadow-none rounded-0" /> </div> <div class=""> <label asp-for="Description" class="form-label text-secondary">Description</label> <input type="text" asp-for="Description" id="Description" class="form-control shadow-none rounded-0" /> </div> </div> <div class="col-md-2 mx-auto pb-4"> <button type="submit" class="sol_add_button mt-0 w-100"> <i role="button" class="fa-solid fa-floppy-disk fa-fw fw-bolder fs-5"></i> <span>Save</span> </button> </div> </div> </form> @await Html.PartialAsync("_AddValue") @* <partial name="_AddValue.cshtml"/> *@ @section Scripts { <script> $("#left_Configuration_menu").show(); </script> }
局部视图(_AddValue.cshtml)代码
@model DL.ViewModels.Configuration.AttributeValueViewModel <form action="AddValue" method="post"> <div class="sale_order_container rounded-2 mb-4"> <div class=""> <h6 class="border-bottom border-secondary-subtle soc_title py-3 px-4"> Attribute Value </h6> </div> <div class="grid_cols_3 p-4 "> <div class=""> <label for="AttributeId" class="form-label text-secondary">Attribute Id</label> <select asp-for="AttributeId" asp-items="@ViewBag.attribute" id="AttributeId" class="form-select shadow-none rounded-0"> <option value="" selected>Select Attribute</option> </select> </div> <div class=""> <label asp-for="AttributeValueName" class="form-label text-secondary">Attribute Value</label> <input type="text" asp-for="AttributeValueName" id="Description" class="form-control shadow-none rounded-0" /> </div> <div class=""> <label asp-for="Description" class="form-label text-secondary">Description</label> <input type="text" asp-for="Description" id="Description" class="form-control shadow-none rounded-0" /> </div> </div> <div class="col-md-2 mx-auto pb-4"> <button type="submit" class="sol_add_button mt-0 w-100"> <i role="button" class="fa-solid fa-floppy-disk fa-fw fw-bolder fs-5"></i> <span>Save</span> </button> </div> </div> </form>
问题原因与修复方案
错误原因
- 缺少AddValue对应的视图:控制器的
AddValuePost方法在ModelState无效时执行return View(avm),ASP.NET Core会自动寻找名为AddValue的视图,但你并没有创建该视图,因此报错。 - 跳转逻辑错误:提交成功后代码执行
return RedirectToAction("AddValue"),但同样不存在AddValue的Get视图,而且你的需求是回到原来的AddAttribute页面。
修复步骤
1. 修改AddValue的Post方法逻辑
将控制器中的AddValue方法修改为提交成功或失败都返回AddAttribute页面:
[HttpPost] public IActionResult AddValue(AttributeValueViewModel avm) { if (ModelState.IsValid) { string status = _valueService.Add(avm); if (status == "OK") { // 提交成功后跳回AddAttribute页面 return RedirectToAction("AddAttribute"); } } // 提交失败时,准备AddAttribute页面所需的ViewBag数据 ViewBag.attribute = _attributeService.AttributeDropDown(); // 添加属性值提交错误提示 ViewBag.ValueErrorMessage = "属性值提交失败,请检查输入"; // 返回AddAttribute视图,传递空的AttributeInfoViewModel(主视图需要该模型) return View("AddAttribute", new AttributeInfoViewModel()); }
2. 优化局部视图的表单路径(推荐)
把局部视图中的表单改为使用ASP.NET Core Tag Helper,确保提交路径正确:
<form asp-action="AddValue" asp-controller="Attribute" method="post"> <!-- 原有表单内容保持不变 --> </form>
3. 显示属性值提交错误(可选)
在AddAttribute.cshtml中局部视图的上方添加错误提示区域,方便用户看到提交失败的原因:
@if (!string.IsNullOrEmpty(ViewBag.ValueErrorMessage)) { <div class="alert alert-danger mb-4">@ViewBag.ValueErrorMessage</div> } @await Html.PartialAsync("_AddValue")
内容的提问来源于stack exchange,提问作者Abdullah Al Mahmud Khan
相关产品推荐
相关产品推荐

