[英]Why model is null after postback in ASP.NET MVC
我正在使用最新的 .NET Framework 和 VS 2019 開發 ASP.NET MVC 應用程序。
在我的頁面中,我有一個簡單的文本框和一個搜索按鈕。 當我單擊搜索按鈕並回發表單時,在控制器中,我得到model.Code
為 NULL
這是我的代碼 - 我的視圖模型:
public class UserManagementViewModel
{
public string Code { get; set; }
// some other properties including simple and complex types
}
在視圖中:
<td style="min-width: 300px">
@Html.TextBoxFor(m => m.Code)
</td>
在控制器中:
[HttpPost]
public ActionResult UpdateUserPermissions(UserManagementViewModel model)
{
// model.Code is null here!!
return RedirectToAction("UserManagement");
}
經過數小時的研究,我嘗試了以下操作:
我查看了 html 源代碼,發現
<input id="Code" name="Code">
使用 Chrome 開發工具,我將輸入的名稱更改為"Model.Code"
<input id="Code" name="Model.Code">
這一次,我在回發后在文本框中獲得了輸入的值。
我不知道為什么會發生這種情況以及為什么沒有正確生成元素名稱!
我能做什么?
編輯:
我還有一些其他控件,如復選框和單選按鈕,我使用純 HTMl 代碼並以“模型”開頭命名它們。 像下面這樣而不是使用@HTML helper。
它工作正常,我得到了 Action 的價值。
解決方法:
我在這里找到了一個解決方法: ASP.NET MVC 4 覆蓋發出的 html 名稱和 ID,因此我將代碼更改為:
@Html.TextBoxFor(m => m.Code, new { @Name = "Model.Code" })
但是這段代碼幫助我解決了我的問題,我仍然不知道為什么 Razor 引擎生成的名稱不起作用。
輔助方法@Html.TextBoxFor
工作完全正確。 基本上,您幾乎在所有情況下都需要使用此方法(除了某些需要使用非標准行為的情況)。
關於您的情況,我認為您在使用HtmlFieldPrefix 時遇到了問題。
此屬性用於生成 HTML 輸入名稱。 我們可以在 GitHub 中查看 MVC 源代碼...
MVC 使用以下代碼片段生成 HTML 輸入(GitHub 鏈接):
private static MvcHtmlString InputHelper(HtmlHelper htmlHelper, InputType inputType, ModelMetadata metadata, string name, object value, bool useViewData, bool isChecked, bool setId, bool isExplicitValue, string format, IDictionary<string, object> htmlAttributes)
{
string fullName = htmlHelper.ViewContext.ViewData.TemplateInfo.GetFullHtmlFieldName(name);
if (String.IsNullOrEmpty(fullName))
{
throw new ArgumentException(MvcResources.Common_NullOrEmpty, "name");
}
TagBuilder tagBuilder = new TagBuilder("input");
tagBuilder.MergeAttributes(htmlAttributes);
tagBuilder.MergeAttribute("type", HtmlHelper.GetInputTypeString(inputType));
tagBuilder.MergeAttribute("name", fullName, true);
string valueParameter = htmlHelper.FormatValue(value, format);
bool usedModelState = false;
...
return tagBuilder.ToMvcHtmlString(TagRenderMode.SelfClosing);
}
正如我們所見, name
屬性由方法GetFullHtmlFieldName
計算。
這個方法我們也可以在 GitHub 上查看( 鏈接):
public string GetFullHtmlFieldName(string partialFieldName)
{
if (partialFieldName != null && partialFieldName.StartsWith("[", StringComparison.Ordinal))
{
// See Codeplex #544 - the partialFieldName might represent an indexer access, in which case combining
// with a 'dot' would be invalid.
return HtmlFieldPrefix + partialFieldName;
}
else
{
// This uses "combine and trim" because either or both of these values might be empty
return (HtmlFieldPrefix + "." + (partialFieldName ?? String.Empty)).Trim('.');
}
}
此方法使用HtmlFieldPrefix
屬性計算名稱。 因此,如果更改此屬性,則可以修改生成的名稱。
我認為您使用部分Views
並且需要帶有一些前綴的渲染屬性才能正確綁定。
請查看帶有示例和可能解決方案的下一個鏈接:
另一方面,要返回模型,您必須使用表單標簽。 MVC 有時將名稱視為模型屬性,但最好明確地這樣做。 這段代碼已經過測試,文本框的兩種變體都可以正常工作。
@model UserManagementViewModel
<form asp-action="UpdateUserPermissions" method="post">
@Html.TextBoxFor(m => m.Code)
// or
<div class="form-group">
<label asp-for="Code" class="control-label"></label>
<input asp-for="Code" class="form-control" />
</div>
<div>
<button type="submit"> submit </button>
</div>
</form>
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.