I have a problem with validation in ASP.NET MVC 2.0. I use the same Action in Controller to perform user request.
For example:
public ActionResult Index(ReportModel model)
{
if (!model.IsInitialDisplay && ModelState.IsValid)
{
model.Result = service.GetResult(model);
}
return View(model);
}
In the ReportModel, I define a flag IsInitialDisplay to determine whether the page is initial displayed or not:
public class ReportModel
{
[Required(ErrorMessage = "*")]
public string Criteria { get; set; }
public bool IsInitialDisplay { get; set; }
public ReportResult Result { get; set; }
public ReportModel()
{
IsInitialDisplay = true;
}
}
And in the View, I use the following code:
<% using (Html.BeginForm())
{ %>
<table>
<tr>
<th>
Criteria:
</th>
<td>
<%= Html.TextBox("Criteria", "") %>
<%= Html.ValidationMessage("Criteria") %>
</td>
</tr>
</table>
<br />
<input type="submit" value="Submit" />
<%= Html.Hidden("IsInitialDisplay", false) %>
<% } %>
As I expect, if users don't input any value for Criteria and click Submit button, the error message for validation will be displayed.
But the validation error message always displayed on initial page load, I don't know how to prevent it?
Does anyone know? Thanks,
[Updated]
I have updated my Action method as below and it's seem to be fine:
public ActionResult Index(ReportModel model)
{
// Collecting some commons data here...
if (model.IsInitialDisplay)
{
ModelState.Clear();
}
else if (ModelState.IsValid)
{
model.Result = service.GetResult(model);
}
return View(model);
}
Model
View
Work fine
Here's a simple solution that combines some good answers:
This uses the http method to determine if it's first load (like Darin's solution).
Most importantly, it has MVC build your controller instead of manually newing one up yourself. This is important if you use dependency injection or if you had other contextual data coming in through the query string (like a nested resource id).
The reason an error message is displayed on initial page load is because your controller action takes
ReportModel
model as argument. When you first access this action with/Home/Index
you are passing no arguments and when the default model binder tries to bind to aReportModel
instance it triggers validation errors.It is a bad practice to use the same action for both rendering and handling the form submission but if you really want to do it you could try like this:
In this case you no longer need the
IsInitialDisplay
property on your model nor the constructor which sets it to true.This being said, here's the recommended way: