ASP.NET MVC 5 Form Validation - c#

I am new to ASP.NET MVC and using version 5. I created a form that is in the layout, and I cannot cannot get it to show validation errors on the view. It will post to the action correctly, and if the model is valid, it will execute. If the model is invalid I will get the following error.
I am hoping someone can point me in the right direction. Thank you in advance!
Server Error in '/' Application.
The view 'ContactSubmit' or its master was not found or no view engine supports the searched locations. The following locations were searched:
~/Views/Home/ContactSubmit.aspx
~/Views/Home/ContactSubmit.ascx
~/Views/Shared/ContactSubmit.aspx
~/Views/Shared/ContactSubmit.ascx
~/Views/Home/ContactSubmit.cshtml
~/Views/Home/ContactSubmit.vbhtml
~/Views/Shared/ContactSubmit.cshtml
~/Views/Shared/ContactSubmit.vbhtml
This is my model I am using:
public partial class Lead
{
[Key]
public int LeadId { get; set; }
[Required]
[StringLength(50, MinimumLength=2, ErrorMessage="* A valid first name is required.")]
[Display(Name="First Name")]
public string FirstName { get; set; }
[Required]
[StringLength(50, MinimumLength=2, ErrorMessage="* A valid last name is required.")]
[Display(Name="Last Name")]
public string LastName { get; set; }
[Required]
[StringLength(50, MinimumLength=2, ErrorMessage="* A valid company is required.")]
public string Company { get; set; }
[Required]
[StringLength(50)]
[EmailAddress(ErrorMessage="* A valid email address is required.")]
public string Email { get; set; }
[Required]
[StringLength(15, MinimumLength=9, ErrorMessage="* A valid phone nunber is required.")]
[Phone(ErrorMessage="Please enter a valid phone number.")]
public string Phone { get; set; }
}
This is the code I have in my Home controller:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult ContactSubmit(
[Bind(Include = "FirstName, LastName, Company, Email, Phone")]
Lead lead)
{
try
{
if (ModelState.IsValid)
{
lead.Tenant = SessionManager.Get<Tenant>(Constants.SessionTenant);
lead.Refferer = SessionManager.Get<string>(Constants.SessionRefferal);
DataStoreManager.AddLead(lead);
return RedirectToAction("SubmissionConfirmed", lead);
}
}
catch (DataException /* dex */)
{
ModelState.AddModelError("", "Unable to perform action. Please contact us.");
return RedirectToAction("SubmissionFailed", lead);
}
return View(lead);
}
[HttpGet]
public ActionResult ContactSubmit()
{
return View();
}
This is the form that I have in my layout:
#using (Html.BeginForm("ContactSubmit", "Home", FormMethod.Post))
{
#Html.AntiForgeryToken()
<fieldset>
<div class="editor-label">
#Html.LabelFor(m => m.FirstName)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.FirstName)
#Html.ValidationMessageFor(m => m.FirstName)
</div>
<div class="editor-label">
#Html.LabelFor(m => m.LastName)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.LastName)
#Html.ValidationMessageFor(m => m.LastName)
</div>
<div class="editor-label">
#Html.LabelFor(m => m.Company)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Company)
#Html.ValidationMessageFor(m => m.Company)
</div>
<div class="editor-label">
#Html.LabelFor(m => m.Email)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Email)
#Html.ValidationMessageFor(m => m.Email)
</div>
<div class="editor-label">
#Html.LabelFor(m => m.Phone)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Phone)
#Html.ValidationMessageFor(m => m.Phone)
</div>
<div class="masthead-button-wrapper">
<input class="btn btn-warning" type="submit" value="Submit" />
</div>
</fieldset>
}

There is one error in your code, I didn't notice first. In the get method you are using -
return View();
Which means your view does not allow parameter but when there is an error you are using -
return View(lead);
In this case MVC is looking for the view with the same name but which also accepts a parameter of Lead type and it fails since there is no view with that option and the only one that is found does not accept parameter as seen from the Get method. When there is no error, you are redirecting to -
return RedirectToAction("SubmissionConfirmed", lead);
and the View with the parameter is never needed to be searched and thus no error.
So, change the view to accept a parameter of Lead and change your get method accordingly.
May be this would help. -
[HttpGet]
public ActionResult ContactSubmit()
{
var lead = new Lead();
return View(lead);
}
and in the view add
#model Lead
at the top
EDIT : In case since you are redirecting you should know that ModelState gets initialized in each request, so redirecting clears it automatically. You have to use some other means to pass modelstate or better if you use client side validation.

Related

User registration page, with a defined user MODEL (MVC ) [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 6 years ago.
Improve this question
I have worked with .Net webforms before and now working on a MVC project.
I am working on creating a user registration page. I have no idea how its MODEL should look like.
See database diagram
User registration page:
Firstname
LastName
Email adress
Subcribe newsletter ?
Password
Choose your city
.....
I think I have to do this in this task:
STEP 1:
Populate cities dropdownList (choose your city) with data from database
STEP 2:
Insert users email address in UserEmail table and set subcribe to 0 or 1
STEP 3:
Save user registration data and EmailID (get from UserEmails table), CityID into Users table
Should I make a large MODEL , like this :
Public Class Registration Model
{
Get, set:
all USEREMAIL plugs ties
all Users plugs ties
all Cities plugs ties
}
How to start with this task in MVC?
(I know how to develop this in webforms , but MVC model confuses me)
You were on the right track.You're trying to create a view which let's users complete a registertion form, this view needs to use the user model and at the same type display a list of cities in a drop down which come from a different table in the database but are related to the user.
In MVC there's a concept called viewmodel, all that it is is a simple class which combines one or more models together.
Below I created a model called SiteUser and then another model called SiteUserViewModel which inherits from the user and gives us all the user properties PLUS an additional property we can use to populate the cities.So when we display the page, we will use the SiteUserViewModel but when we post to the controller to save the user in the database we will use SiteUser:
Models:
namespace MVCTutorial.Models
{
public class SiteUser
{
[Display(Name="First Name")]
public string FirstName { get; set; }
[Display(Name = "Last Name")]
public string LastName { get; set; }
[DataType(DataType.EmailAddress)]
public string EmailAddress { get; set; }
[Display(Name = "Subscribe To Newsletter?")]
public bool SubscribeToNewsletter { get; set; }
[DataType(DataType.Password)]
public string Password { get; set; }
[Display(Name="City")]
public int CityId { get; set; }
}
public class SiteUserViewModel : SiteUser
{
public List<SelectListItem> Cities { get; set; }
}
}
Controller:
public class SiteUserController : Controller
{
[HttpGet]
public ActionResult Index()
{
var model = new SiteUserViewModel();
//Replace this with logic that reads cities from the database
var city1 = new SelectListItem { Text = "Johannesburg", Value = "1" };
var city2 = new SelectListItem { Text = "Cape Town", Value = "2" };
model.Cities = new List<SelectListItem> { city1, city2 };
return View(model);
}
[HttpPost]
public ActionResult CreateUser(SiteUser user)
{
System.Diagnostics.Debugger.Break();
//Write the code to add user to the database
return View();
}
}
View:
#model MVCTutorial.Models.SiteUserViewModel
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width" />
<title>Create User</title>
</head>
<body>
#using (Html.BeginForm("CreateUser", "SiteUser"))
{
#Html.ValidationSummary(true)
<fieldset>
<legend>Site User</legend>
<div class="editor-label">
#Html.LabelFor(model => model.FirstName)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.FirstName)
#Html.ValidationMessageFor(model => model.FirstName)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.LastName)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.LastName)
#Html.ValidationMessageFor(model => model.LastName)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.EmailAddress)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.EmailAddress)
#Html.ValidationMessageFor(model => model.EmailAddress)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.SubscribeToNewsletter)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.SubscribeToNewsletter)
#Html.ValidationMessageFor(model => model.SubscribeToNewsletter)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.Password)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.Password)
#Html.ValidationMessageFor(model => model.Password)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.CityId)
</div>
<div class="editor-field">
#Html.DropDownList("CityId", Model.Cities, "Please select one")
</div>
<p>
<input type="submit" value="Create" />
</p>
</fieldset>
}
</body>
</html>
Result:

Model attribute null on post

I have a simple application that I've loosely based off the MVC Music store used in a tutorial on asp.net that allows a user to enter details about TV shows that they are watching so they can keep track of which episode they're up to in each show.
The main entities in my application are Show:
Public class Show
{
// a few automatic properties
public int id { get; set; }
public Genre Genre { get; set; }
}
and the Genre class
Public partial class Genre
{
public int GenreId { get; set; }
public string Name { get; set; }
public List<Show> Shows { get; set; }
}
My POST edit method in my controller was generated by VS for me:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(Show show)
{
if (ModelState.IsValid)
{
db.Entry(show).State = EntityState.Modified;
db.SaveChanges();
return RedirectToAction("Index");
}
return View(show);
}
When I inspect db in the debugger, I can see that the Show objects (however many are in the database at the time. I seed it with two but usually add a third via the form) all have the genres I've entered but after the Edit action returns the view, the Genre is null while all the other values are updated. Why is this?
I thought perhaps the genre field was null because I wasn't instantiating them but where would I do that? I don't want a new genre created every time a Show's genre is set. I just want a show to have a genre reference so that I can eventually allow the user to select a genre and see all the shows they're following of that genre.
EDIT: Here's my Edit View. The Details view also looks very similar.
#model watchedCatalogue2.Models.Show
#{
ViewBag.Title = "Edit";
}
<h2>Edit</h2>
#using (Html.BeginForm()) {
#Html.AntiForgeryToken()
#Html.ValidationSummary(true)
<fieldset>
<legend>#Html.DisplayFor(m => m.Name)</legend>
#Html.HiddenFor(m => m.id)
<div class="editor-label">
#Html.LabelFor(m => m.Name)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Name)
#Html.ValidationMessageFor(m => m.Name)
</div>
<div class="editor-label">
#Html.LabelFor(m => m.Genre)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Genre.Name)
#Html.ValidationMessageFor(m => m.Genre.Name)
</div>
<div class="editor-label">
#Html.Label("Number of episodes")
</div>
<div class="editor-field">
#Html.EditorFor(m => m.NoEpisodes)
#Html.ValidationMessageFor(m => m.NoEpisodes)
</div>
<div class="editor-label">
#Html.Label("Number of episodes watched")
</div>
<div class="editor-field">
#Html.EditorFor(m => m.NoEpisodesWatched)
#Html.ValidationMessageFor(m => m.NoEpisodesWatched)
</div>
<div class="editor-label">
#Html.Label("Watching State")
</div>
<div class="editor-field">
#Html.DropDownListFor(m => m.State, watchedCatalogue2.Models.Show.WatchStateItems)
</div>
<div class="editor-label">
#Html.LabelFor(m => m.Description)
</div>
<div class="editor-field">
#Html.EditorFor(m => m.Description)
#Html.ValidationMessageFor(m => m.Description)
</div>
<p>
<input type="submit" value="Save" />
</p>
</fieldset>
Also, for good measure, db in my controller refers to my CatalogueEntities class:
namespace watchedCatalogue2.Models
{
public class CatalogueEntities : DbContext
{
public DbSet<Genre> Genres { get; set; }
public DbSet<Show> Shows { get; set; }
}
}
The problem is probably the fact that in MVC all the data is not retained/posted onto the POST method, but only those rendered as an editable element on the View and contained in the Model.
The simplest work-around will be to render it as a hidden field, as follows:
MVC 2.0 and earlier:
<%: Html.HiddenFor(m => m.GenreId) %>
Razor:
#Html.HiddenFor(m => m.GenreId)
If you use AJAX or something similar, you could also just send/pass the value as a parameter.
Also note, if you make use of the ModelState.IsValid functionality, it is possible and very probable that the Hidden fields would be rendered as null, and most probably as a problem. To remove this, which is not always advised, just add ModelState.Remove("TheKey");, in your case it is probably, ModelState.Remove("GenreID");
If I'm following the problem right, you need to render it on the form in some way for the data to be maintained, bearing in mind the web is stateless, if the value isn't present when the form is posted, it won't be bound back on to your view model.
On your view include in the form:
#Html.HiddenFor(model => model.GenreId)
Or depending on what your URL is like on your Get, you could change your POST method signature to include the id.
After some research, I noticed many of the model classes in the examples had references to other models that were marked as virtual. I figured I had nothing to lose so I modified my Show class so public Genre Genre { get; set; } now reads public virtual Genre Genre { get; set; }. Suddenly it all works. I'd appreciate if someone who knows why it works could explain it to me because all I've seen thus far have been references to lazy loading but nothing relating to my problem.
Thanks for the help, everyone.

Controller unwantedly creates new user in database

On my MVC4 application I have a page where an user can be placed in a schedule. The idea is that you can select a person and that they will be entered on the schedule. The Schedule Model looks as follows:
public class Schedule {
[Key]
public int scheduleId { get; set; }
[Column(TypeName = "Date")]
[DataType(DataType.Date)]
public DateTime date { get; set; }
public int UserId { get; set; }
public virtual User User { get; set; }
}
The User Model where the Schedule Model refers to looks like this:
public class User {
public int UserId { get; set; }
[Display(Name = "Naam")]
public string Name { get; set; }
public string Email { get; set; }
[Display(Name = "Beschikbaar")]
public bool isAvailable { get; set; }
}
An user can be placed on the scheduling page with the following controller:
public ActionResult Create(Schedule schedule)
{
if (ModelState.IsValid)
{
db.Schedules.Add(schedule);
db.SaveChanges();
return RedirectToAction("Index");
}
return View(schedule);
}
The Schedule/Create view looks like this:
and has the following code:
<h2>Schedule a person</h2>
#using (Html.BeginForm()) {
#Html.AntiForgeryToken()
#Html.ValidationSummary(true)
<fieldset>
<legend>Schedule</legend>
<div class="editor-label">
#Html.LabelFor(model => model.UserId)
</div>
<div class="editor-field">
#Html.DropDownList("UserId", String.Empty)
#Html.ValidationMessageFor(model => model.UserId)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.date)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.date)
#Html.ValidationMessageFor(model => model.date)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.User.isAvailable)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.User.isAvailable)
#Html.ValidationMessageFor(model => model.User.isAvailable)
</div>
<p>
<input type="submit" value="Plan" />
</p>
</fieldset>
}
This code does place the user on the schedule on the specified date. But somehow an extra "null" user is created in the database every time an existing user is added to the schedule. See this image:
I have been breaking my head over this unwanted behaviour for the past hours. The Create action of the ScheduleController does not specify to create an extra user. I have no idea why it does do so anyway.
Does anyone here have any idea?
It's because of your .User.IsAvailabe property. This creates a new user when adding the schedule.
You'll have to attach the existing user to your schedule. Perhaps you can even get rid of UserId and use User.Id in your form.

Modelstate validation always return false using a dropdownlist

NOTE: Code updated to take into account the comments and answer made below.
In my MVC app I need sometimes to make references to other objects (like a many-to-many relationship, or one-to-many relationship).
So I have this model:
public class ObjInfo
{
[Required(ErrorMessage = "Obj ID is required.")]
[Display(Name = "ObjID")]
public int m_Id { get; set; }
[Required(ErrorMessage = "Obj Name is required.")]
[Display(Name = "Obj Name")]
public string m_Name { get; set; }
[Display(Name = "Obj Number")]
public int m_Number { get; set; }
(...)
[Required(ErrorMessage = "Other Obj is required.")]
[Display(Name = "OtherObj")]
public int m_OtherObjID { get; set; }
public OtherObjInfo m_OtherObj { get; set; }
(...)
}
I have default and parameters constructors as well and can show them as needed, though I am not sure if they are at fault. Anyway.
In my controller, I have the two create methods following MVC methods:
//
// GET: /Obj/Create
public ActionResult Create()
{
ViewBag.List = new SelectList(PopulateDDLs(), "OtherObj", "Other obj ID");
return View();
}
//
// POST: /Obj/Create
[HttpPost]
public ActionResult Create(Objinfo obj)
{
if (ModelState.IsValid)
{
m_ObjManager.CreateObj(obj);
return RedirectToAction("SearchIndex");
}
ViewBag.List = new SelectList(PopulateDDLs(), "OtherObj", "Other obj ID");
return View(obj);
}
And, finally, here's how my "Create" view is coded:
#model MyApp.Models.ObjInfo
#{
ViewBag.Title = "Create";
}
<h2>Create</h2>
#using (Html.BeginForm()) {
#Html.ValidationSummary(true)
<fieldset>
<legend>OBJ</legend>
<div class="editor-label">
#Html.LabelFor(model => model.m_Id)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.m_Id)
#Html.ValidationMessageFor(model => model.m_Id)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.m_Name)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.m_Name)
#Html.ValidationMessageFor(model => model.m_Name)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.m_Number)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.m_Number)
#Html.ValidationMessageFor(model => model.m_Number)
</div>
(...)
<div class="editor-label">
#Html.LabelFor(model => model.m_OtherObj , "Other Obj")
</div>
<div class="editor-field">
#Html.DropDownList(model => model.m_OtherObjID, ViewBag.List as SelectList, "--- Select Other Obj ---", new {#class = "OtherObjInfo "})
#Html.ValidationMessageFor(model => model.m_OtherObj)
</div>
<p>
<input type="submit" value="Create" />
</p>
</fieldset>
}
<div>
#Html.ActionLink("Back to List", "Index")
</div>
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
}
Basically, the problem is that each time I click on the "create" button, the ModelState validation is always false for the OtherObj even if something is selected in the dropdownlist. Every other values are correct except this one.
I don't understand why and I would greatly appreciate your help on this one, thank you for your help!
After code edited **
Now I get a crash as I enter the "Create" view:
DataBinding: 'System.String' does not contain a property with the name 'OtherObj'.
Exactly on the line where my dropdownlistfor is located.
The datavalueField and dataTextField are supposed to refer to what exactly?
add otherObjectId to your model
public class ObjInfo
{
public int m_Id { get; set; }
...
[Required(ErrorMessage = "Other Obj is required.")]
[Display(Name = "OtherObj")]
public int otherObjectId { get; set; }
public OtherObjInfo m_OtherObj { get; set; }
...
}
controller
public ActionResult Create()
{
ViewBag.List = new SelectList(PopulateDDLs(), "Id", "Name");
return View();
}
[HttpPost]
public ActionResult Create(Objinfo obj)
{
if (ModelState.IsValid)
{
m_ObjManager.CreateObj(obj);
return RedirectToAction("SearchIndex");
}
ViewBag.List = new SelectList(PopulateDDLs(), "Id", "Name");
return View(obj);
}
view
<div class="editor-label">
#Html.LabelFor(model => model.m_OtherObj , "Other Obj")
</div>
<div class="editor-field">
#Html.DropDownListFor(model => model.otherObjectId, ViewBag.List as SelectList, "--- Select Category ---", new { #class = "some_class" })
#Html.ValidationMessageFor(model => model.m_OtherObj)
</div>
better way is using strongly typed helpers. All your helpers are strongly-typed (editorfor, textboxfor, dropdownlistfor,...) except dropdownlist.
if you want to bind DDL value to your model, You should use dropdownlistfor instead of dropdownlist.
your model state is not valid, because you dont bind required value as DDL to model.

How does the MVC3 Controller retrieve HTTPPOST params?

I'm not quite understanding how this works.
Passing parameters from my entity objects works fine. But when I create new fields, only the first one is retrieved.
Model User Class:
public class User {
[Key]
public long Uid { get; set; }
[Required]
[StringLength(50, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 4)]
[DataType(DataType.EmailAddress)]
[Display(Name = "Email:")]
public string Email { get; set; }
[Required]
[StringLength(20, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 4)]
[Display(Name = "User Name:")]
public string Username { get; set; }
public string Password { get; set; }
public byte Role { get; set; }
public DateTime Created { get; set; }
}
CSHTML:
#using (Html.BeginForm( null,
null,
FormMethod.Post,
new { id = "regform" })
) {
#Html.ValidationSummary(true)
<fieldset>
<legend>Register</legend>
<div class="editor-label">
#Html.LabelFor(model => model.Email)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.Email)
#Html.ValidationMessageFor(model => model.Email)
</div>
<div class="editor-label">
#Html.LabelFor(model => model.Username)
</div>
<div class="editor-field">
#Html.EditorFor(model => model.Username)
#Html.ValidationMessageFor(model => model.Username)
</div>
<div class="editor-label">
Password:
</div>
<div class="editor-field">
#Html.Password("pwd")
</div>
<div class="editor-label">
Confirm Password:
</div>
<div class="editor-field">
#Html.Password("confirm")
</div>
<p>
<input type="submit" value="Register" />
</p>
</fieldset>
}
Controller:
[HttpPost]
public ActionResult Register(User user, string pwd, string confirm) {
user.Username = confirm;
user.Created = DateTime.Now;
user.Role = 255;
user.Password = EncryptPassword.Password(pwd);
if (ModelState.IsValid && pwd == confirm) {
db.Users.Add(user);
db.SaveChanges();
return RedirectToAction("Index");
}
return View(user);
}
Where I'm getting confused, is pwd picks up fine. confirm on the other hand remains null. My initial thought that it was calling by order and confirm in the model was simply conPwd. When that didn't work, I changed it's name to confirm. It still is not working and I can't find anything that explains how multiple parameters are passed to the controller.
Edit:
Updated my code. Believe it or not, this alone has taken me most of the day to write because I've been trying to understand what I'm doing. There is just so much to take in when you're learning Entities, LINQ, MVC, ASP.NET and Razor all at the same time. Basic C# is the only part I came in to this knowing. :)
You need a strongly typed view for your RegisterModel then use a Html.BeginForm to post the data to the controller.
Model
// This is the Model that you will use to register users
public class RegisterModel
{
[Required]
[Display(Name = "User name")]
public string UserName { get; set; }
[Required]
[DataType(DataType.EmailAddress)]
[Display(Name = "Email address")]
public string Email { get; set; }
[Required]
[StringLength(100, ErrorMessage = "The {0} must be at least {2} characters long.", MinimumLength = 6)]
[DataType(DataType.Password)]
[Display(Name = "Password")]
public string Password { get; set; }
[DataType(DataType.Password)]
[Display(Name = "Confirm password")]
[Compare("Password", ErrorMessage = "The password and confirmation password do not match.")]
public string ConfirmPassword { get; set; }
}
View (CSHTML)
// This is your strongly typed view that will use
// model binding to bind the properties of RegisterModel
// to the View.
#model Trainer.Models.RegisterModel
// You can find these scripts in default projects in Visual Studio, if you are
// not using VS, then you can still find them online
<script src="~/Scripts/jquery.validate.min.js"></script>
<script src="~/Scripts/jquery.validate.unobtrusive.min.js"></script>
// This is where your form starts
// The "Account" parameter states what controller to post the form to
#using (Html.BeginForm((string)ViewBag.FormAction, "Account")) {
#Html.ValidationSummary(true, "Account creation was unsuccessful. Please correct the errors and try again.")
<fieldset>
<legend>Registration Form</legend>
<ol>
<li>
#Html.LabelFor(m => m.UserName)
#Html.TextBoxFor(m => m.UserName)
#Html.ValidationMessageFor(m => m.UserName)
</li>
<li>
#Html.LabelFor(m => m.Email)
#Html.TextBoxFor(m => m.Email)
#Html.ValidationMessageFor(m => m.Email)
</li>
<li>
#Html.LabelFor(m => m.Password)
#Html.PasswordFor(m => m.Password)
#Html.ValidationMessageFor(m => m.Password)
</li>
<li>
#Html.LabelFor(m => m.ConfirmPassword)
#Html.PasswordFor(m => m.ConfirmPassword)
#Html.ValidationMessageFor(m => m.ConfirmPassword)
</li>
</ol>
<!-- The value property being set to register tells the form
what method of the controller to post to -->
<input type="submit" value="Register" />
</fieldset>
}
Controller
// The AccountController has methods that only authorized
// users should be able to access. However, we can override
// this with another attribute for methods that anyone
// can access
[Authorize]
public class AccountController : Controller
{
// This will allow the View to be rendered
[AllowAnonymous]
public ActionResult Register()
{
return ContextDependentView();
}
// This is one of the methods that anyone can access
// Your Html.BeginForm will post to this method and
// process what you posted.
[AllowAnonymous]
[HttpPost]
public ActionResult Register(RegisterModel model)
{
// If all of the information in the model is valid
if (ModelState.IsValid)
{
// Attempt to register the user
MembershipCreateStatus createStatus;
Membership.CreateUser(model.UserName, model.Password, model.Email, passwordQuestion: null, passwordAnswer: null, isApproved: true, providerUserKey: null, status: out createStatus);
// If the out parameter createStatus gives us a successful code
// Log the user in
if (createStatus == MembershipCreateStatus.Success)
{
FormsAuthentication.SetAuthCookie(model.UserName, createPersistentCookie: false);
return RedirectToAction("Index", "Home");
}
else // If the out parameter fails
{
ModelState.AddModelError("", ErrorCodeToString(createStatus));
}
}
// If we got this far, something failed, redisplay form
return View(model);
}
}

Categories