Displaying Invalid user name or password using MVC Validation - asp.net-mvc

I am using MVC validation to check if use name and password exit in database or not. ModelState.IsValid is true always even when I did not find any matching user.
if (objModel != null)
{
if (ModelState.IsValid && Membership.ValidateUser(objUsersModel.UserName, objUsersModel.Password))
{
Profile.Initialize(objUsersModel.UserName.Trim(), true);
FormsAuthentication.SetAuthCookie(objUsersModel.UserName, false);
return RedirectToAction("Index", "Home");
}
}
How can I set this to false and set the values for error message in mvc view. Here is my MVC view .
<form role="form">
<div class="form-group">
<label for="exampleInputEmail1">User Name </label>
<i class="fa fa-user"></i>
#Html.TextBoxFor(m => m.UserName, new { maxlength = 50, #class = "form-control" })
#Html.ValidationMessageFor(u => u.UserName)
</div>
<div class="form-group">
<label for="exampleInputPassword1">Password</label>
<i class="fa fa-lock"></i>
#Html.PasswordFor(m => m.Password, new { maxlength = 50, #class = "form-control" })
#Html.ValidationMessageFor(u => u.Password)
</div>
<div class="form-actions">
<label class="checkbox"> <input type="checkbox" class="uniform" value=""> Remember me</label>
<button type="submit" class="btn btn-danger">Submit</button>
</div>
</form>

You need to add a ModelState error and return the view if the user name and password are not valid
if (!ModelState.IsValid)
{
return View(yourModel);
}
if (!Membership.ValidateUser(objUsersModel.UserName, objUsersModel.Password)
{
ModelState.AddModelError(string.Empty, "The user name or password is incorrect");
return View(yourModel);
}
....
return RedirectToAction("Index", "Home");
and in the view, include
#Html.ValidationSummary(true)
to display the message

Related

ASP.NET MVC Not logged in successfully showing 404 error

I have a ASP.NET MVC app running with Forms Authenticated enabled.
In my own machine and browser (Edge,IE,chrome), I am able to login in my website.
It works for other users as well. But, for some users, they are not able to login to the home page of the website and it is going to 404 page not found error....
I am sharing my code behind..
Login action method
[HttpPost]
[AllowAnonymous]
public ActionResult LoginUser(LoginUser login)
{
if (ModelState.IsValid)
{
if(AuthenticateUserAD(login) != "")
{
FormsAuthentication.SetAuthCookie(login.UserName, login.RememberMe);
if (login.RememberMe)
{
HttpCookie cookie = new HttpCookie("Login");
cookie.Values.Add("UserName", login.UserName);
cookie.Values.Add("Password", login.Password);
cookie.Expires = DateTime.Now.AddDays(10);
Response.Cookies.Add(cookie);
}
ViewBag.IsLoginValid = "Valid";
return RedirectToAction("Index", "Service");
}
else
{
ViewBag.Invalid = Session["error"].ToString();
ViewBag.IsLoginValid = "Invalid";
return View("LoginUser");
}
}
else
{
ModelState.AddModelError("", "The user name or password provided is incorrect");
}
return View(login);
}
LoginUser.cshtml
#using (Html.BeginForm("LoginUser", null, FormMethod.Post))
{
<div class="row mt-5">
<div class="col-6 col-sm-6 offset-3 bodyColor" style="border-radius: 25px;">
<div class="col-8 col-sm-8 offset-2">
<div style="max-width: 400px;">
<div class="text-center section-title">
<h2>Login</h2>
</div>
#Html.LabelFor(model => model.UserName)
<div class="input-group form-group">
<div class="input-group-prepend">
<span class="input-group-text date-Textbox"><i class="fa fa-user"></i></span>
</div>
#Html.TextBoxFor(model => model.UserName, new { #class = "form-control textbox-font" })
#Html.ValidationMessageFor(model => model.UserName, "", new { #class = "textRed" })
</div>
#Html.LabelFor(model => model.Password)
<div class="input-group form-group">
<div class="input-group-prepend">
<span class="input-group-text date-Textbox"><i class="fa fa-lock"></i></span>
</div>
#Html.TextBoxFor(model => model.Password, new { #class = "form-control textbox-font", type = "password" })
#Html.ValidationMessageFor(model => model.Password, "", new { #class = "textRed" })
</div>
#Html.CheckBoxFor(model => model.RememberMe)
#Html.LabelFor(model => model.RememberMe)
<input type="hidden" name="ReturnUrl" value="#Request.QueryString["ReturnUrl"]" />
<div class="col-sm-12 col-xs-12">
<input type="submit" value="Login" id="btnLogin" style="width:100%;" autofocus class="btn btn-main-custom" />
</div>
</div>
</div>
}
I really do not know whether this is a browser problem or a development problem or cookies problem.
Appreciate any help, Could anyone find a solution or a workaround?
Thanks

How to validate a duplicate post request from a form in MVC

I am having an form which insert a record whenever a post request is made,but the problem is that if someone clicks submit button more than 1 times than duplicate post request are made and at the end same records are getting inserted. I dont want to check that the record is already present or not because the record would be different always. I tried using ValidateAntiForgeryToken filter in controller but it is failing to validate the requests, Below is my View Code.
#using (Html.BeginForm("Create", "Home",FormMethod.Post,new { onkeydown = "return event.keyCode!=13" }))
{
#Html.AntiForgeryToken()
<div class="right-col">
#Html.TextBoxFor(model => model.Name, new { placeholder = "Name", #class = "small-box" })
</div>
<div class="left-col">Email Id :</div>
<div class="right-col">
#Html.TextBoxFor(model => model.EmailId, new { placeholder = "Email Id", #class = "small-box",id="resumeemailid" })
#Html.ValidationMessageFor(model => model.EmailId)
</div>
<div class="left-col">Address :</div>
<div class="right-col">
#Html.TextAreaFor(model => model.Address, new { placeholder = "Address", #class = "small-box" })
</div>
<div class="buttons resume-threebutton">
<input type="submit" id="register-button" class="gradient-btn" value="#T("Account.Passport.Register.Button.Upload", "Upload")" name="Command" />
<input type="submit" id="register-button" class="gradient-btn" value="#T("Account.Passport.Button.UploadandAdd", "Upload And Add New")" name="Command" />
<input type="button" id="register-button" class="gradient-btn" value="#T("Account.Passport.Register.Button.Cancel", "cancel")" name="register-button" onclick="location.href='#Url.Action("SelectTemplate", "CustomerTemplate")'" />
</div>
}
and below is my controller Post method
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(ProductModel model)
{
//To do add the product here...
}

How to check if any model item is assigned a value in MVC?

I have a model which have properties.And, i want to check that if any model item has some value or not.Also,no property is set to mandatory or optional using data-annotations.If no property is assigned and any value then i should set some model error e.g "Please specify some search criteria."
#using (Html.BeginForm("GetAdvanceSearchData", "Home", FormMethod.Post)){
<div class="rTableCell" style="border:none !important">
#Html.TextBoxFor(m => m.MessageStatus, new { placeholder = Html.DisplayNameFor(n => n.MessageStatus), #class = "fieldtextbox", #style = "height: 25px !important" })
#Html.ValidationMessageFor(m => m.MessageStatus)
</div>
<div class="rTableCell" style="border:none !important">
#Html.TextBoxFor(m => m.RequestType, new { placeholder = Html.DisplayNameFor(n => n.RequestType), #class = "fieldtextbox", #style = "height: 25px !important" })
#Html.ValidationMessageFor(m => m.RequestType)
</div>
<div class="rTableCell" style="border:none !important">
</div>
<div class="rTableCell" style="border:none !important">
<p class="submit">
<button type="submit" name="submit">
<i class="fa fa-arrow-right" aria-hidden="true"></i>
</button>
</p>
</div>
}
These are only few properties for the model.
In action method GetAdvanceSearchData you can do your own validity checks, in addition to validation attributes, or instead of them.
If you add an entry to ModelState then ModelState.IsValid will become false, and the added entry will show in the output of Html.ValidationMessageFor(...) or Html.ValidationSummary().
Example:
[HttpPost]
public ActionResult GetAdvanceSearchData(YourModel vm)
{
if (vm == null || (string.IsNullOrEmpty(vm.MessageStatus) && string.IsNullOrEmpty(vm.RequestType)))
{
ModelState.AddModelError("", "Please specify some search criteria")
// Using "" as Key will only show when you use #Html.ValidationSummary().
// Using "myErr" as Key will show when you use #Html.ValidationMessage("myErr").
// Using a property name as Key will show it next to the property if you use #Html.ValidationMessageFor(m => m.property).
}
if (ModelState.IsValid)
{
var results = ...
return View("ResultsView", results);
}
else
{
return View(vm);
}
}

Why Http Get action is called instead of Http post action?

I'm working with MVC and spent whole day getting stuck with this problem. Here is code at the controller:
public class CMController : Controller
{
public ActionResult SignUp()
{
return View("SignUpPage");
}
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult SignUp(User u)
{
if (ModelState.IsValid)
{
using (CmdbEntities dc = new CmdbEntities())
{
dc.Users.Add(u);
dc.SaveChanges();
ModelState.Clear();
u = null;
ViewBag.Message = ("Successfully sign on");
}
}
else
{
ViewBag.Message = ("Error");
}
return View("Welcome");
}
}
Here is the SignUpPage.cshtml view:
#using (Html.BeginForm("SignUp", "CM", FormMethod.Post))
{
#Html.AntiForgeryToken()
<div class="form-group" style="padding:5px 50px">
<label> First name:</label>
<div>
#Html.TextBoxFor(model => model.FirstName, new {#class="form-control", placeholder="Enter first name", ID="FirstName"})
</div>
</div>
<div class="form-group" style="padding:5px 50px">
<label >Last name:</label>
<div>
#Html.TextBoxFor(model => model.LastName, new {#class="form-control", placeholder="Enter first name", ID="LastName"})
</div>
</div>
<div class="form-group" style="padding:5px 50px">
<label for="email">Email:</label>
<div>
#Html.TextBoxFor(model => model.Email, new {#class="form-control", placeholder="Enter email", ID="Email", type="email"})
</div>
</div>
<div class="form-group" style="padding:5px 50px">
<label >User name:</label>
<div>
#Html.TextBoxFor(model => model.UserName, new {#class="form-control", placeholder="Enter user name", ID="UserName"})
</div>
</div>
<div class="form-group" style="padding:5px 50px">
<label for="pwd">Password:</label>
<div>
#Html.TextBoxFor(model => model.Password, new {#class="form-control", placeholder="Enter password", ID="Password", type="password"})
</div>
</div>
<div class="form-group" style="padding:5px 50px">
<label for="pwd">Confirm password:</label>
<div>
#Html.TextBoxFor(model => model.ConfirmPassword, new {#class="form-control", placeholder="Re-enter password", ID="_password", type="password"})
</div>
</div>
<div class="form-group" style="padding:5px 50px">
<div>
<input type="submit" ID="SignUp" class="btn btn-success" value="Sign Up" />
</div>
</div>
}
The problem is, when load page first time, the action SignUp() is called which is correct. But when submit the form, SignUp() is called again instead of the post action SignUp(User u).
One more problem, even the form has post method, when click submit the url contains input information just like get method, I don't understand.
Here is the page html source of form tag.
<form action="/CM/SignUp" method="post"><input name="__RequestVerificationToken" type="hidden" value="VJ0YcQr1Z-l3Qo717pRpZNT-QtL59G2EJXy2JQL8NFnOm-XoNnAD-8T-Itz3i1EboGj0bhpBf2G26ifxm4F5ZRyKimkOyZW1AxZ3ckPNuRk1" />
Please help, thank you.
Can you please try adding
[AllowAnonymous]
to the post method?
Did you activate global authorization anywhere
System.Web.Mvc.AuthorizeAttribute
?

Retrieving dropdown values from partial view during post method

I need to get the selected dropdown value from partial view and included in the CategoryID in the Book class...
[Authorize]
public PartialViewResult GetAllCategory()
{
ProcessSVC.Category newCategory = new ProcessSVC.Category();
newCategory.ChildCategories = obj1.GetAllCategories(String.Empty);
return PartialView(newCategory);
}
GetAllCategory.cshtml (PartialView)
#model MvcAdminTemplate.ProcessSVC.Category
#Html.DropDownListFor(m => m.ParentID, new SelectList(Model.ChildCategories, "ID", "DisplayName"), new { #class = "form-control" })
Create View:
[Authorize]
[HttpPost]
public ActionResult Create()
{
MvcAdminTemplate.ProcessSVC.Book oBook = new ProcessSVC.Book();
return View(oBook);
}
Create.cshtml
#model MvcAdminTemplate.ProcessSVC.Book
#{
ViewBag.Title = "Create";
}
#Html.Partial("_LeftMenu")
<!-- content -->
<h2>Create</h2>
<div class="col-md-10">
#using (Html.BeginForm("Create", "Books", FormMethod.Post, new { enctype = "multipart/form-data" }))
{
<div class="row">
<div class="bootstrap-admin-no-table-panel-content bootstrap-admin-panel-content collapse in">
<form class="form-horizontal">
<fieldset>
<legend>Add Book</legend>
<div class="form-group">
<div class="col-lg-2">
#Html.LabelFor(m => m.BookName, new { #class = "control-label" })
</div>
<div class="col-lg-10">
#Html.TextBoxFor(m => m.BookName, new { #class = "form-control", type = "text" })
<p class="help-block"> </p>
</div>
</div>
<div class="form-group">
<div class="col-lg-2">
#Html.LabelFor(m => m.Description, new { #class = " control-label" })
</div>
<div class="col-lg-10">
#Html.TextBoxFor(m => m.Description, new { #class = "form-control ", type = "text" })
<p class="help-block"> </p>
</div>
</div>
<div class="form-group divCategory">
<div class="col-lg-2">
#Html.Label("Parent Category", new { #class = " control-label" })
</div>
<div class="col-lg-10">
#Html.HiddenFor(m => m.BookId, new { #class = "hdn-id" })
#Html.Action("GetAllCategory","Books")
<span class="help-block"> </span>
</div>
<button type="submit" class="btn btn-primary">Save changes</button>
<button type="reset" class="btn btn-default">Cancel</button>
</div>
</fieldset>
</form>
</div>
</div>
}
After submission of the above form i need to get Book attributes and Category "Selected Category".
[Authorize]
[HttpPost]
public ActionResult Create(ProcessSVC.Book oBook)
{
oBook.LanguageID = 1;
_service.AddBooks(oBook.ActualPrice,oBook.ActualPriceString, oBook.Author, oBook.BookId, oBook.BookName, oBook.CategoryID, oBook.Currency, oBook.CurrentPrice, oBook.CurrentPriceString,
oBook.Description, oBook.DiscountPercentage, oBook.DiscountValue, oBook.LanguageID,
oBook.NativeLanguageName, oBook.Publisher);
TempData.Add("SuccessMessage", " New book " + oBook.BookName + " Added !");
return RedirectToAction("Index");
}
Please suggest me.
To correctly bind your model, you need to create the dropdown in the main view. This line in you partial view
#Html.DropDownListFor(m => m.ParentID, ....
will render a select
<select name="ParentID" ...
but you model is expecting a property named CategoryID
In you Create() method, generate the SelectList and assign to a view model property or to ViewBag and then (instead or #Html.Action("GetAllCategory","Books") use
#Html.DropDownListFor(m => m.CategoryID, ....
use this line in your GetAllCategory.cshtml file
#Html.DropDownList("CategoryID", new SelectList(Model.ChildCategories, "ID", "DisplayName"), new { #class = "form-control" })

Resources