ASP.NET MVC Multiple form in one page: Validation doesn't work [closed] - asp.net-mvc

Closed. This question is not reproducible or was caused by typos. It is not currently accepting answers.
This question was caused by a typo or a problem that can no longer be reproduced. While similar questions may be on-topic here, this one was resolved in a way less likely to help future readers.
Closed 7 years ago.
Improve this question
I am creating a register login page in asp mvc and as i need, this page has two models and two form actions.
every thing is ok but the validation.
the models are:
public class Account_Index_ViewModel
{
public UserAccount_Login_ViewModel userAccount_Login_ViewModel { get; set; }
public UserAccount_Register_ViewModel userAccount_Register_ViewModel { get; set; }
}
public class UserAccount_Login_ViewModel
{
[Required]
[DataType(DataType.Password)]
public string Pass { get; set; }
[Required]
public string LoginName { get; set; } // NickName/Email/MobilePhone
}
public class UserAccount_Register_ViewModel
{
public string NickName { get; set; }
public string Passw { get; set; }
public string PassConfirm { get; set; }
public string Email { get; set; }
public string MobilePhone { get; set; }
}
and the view :
#model GhafasehWebSite.Models.Account_Index_ViewModel
#{
ViewBag.Title = "Index";
}
<h2>Index</h2>
<div class="AccountBook">
<div class="half-width">
#using (Html.BeginForm("Login", "Account"))
{
Html.EnableClientValidation();
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>ورود به سیستم</h4>
<hr />
#Html.ValidationSummary(true)
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Login_ViewModel)(model.userAccount_Login_ViewModel)).LoginName, new { #class = "control-label col-md-4" })
<div class="col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Login_ViewModel)(model.userAccount_Login_ViewModel)).LoginName, new { #class = "form-control", placeholder = "نام مستعار/ایمیل/شماره موبایل" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Login_ViewModel)(model.userAccount_Login_ViewModel)).LoginName)
</div>
</div>
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Login_ViewModel)(model.userAccount_Login_ViewModel)).Pass, new { #class = "control-label col-md-4" })
<div class="col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Login_ViewModel)(model.userAccount_Login_ViewModel)).Pass, new { #class = "form-control" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Login_ViewModel)(model.userAccount_Login_ViewModel)).Pass)
</div>
</div>
<div class="form-group">
<div class="col-md-offset-4 col-md-10">
<input type="submit" value="ورود" class="btn btn-primary" />
</div>
</div>
</div>
}
</div>
<div class="half-width">
#using (Html.BeginForm("Register","Account"))
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>ثبت نام در سیستم</h4>
<hr />
#Html.ValidationSummary(true)
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).NickName, new { #class = "control-label col-md-4" })
<div class=" col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).NickName, new { #class = "form-control" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).NickName)
</div>
</div>
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).Passw, new { #class = "control-label col-md-4" })
<div class=" col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).Passw, new { #class = "form-control" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).Passw)
</div>
</div>
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).PassConfirm, new { #class = "control-label col-md-4" })
<div class=" col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).PassConfirm, new { #class = "form-control" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).PassConfirm)
</div>
</div>
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).Email, new { #class = "control-label col-md-4" })
<div class=" col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).Email, new { #class = "form-control" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).Email)
</div>
</div>
<div class="form-group col-md-12">
#Html.LabelFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).MobilePhone, new { #class = "control-label col-md-4" })
<div class=" col-md-8">
#Html.TextBoxFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).MobilePhone, new { #class = "form-control" })
#Html.ValidationMessageFor(model => ((GhafasehWebAPI.Models.UserAccount_Register_ViewModel)model.userAccount_Register_ViewModel).MobilePhone)
</div>
</div>
<div class="form-group">
<div class="col-md-offset-4 col-md-10">
<input type="submit" value="ثبت نام" class="btn btn-success" />
</div>
</div>
</div>
}
</div>
</div>
<div>
#Html.ActionLink("Back to List", "Index")
</div>
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
}
and the controller:
[HttpGet]
public ActionResult Index()
{
return View(new Account_Index_ViewModel());
}
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Login(UserAccount_Login_ViewModel model)
{
if (ModelState.IsValid)
{
if (DataProvider.LoginUser(model, ModelState, Request, Session))
{
return RedirectToAction("Index", "Home");
}
}
return View("Index");
}
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Register(UserAccount_Register_ViewModel model)
{
if (ModelState.IsValid)
{
if (DataProvider.RegisterUser(model, ModelState, Request, Session))
{
return RedirectToAction("Index", "Home");
}
}
return View("Index");
}
you should know that server side validation works fine but the client side is asleep.
So, what do you suggest?

When you say the validation doesn't work what do you mean? you press Login button with empty username/password and it doesn't show required error?
If so , I Created new project with your model view controller and it worked !!! The validation works.

Related

One model for two submit buttons in ASP.NET MVC

I have a form on my view:
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group">
#Html.LabelFor(model => model.DateFrom, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.DateFrom, new { htmlAttributes = new { #class = "form-control date-picker" } })
#Html.ValidationMessageFor(model => model.DateFrom, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.DateTo, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.DateTo, new { htmlAttributes = new { #class = "form-control date-picker" } })
#Html.ValidationMessageFor(model => model.DateTo, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Create" class="btn btn-default" formAction=#Url.Action("CreateReport") />
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.EMail, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.EMail, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.EMail, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Send to email" class="btn btn-default" formAction=#Url.Action("SendEmail") />
</div>
</div>
</div>
}
As you can see I have two butons, first button call CreateReport action and than Send button call SendEmail action. I want to create report and then send this report by e-mail.
Here is my controller actions:
public ActionResult Index()
{
Report
report=ReportRepository.GetReport(DateTime.Parse("02.08.1996"), DateTime.Parse("07.08.1996"));
return View(report);
}
public ActionResult CreateReport(Report report)
{
report = ReportRepository.GetReport(report);
return View("Index", report);
}
public ActionResult SendEmail(Report report)
{
return View("Index", report);
}
And my model class:
public class Report
{
public DateTime DateFrom { get; set; }
public DateTime DateTo { get; set; }
public List<OrderDetails> Orders { get; set; }
[Display(Name = "Email address")]
[EmailAddress(ErrorMessage = "Invalid Email Address")]
public string EMail { get; set; }
}
So I mean that I fill Orders list in CreateReport action and display it and after it I press "Send to email" button, that's call "SendEmail" action, where I save Orders list to file and send it.
The problem is that in "SendEmail" action List is null.
How can I fix it?
The simplest way that I could think of is to remove your submit action for create report and handle this with ajax call. So that you will have only one submit action.
Or else you can try with 2 forms in your View.
Personally, I prefer the 1st option.
I'v found a solution. The solution is not to pass model to controller but store my List in Session. Like this:
public ActionResult Index()
{
Report report=ReportRepository.GetReport(DateTime.Parse("02.08.1996"), DateTime.Parse("07.08.1996"));
Session["Orders"] = report.Orders;
return View(report);
}
public ActionResult CreateReport(Report report)
{
report = ReportRepository.GetReport(report);
Session["Orders"] = report.Orders;
return View("Index", report);
}
public ActionResult SendEmail(Report report)
{
List<OrderDetails> orders = (List<OrderDetails>)Session["Orders"];
report.Orders = orders;
return View("Index", report);
}

how to bind dropdown using foreign key in mvc

trying to bind the BrandName column drop down but i am unable to get it..can any one help me to get this.
Here is my code:
public class ApplicationUser : IdentityUser
{
[Column(Order = 1), ForeignKey("Brands")]
public int BrandId { get; set; }
public virtual Brands Brands { get; set; }
}
public class Brands
{
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
public string BrandName { get; set; }
public string ContactPerson { get; set; }
public string ContactNumber { get; set; }
}
controller code:
public ActionResult Register()
{
ViewBag.Name = new SelectList(context.Roles.Where(u => !u.Name.Contains("Admin"))
.ToList(), "Name", "Name");
return View();
}
Register.chstml code:
#using (Html.BeginForm("Register", "Account", FormMethod.Post, new { #class = "form-horizontal", role = "form" }))
{
#Html.AntiForgeryToken()
<h4>Create a new account.</h4>
<hr />
#Html.ValidationSummary()
<div class="form-group">
#Html.LabelFor(m => m.UserName, new { #class = "col-md-2 control-label" })
<div class="col-md-10">
#Html.TextBoxFor(m => m.UserName, new { #class = "form-control" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(m => m.Password, new { #class = "col-md-2 control-label" })
<div class="col-md-10">
#Html.PasswordFor(m => m.Password, new { #class = "form-control" })
</div>
</div>
<div class="form-group">
#Html.LabelFor(m => m.ConfirmPassword, new { #class = "col-md-2 control-label" })
<div class="col-md-10">
#Html.PasswordFor(m => m.ConfirmPassword, new { #class = "form-control" })
</div>
</div>
<div class="form-group">
#Html.Label("User Role", new { #class = "col-md-2 control-label" })
<div class="col-md-10">
#Html.DropDownList("UserRoles", (SelectList)ViewBag.Name, " ", new { #class = "form-control" })
</div>
</div>
<div class="form-group">
#Html.Label("Brand Id", new { #class = "col-md-2 control-label" })
<div class="col-md-10">
#Html.DropDownList("BrandId",(SelectList)ViewBag.BrandNamenew,"",new{ #class = "form-control" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" class="btn btn-default" value="Register" />
</div>
</div>
}
how to write controller and cshtml code to bind BrandId dropdown

Why returened values of form are null in MVC project?

I try to update a record .I use validation in this view but always
ModelState.IsValid = false
I search on the internet and found that I should check errors with this code :
var errors = ModelState.Values.SelectMany(v => v.Errors);
Now I can not understand that what is problem?
In this image you can see that all parameters are null.
Please advice.
View:
#model TravelEnterAdminTemplate.Models.LG.ResturantModel
#{
ViewBag.Title = "EditRestaurant";
Layout = "~/Views/Shared/_Layout.cshtml";
}
#*fck Editor*#
<script type="text/javascript" src="#Url.Content("~/Content/Adminex/js/fckEditor/fckeditor.js")"></script>
<script type="text/javascript">
window.onload = function () {
var sBasePath = '#Url.Content("~/Content/Adminex/js/fckeditor/")';
var oFCKeditor = new FCKeditor('Restaurants_Description');
oFCKeditor.BasePath = sBasePath;
oFCKeditor.Height = 450;
oFCKeditor.Width = 800;
oFCKeditor.ReplaceTextarea();
//----------------------DescriptionEn---------------------
var oFCKeditorEn = new FCKeditor('Restaurants_DescriptionEn');
oFCKeditorEn.BasePath = sBasePath;
oFCKeditorEn.Height = 450;
oFCKeditorEn.Width = 800;
oFCKeditorEn.ReplaceTextarea();
}
</script>
<div class="container">
<h4>ویرایش رستوران</h4>
<hr />
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
#Html.HiddenFor(model => model.Restaurants.id)
<div class="row">
<div class="col-md-4 pull-right">
#Html.LabelFor(model => model.Restaurants.RestaurantName, htmlAttributes: new { #lablefor = "RestaurantName" })
#Html.EditorFor(model => model.Restaurants.RestaurantName, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.RestaurantName, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-7 pull-right">
#Html.LabelFor(model => model.Restaurants.Address, htmlAttributes: new { #lablefor = "Address" })
#Html.EditorFor(model => model.Restaurants.Address, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.Address, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-2 pull-right">
#Html.LabelFor(model => model.Restaurants.City.Country.NameFa, htmlAttributes: new { #lablefor = "CountryId" })
#Html.DropDownList("CountryId", null, new { #class = "form-control" })
</div>
</div>
<div class="row">
<div class="col-md-2 pull-right">
<div>
#Html.LabelFor(model => model.Restaurants.City.NameFA, htmlAttributes: new { #lablefor = "CityId" })
#Html.DropDownList("CityId", null, new { #class = "form-control" })
</div>
</div>
</div>
<div class="row">
<div class="col-md-2 pull-right">
#Html.LabelFor(model => model.Restaurants.Tell, htmlAttributes: new { #lablefor = "Tell" })
#Html.EditorFor(model => model.Restaurants.Tell, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.Tell, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-4 pull-right">
#Html.LabelFor(model => model.Restaurants.Title, htmlAttributes: new { #lablefor = "Title" })
#Html.EditorFor(model => model.Restaurants.Title, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">
#Html.ValidationMessageFor(model => model.Restaurants.Title, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-3 pull-right">
#Html.LabelFor(model => model.Restaurants.InsertDate, htmlAttributes: new { #lablefor = "InsertDate" })
#Html.EditorFor(model => model.Restaurants.InsertDate, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.InsertDate, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-5 pull-right">
#Html.LabelFor(model => model.Restaurants.Summary, htmlAttributes: new { #lablefor = "Summary" })
#Html.EditorFor(model => model.Restaurants.Summary, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">
#Html.ValidationMessageFor(model => model.Restaurants.Summary, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-8 pull-right">
#Html.LabelFor(model => model.Restaurants.Description, htmlAttributes: new { #lablefor = "Description" })
#Html.EditorFor(model => model.Restaurants.Description, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.Description, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-3 pull-right">
#Html.LabelFor(model => model.Restaurants.LocationX, htmlAttributes: new { #lablefor = "LocationX" })
#Html.EditorFor(model => model.Restaurants.LocationX, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">
#Html.ValidationMessageFor(model => model.Restaurants.LocationX, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-3 pull-right">
#Html.LabelFor(model => model.Restaurants.LocationY, htmlAttributes: new { #lablefor = "LocationY" })
#Html.EditorFor(model => model.Restaurants.LocationY, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.LocationY, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-3 pull-right">
#Html.LabelFor(model => model.Restaurants.Website, htmlAttributes: new { #lablefor = "Website" })
#Html.EditorFor(model => model.Restaurants.Website, new { htmlAttributes = new { #class = "form-control website" } })
</div>
<div class="col-md-4 pull-right">#Html.ValidationMessageFor(model => model.Restaurants.Website, "", new { #class = "text-danger" })</div>
</div>
<div class="row">
<div class="col-md-5 pull-right">
<div class="checkbox">
#Html.LabelFor(model => model.Restaurants.IsActive, htmlAttributes: new { #lablefor = "IsActive" })
#Html.EditorFor(model => model.Restaurants.IsActive)
</div>
<div class="col-md-4 pull-right">
#Html.ValidationMessageFor(model => model.Restaurants.IsActive, "", new { #class = "text-danger" })
</div>
</div>
</div>
#*-------------------------------------------------------------------------------------*#
<fieldset dir="ltr" class="fieldsetEn">
<legend>English Content</legend>
<div class="row">
<div class="col-md-5">
<div class="checkbox checkboxEn">
#Html.LabelFor(model => model.Restaurants.IsEnglish, htmlAttributes: new { #Labelfor = "IsEnglish" })
#Html.EditorFor(model => model.Restaurants.IsEnglish)
</div>
<div class="col-md-4 ">
#Html.ValidationMessageFor(model => model.Restaurants.IsEnglish, "", new { #class = "text-danger" })
</div>
</div>
</div>
<div class="row">
<div class="col-md-4">
#Html.LabelFor(model => model.Restaurants.RestaurantNameEn, htmlAttributes: new { #Labelfor = "RestaurantNameEn" })
#Html.EditorFor(model => model.Restaurants.RestaurantNameEn, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 ">
#Html.ValidationMessageFor(model => model.Restaurants.RestaurantNameEn, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-7">
#Html.LabelFor(model => model.Restaurants.AddressEn, htmlAttributes: new { #Labelfor = "AddressEn" })
#Html.EditorFor(model => model.Restaurants.AddressEn, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 ">
#Html.ValidationMessageFor(model => model.Restaurants.AddressEn, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-4">
#Html.LabelFor(model => model.Restaurants.TitleEn, htmlAttributes: new { #Labelfor = "TitleEn" })
#Html.EditorFor(model => model.Restaurants.TitleEn, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 ">
#Html.ValidationMessageFor(model => model.Restaurants.TitleEn, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-5">
#Html.LabelFor(model => model.Restaurants.SummaryEn, htmlAttributes: new { #Labelfor = "" })
#Html.EditorFor(model => model.Restaurants.SummaryEn, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 ">
#Html.ValidationMessageFor(model => model.Restaurants.SummaryEn, "", new { #class = "text-danger" })
</div>
</div>
<div class="row">
<div class="col-md-7">
#Html.LabelFor(model => model.Restaurants.DescriptionEn, htmlAttributes: new { #Labelfor = "DescriptionEn" })
#Html.TextAreaFor(model => model.Restaurants.DescriptionEn, new { htmlAttributes = new { #class = "form-control" } })
</div>
<div class="col-md-4 ">
#Html.ValidationMessageFor(model => model.Restaurants.DescriptionEn, "", new { #class = "text-danger" })
</div>
</div>
</fieldset>
#{
string path = System.Configuration.ConfigurationManager.AppSettings["ImageEdit"];
}
<div class="row text-right">
#foreach (var item in Model.PhotoTables)
{
<text>
<div class="col-xs-2 col-wrapper pull-right">
<div class="image-wrapper">
<img src="#Url.Content(path + item.PhotoName)" alt="" class=" img-responsive" />
<img class="delimg" src="~/Content/Adminex/images/delete-icons.png" id="#item.Id" alt="حذف تصویر" />
</div>
</div>
</text>
}
</div>
<br />
<br />
<div class="row">
<div class="col-md-4"></div>
<div class="col-md-4">
<input type="submit" value="ذخیره تغییرات" class="btn btn-info btn-block" />
</div>
<div class="col-md-4"></div>
</div>
</div>
}
</div>
<script src="~/Content/Adminex/js/ajax/Restaurants_Edit.js"></script>
#section Scripts {
#Scripts.Render("~/bundles/jqueryValidation")
}
Model:
//------------------------------------------------------------------------------
// <auto-generated>
// This code was generated from a template.
//
// Manual changes to this file may cause unexpected behavior in your application.
// Manual changes to this file will be overwritten if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------
namespace TravelEnterAdminTemplate.Models.dbModel
{
using System;
using System.Collections.Generic;
public partial class Restaurant
{
public int id { get; set; }
public int CityId { get; set; }
public string RestaurantName { get; set; }
public string Address { get; set; }
public string Tell { get; set; }
public string Title { get; set; }
public System.DateTime InsertDate { get; set; }
public string Summary { get; set; }
public string Description { get; set; }
public string LocationX { get; set; }
public string LocationY { get; set; }
public string UserId { get; set; }
public int Visitor { get; set; }
public bool IsActive { get; set; }
public string Website { get; set; }
public int CategoryId { get; set; }
public string RestaurantNameEn { get; set; }
public string AddressEn { get; set; }
public string TitleEn { get; set; }
public string SummaryEn { get; set; }
public string DescriptionEn { get; set; }
public Nullable<int> VisitorEn { get; set; }
public bool IsEnglish { get; set; }
public virtual AspNetUser AspNetUser { get; set; }
public virtual City City { get; set; }
}
}
I sometimes use Code like this for debugging. (written from memory)
var errors = new List<KeyValuePair<string, string>();
for (int i = 0; i < ModelState.Keys.Count; i++)
{
var value = ModelState.Values.ElementAt(i);
if value.Errors.Any()
{
foreach (var error in Value.Errors)
{
errors.Add(new KeyValuePair<string, string>
(ModelState.Keys.ElementAt(i),
error.Message ?? error.Exception.Message);
}
}
}
This should help you diagnose which model elements are causing validation errors.
A common reason for server side validation errors is that a non-nullable int or Guid Id field is included in the model but is either not included in the view, or is hidden and / or not populated.
that's not how you post though.
your post method should be very simple, something like :
public async Task Post(ModelClass someName)
so you basically have a model class. That class needs to be decorated with [DataContract] which needs a reference to System.Runtime.Serialization
Each property in that class that you want to be able to send as part of a post needs to then have a DataMember tag on it. This way the default serialization used by the MVC engine will kick in and accept your post as long as the names passed by the form match those in the model exactly. This applies especially when we work with WebApi. For pure MVC work we don't need those tags
Always do model validation first :
if (!ModelState.IsValid) then return an error code
every validation item you have on your model properties needs to happen before the ModelState will be valid.
Here's a basic example which I wrote a few years ago, maybe it will help :
mvc article

MVC strongly typed view data

I have a strongly typed view that creates the form fields like this:
#Html.TextBoxFor(x => x.Name, new { #class = "form-control" })
That's fine, X in the above lambda expression relates to a class I've created with a property of 'Name'.
How do I use this same view but have access to the properties of a different class? For example if you imagine I've another class called - UserDetails, and email address is a property of that. How can I do this:
#Html.TextBoxFor(x => x.Email, new { #class = "form-control" })
within the same strongly typed view?
In asp.net mvc you pass model to view like this:
public ActionResult Base()
{
return View(new DerviedOne());
}
And here is your models definitions :
public class BaseModel
{
public int Id { get; set; }
}
public class DerviedOne : BaseModel
{
public string Email { get; set; }
}
public class DerviedTwo : BaseModel
{
public string Name { get; set; }
}
Then you have to create three views:
Base View:
#using Models
#model Models.BaseModel
#{
ViewBag.Title = "Base";
Layout = "~/Views/Shared/_Layout.cshtml";
}
<h2>Base</h2>
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>BaseModel</h4>
<hr/>
#Html.ValidationSummary(true, "", new {#class = "text-danger"})
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
#Html.TextBoxFor(x=>x.Id)
<input type="submit" value="Create" class="btn btn-default"/>
</div>
</div>
</div>
if(Model is DerviedOne)
{
Html.RenderPartial("DerviedOneView", Model as DerviedOne);
}
if (Model is DerviedTwo)
{
Html.RenderPartial("DerviedTwoView", Model as DerviedTwo);
}
}
Second view:
#model WebApplication.Models.DerviedOne
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>DerviedOne</h4>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group">
#Html.LabelFor(model => model.Email, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Email, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Email, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Create" class="btn btn-default" />
</div>
</div>
</div>
}
Third view:
#model WebApplication.Models.DerviedTwo
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>DerviedTwo</h4>
<hr />
#Html.ValidationSummary(true, "", new { #class = "text-danger" })
<div class="form-group">
#Html.LabelFor(model => model.Name, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Name, new { htmlAttributes = new { #class = "form-control" } })
#Html.ValidationMessageFor(model => model.Name, "", new { #class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Create" class="btn btn-default" />
</div>
</div>
</div>
}

How do I pass a ViewModel to an Edit Action in ASP.NET MVC 5

I'm learning about using ViewModels to pass information from the view to the controller and vice versa. I have my create action, view, and viewmodel working perfectly but I'm having trouble with the edit one. I get the error:
The model item passed into the dictionary is of type 'CatVM.Models.Cat', but this dictionary requires a model item of type 'CatVM.Models.EditCatViewModel'.
Here is my code:
Controller Method
// GET: /Cats/Edit/5
public ActionResult Edit(int? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
Cat cat = unitOfWork.CatRepository.GetByID(id);
if (cat == null)
{
return HttpNotFound();
}
return View(cat);
}
View
#model CatVM.Models.EditCatViewModel
#{
ViewBag.Title = "Edit";
}
<h2>Edit</h2>
#using (Html.BeginForm())
{
#Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>Cat</h4>
<hr />
#Html.ValidationSummary(true)
#Html.HiddenFor(model => model.ID)
<div class="form-group">
#Html.LabelFor(model => model.Name, new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Name)
#Html.ValidationMessageFor(model => model.Name)
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Color, new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Color)
#Html.ValidationMessageFor(model => model.Color)
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.FurLength, new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.FurLength)
#Html.ValidationMessageFor(model => model.FurLength)
</div>
</div>
<div class="form-group">
#Html.LabelFor(model => model.Size, new { #class = "control-label col-md-2" })
<div class="col-md-10">
#Html.EditorFor(model => model.Size)
#Html.ValidationMessageFor(model => model.Size)
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Save" class="btn btn-default" />
</div>
</div>
</div>
}
<div>
#Html.ActionLink("Back to List", "Index")
</div>
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
}
EditCatViewModel
public class EditCatViewModel
{
public int ID { get; set; }
[Required]
[StringLength(50)]
public string Name { get; set; }
[Required]
[StringLength(50)]
public string Color { get; set; }
[Required]
[StringLength(50)]
[Display(Name = "Fur Type")]
public string FurLength { get; set; }
[StringLength(50)]
public string Size { get; set; }
}
}
That's because the item you receive from CatRepository.GetByID(id); is of type Cat, not EditCatViewModel.
You can bypass this by constructing a new viewmodel from this object:
Cat cat = unitOfWork.CatRepository.GetByID(id);
var viewModel = new EditCatViewModel {
Name = cat.Name,
Color = cat.Color,
FurLength = cat.FurLength,
Size = cat.Size
};
return View(viewModel);
Alternatively you could construct implicit or explicit casting methods or use a mapping tool like AutoMapper.
Your return view should be of type CatVM.Models.EditCatViewModel now your returning a Cat
return View(cat);
transform your model in a view model and pass this object back to the view

Resources