ASP.NET MVC 3 - Best practice for handling Model in View
I am using ASP.NET MVC 3 and have several pages where the majority of the View Model is read-only. An example field would be like such:
<div class="display-label">My Field</div>
<div class="display-field">@Model.MyField</div>
I then have a field where the user has to type in some verification text like so:
@Html.LabelFor(model => model.Verification)
@Html.PasswordFor(model => model.Verification)开发者_开发百科
When the user submits the form and it hits my controller, the ViewModel's fields are all null except for the Verification field. The way I have gotten around this, thus far, is to have several HiddenFor fields like such:
@Html.HiddenFor(model => model.MyField)
However, this gets ugly really fast. Is there a better way to handle the model in the view state so during the POST of the form submission, I can get all of my fields? This is important in case the verification text does not match during the POST and I need to return the view model without re-retrieving it from the database.
Thanks for any suggestions.
There is no better way around it without re-retrieving the value from the database. The reason is because MVC's model binding only looks at the GET or POST parameters to bind the MyField
to the action's model, and if the GET/POST parameters don't have a MyField
value then it has to keep that property as null (how else is it going to know what the value shouldbe?)
In order for the model binder to see your MyField
value is to pass it in the GET/POST parameters, and to do this you have to explicitly tell your view's form to pass the value in via Html.HiddenFor()
. There's no way for the view to automatically know to send that property in the post/get parameters.
However one idea you can look at is to create a Razor (or Html) helper method that takes a field name and an expression (the x => x.MyField
) and writes the following output for you:
<div class="display-label">My Field</div>
<div class="display-field">@Model.MyField</div>
@Html.HiddenFor(model => model.MyField)
This means you only have to write one line of code (something like @Html.ShowReadOnlyField(x => x.MyField, "My Field")
instead of those 3 lines. However, this also assumes that everywhere you want to do this will have the same div structure.
Edit: Just keep in mind the security concerns about read-only fields, because they aren't truly read-only.. It is better to re-retrieve this data from the database if this data is going to be used for anything in the controller, because even though it's read only on the HTML form, users can still set this value to anything they want by manipulating the POST/GET data.
Please try to serialize the Model in the Page and then do a Post? This Should Solve the Problem.
<%= Html.Serialize("User",Model) %>
[HttpPost]
public ActionResult Register([DeserializeAttribute] User user, FormCollection userForm)
{
}
精彩评论