Reputation: 2609
Ok, let me start out by saying that I am brand new to MVC. With that out of the way, I am using the version of MVC that ship with Visual Studio 2010. This is also using Visual Basic, but I am sure that you can figure that out once you see the code.
I am trying to validate my data, and the validation process is working correctly. However, if the validation fails the values that were in my textbox are not reloaded on the form.
My form is fairly simplistic as I wanted to start with something simple for my first application. It consists of a table that is tied to a collection of Agreement objects. At the bottom of the table, I have two textboxes for adding a new agreement. It is these two textboxes that are not getting the data posted back to them.
Here is the view:
<%@ Page Title="" Language="VB" MasterPageFile="~/Views/Shared/Food.Master" Inherits="System.Web.Mvc.ViewPage(Of IEnumerable (Of NdaToolLibrary.BusinessLayer.Agreement))" %>
<asp:Content ID="Content1" ContentPlaceHolderID="PrimaryContent" runat="server">
<h1>Agreement List</h1>
<table cellpadding="0" cellspacing="0" border="0" class="tableDefault" style="width: 300px !important">
<tr>
<th>
AccountType
</th>
<th>
NationalId
</th>
<th></th>
</tr>
<% For i As Integer = 0 To Model.Count - 1%>
<tr class="<%= IIF(i mod 2 = 0, "", "detailRow") %>">
<td>
<%: Model(i).AccountType%>
</td>
<td>
<%: Model(i).NationalId%>
</td>
<td>
<%: Html.RouteLink("Delete", "Delete", New With {.action="Delete", .acctType = Model(i).AccountType, .id = Model(i).NationalId})%>
</td>
</tr>
<% Next%>
<tr class="footerRow">
<td>
<%= Html.TextBox("AccountType")%>
<%= Html.ValidationMessage("AccountType", " ")%>
</td>
<td>
<%= Html.TextBox("NationalId")%>
<%= Html.ValidationMessage("NationalId"," ")%>
</td>
<td>
<a href="javascript: document.forms[0].action='/Agreement/Create'; document.forms[0].submit();">Create</a>
</td>
</tr>
</table>
<%= Html.ValidationSummary("Could not save agreement. Reasons include:", New with{.class = "red"})%>
</asp:Content>
Here is the controller:
Namespace Web
Public Class AgreementController
Inherits System.Web.Mvc.Controller
Public Function Create(ByVal FormValues As FormCollection) As ActionResult
Dim agreement As New BusinessLayer.Agreement()
agreement.AccountType = FormValues("AccountType").ToString()
agreement.NationalId = FormValues("NationalId").ToString()
If agreement.IsValid Then
Try
agreement.Save()
Catch ex As Exception
ModelState.AddModelError("", ex.Message)
End Try
Else
For Each validationError As BusinessLayer.DataValidationMessage In agreement.GetValidationResults()
ModelState.AddModelError(validationError.Property, validationError.Message)
Next
End If
'Try
' agreement.AccountType = FormValues("AccountType").ToString()
' agreement.NationalId = FormValues("NationalId").ToString()
' agreement.Save()
'Catch dvEx As BusinessLayer.DataValidationException
' For Each validationError As BusinessLayer.DataValidationMessage In dvEx.ValidationMessages
' ModelState.AddModelError(validationError.Property, validationError.Message)
' Next
'Catch ex As Exception
' ModelState.AddModelError("", ex.Message)
'End Try
Dim agreements As New BusinessLayer.AgreementCollection()
agreements.Load()
Return View("Index", agreements)
End Function
Public Function Delete(ByVal AcctType As String, ByVal Id As String) As ActionResult
Dim agreement As New BusinessLayer.Agreement()
agreement.AccountType = AcctType
agreement.NationalId = Id
Return View("Delete", agreement)
End Function
<AcceptVerbs(HttpVerbs.Post)> _
Public Function Delete(ByVal AcctType As String, ByVal Id As String, ByVal FormValues As FormCollection) As ActionResult
Dim agreement As New BusinessLayer.Agreement(AcctType, Id)
agreement.Delete()
Return RedirectToAction("Index")
End Function
Public Function Index() As ActionResult
Dim agreements As New BusinessLayer.AgreementCollection()
agreements.Load()
' Return View("Index", agreements) is implied because the view has the same name as the action
Return View(agreements)
End Function
End Class
End Namespace
Upvotes: 1
Views: 1773
Reputation: 227
First of all I think you should extract your fields need to create a new account in a separate view ( right now it's in the master page). You can access this new view by putting a link to it on the master page view.
Your new View should be strongly typed ( you need to create a model for it).
And put the fields needed to create your account in a using (Html.BeginForm()) {} statement in your new view page.
And on the controller you must have something like
public void Create(YourModelType model)
{
if (!ModelState.IsValid) //this will check if there are validation errors after binding
{
return View(model); //this will repopulate back the input collected from the form
}
//here you can put your code to process the creation
}
Sorry to give you example in C# but I don't know VB .
Hope that my answer help you.
Upvotes: 3