我在部分 View 中有一个登录表单,该表单位于主模板(布局)的模式中。单击按钮后,将出现登录表单,用户应填写该表单,直到一切正常,但每当用户单击登录按钮时,数据都会发送到服务器进行验证,如果数据正常,则用户将被重定向到网站安全区域,但如果没有,用户就会丢失,因为页面已刷新并且模式未显示回来,因此用户必须单击返回登录以预览模式,然后看到错误!我想实现一个ajax登录,当用户单击登录按钮时,如果数据正确,则应重定向到网站安全区域,否则应给出错误。这是登录的部分 View 。
@model Hire.af.WebUI.Models.LoginViewModel
<!--Login Form-->
@using (Html.BeginForm("Login", "Account", new { ReturnUrl = ViewBag.ReturnUrl }, FormMethod.Post, new { @class = "noo-ajax-login-form form-horizontal", role = "form" }))
{
@Html.AntiForgeryToken()
<hr />
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="form-group row">
<div class="col-sm-9">
@Html.TextBoxFor(m => m.Email, new { @class = "log form-control", @placeholder="Email OR Username" })
@Html.ValidationMessageFor(m => m.Email, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group row">
@Html.LabelFor(m => m.Password, new { @class = "col-sm-3 control-label" })
<div class="col-sm-9">
@Html.PasswordFor(m => m.Password, new { @class = "pwd form-control", @placeholder="Password" })
@Html.ValidationMessageFor(m => m.Password, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group row">
<div class="col-sm-9 col-sm-offset-3">
<div class="checkbox">
<div class="form-control-flat">
<label class="checkbox">
@Html.CheckBoxFor(m => m.RememberMe, new { @class = "rememberme", @type = "checkbox" })
<i></i> Remember Me
</label>
</div>
</div>
</div>
</div>
<!--Remember Me Checkbox-->
<div class="form-actions form-group text-center">
<input type="submit" value="Sign In" class="btn btn-primary" />
<div class="login-form-links">
<span><a href="#"><i class="fa fa-question-circle"></i> Forgot Password?</a></span>
<span>
Don't have an account yet?
<a href="#" class="member-register-link" data-rel="registerModal">
@Html.ActionLink("Register Now", "Register") <i class="fa fa-long-arrow-right"></i>
</a>
</span>
</div>
</div>
@* Enable this once you have account confirmation enabled for password reset functionality
<p>
@Html.ActionLink("Forgot your password?", "ForgotPassword")
</p>*@
}
如有任何帮助,我们将不胜感激。谢谢。
Samit Patel 的编辑1:这是登录的 Controller 操作方法
// GET: /Account/Login
[AllowAnonymous]
public ActionResult Login(string returnUrl)
{
ViewBag.ReturnUrl = returnUrl;
return View();
}
//
// POST: /Account/Login
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public async Task<ActionResult> Login(LoginViewModel model, string returnUrl)
{
if (!ModelState.IsValid)
{
return View(model);
}
// This doesn't count login failures towards account lockout
// To enable password failures to trigger account lockout, change to shouldLockout: true
var result = await SignInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, shouldLockout: false);
switch (result)
{
case SignInStatus.Success:
return RedirectToLocal(returnUrl);
case SignInStatus.LockedOut:
return View("Lockout");
case SignInStatus.RequiresVerification:
return RedirectToAction("SendCode", new { ReturnUrl = returnUrl, RememberMe = model.RememberMe });
case SignInStatus.Failure:
default:
ModelState.AddModelError("", "Invalid login attempt.");
return View(model);
}
}
最佳答案
实际上,您应该将模型来回传递给 View 和 Controller ,因此术语 MVC( Model View Controller )。我将创建一个 WebLogin.cs 模型,这样您就可以验证模型的状态。我对上述代码遇到的最大问题是您包含了防伪 token ,但您没有以任何方式处理它,这使得包含它毫无意义。
网络登录{
[Required]
public string Name {get;set;}
[Required]
public string Password {get;set;}
}
在这里,您可以允许 HTML、通过数据注释预设字符串的最大长度等,并设置一些预设的错误消息以在发生错误时指导用户。
请参阅以下内容: https://msdn.microsoft.com/en-us/library/ee256141(v=vs.100).aspx
在 Controller 端:
[HttpGet]
public async Task<ActionResult> AuthenticateUser(){
return View(new WebLoginModel());
}
[HttpPost,ValidateAntiforgeryToken]
public async Task<ActionResult> AuthenticateUser(WebLoginModel login){
//Right here you can flag a model is invalid and return an error to the Jquery
//AJAX call and handle it directly with HTML.
if(!ModelState.Valid)return new HttpStatusCodeResult(HttpstatusCode.Invalid);
var validLogin = LoginMethodInYourModel( Or whatever else you are using ).
}
在 HTML/Jquery 中你可以这样做:
<script type="text/javascript">
$('form').submit(function () {
var form = $('form'); // This will work if its the only form in the
//view, otherwise use an Id, Name or even a class will work.
var token = $('input[name="__RequestVerificationToken"]', form).val();
var lData = $('form').serialize();
$.ajax({
url: $(this).data('url'),
type: 'POST',
data: {
__RequestVerificationToken: token,
WebLoginModel: lData
},
success: function (result) {
alert(result.someValue);
},
error:function(errorResult){
//You can handle the error gracefully here and allow your user to
//know what is going on.
}
});
return false;
});
</script>
我不能把这一切归功于我,我实际上从以下帖子中学到了处理/验证防伪 token 的最佳方法:
include antiforgerytoken in ajax post ASP.NET MVC
通过使用 JQuery 这样做,您可以用等待玻璃或旋转 Logo 提示用户,并在服务器端做一些工作,它是干净的,切中要害的。
关于jquery - 如何使用asp.net mvc5实现ajax登录?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36019417/