在 Ajax 发布 MVC 5 后禁用重定向到控制器



我在_Layout上有一个锚点,可以调用带有操作的模态来获取显示模态的部分视图

<ul class="navbar-nav mr-auto">
<li class="nav-item">
@Html.Action("LogoutModal", "Account")
<a class="nav-link" href="#" data-toggle="modal" data-target="#modalLogout">
Log Out
</a>
</li>
</ul>

此操作将转到此控制器

public class AccountController : Controller
{
public ActionResult LoginModal()
{
return PartialView("_PartialLogin");
}
...

这是带有模态的部分视图

@model HutLogistica.ViewModels.LoginViewModel
@{
Layout = null;
}
<link href="~/Content/bootstrap.css" rel="stylesheet" />
<link href="~/Content/login.css" rel="stylesheet" />
<link href="~/Content/fontawesome-all.css" />
<script src="~/scripts/jquery-3.3.1.js"></script>
<script src="~/Scripts/jquery.validate.js"></script>
<script src="~/Scripts/jquery.validate.unobtrusive.js"></script>
<script src="~/Scripts/bootstrap.js"></script>
<script src="~/Scripts/fontawesome/all.js"></script>
<!-- Modal -->
<div class="modal fade" id="modalLogin" tabindex="-1" role="dialog" aria-labelledby="exampleModalLabel" aria-hidden="true">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-body">

@using (Html.BeginForm("Login", "Account", FormMethod.Post, new { id = "formModal" }))
{
@Html.AntiForgeryToken();
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
@Html.EditorFor(model => model.Username, new { htmlAttributes = new { @class = "form-control form-control-lg", placeholder = "Username", autofocus = true } })
@Html.ValidationMessageFor(model => model.Username, "")

@Html.EditorFor(model => model.Password, new { htmlAttributes = new { @class = "form-control form-control-lg", placeholder = "Password" } })
@Html.ValidationMessageFor(model => model.Password, "")
@Html.EditorFor(model => model.RememberMe, new { htmlAttributes = new { @class = "custom-control-input", id = "customCheck" } })
<button type="submit" class="btn btn-info">
Entrar
</button>
}
<div id="loader" class="text-center p-3 d-none">
<div class="lds-circle"><div></div></div>
<p><span class="text-muted">Aguarde...</span></p>
</div>
</div>
</div>
</div>
</div>
<script type="text/javascript">
$(document).ajaxStart(function () {
$("#loader").removeClass('d-none');
});
$(document).ajaxStop(function () {
$("#loader").addClass('d-none');
});
$(function () {
$("#formModal").submit(function () {
if ($(this).valid()) {
$.ajax({
url: this.action,
type: this.method,
cache: false,
processData: false,
contentType: false,
data: $(this).serialize(),
success: function (status, response) {
if (response.success) {
alert('Autenticado com sucesso');
$('#loginModal').modal('hide');
//Refresh
location.reload();
} else {
alert(response.responseText);
}
},
error: function (response) {
alert(response.data.responseText)
}
});
}
return false;
});
</script>

在我使用 ajax 以模态提交表单之前,每个薄型都工作正常。

这是我提交后去的控制器

// POST: /Account/Login
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public ActionResult Login(LoginViewModel model)
{
if (ModelState.IsValid)
{
var user = Authenticate(model);
if (user != null)
{
var ticket = new FormsAuthenticationTicket(
1,
user.Id.ToString(),
DateTime.Now,
DateTime.Now.AddHours(5),
model.RememberMe,
user.Roles.Select(c => c.Nome).FirstOrDefault(),
FormsAuthentication.FormsCookiePath
);
Response.Cookies.Add
(
new HttpCookie
(
FormsAuthentication.FormsCookieName,
FormsAuthentication.Encrypt(ticket)
)
);
return Json(new { success = true });
}
else
{
ModelState.AddModelError("", "Username / Password incorrectos");
return Json(new { success = false, responseText = "Username / Password incorrectos" });
}
}
else
return Json(new { success = false, responseText = "Dados inválidos" });
}

这就是问题所在。提交表单后,我被重定向到 localhost:port/account/Login,如果出现错误,则向我显示 json 的内容。我只想检索 ajax 成功的错误并在模态上打印错误......为什么我被重定向到包含 json 内容的控制器?

我在堆栈溢出中看到的另一篇帖子中向 ajax 配置添加了一些选项,但显然在我的情况下没有改变任何东西。

我只想保持我的模式并接收成功或出现错误的状态消息。如果有错误,我只是刷新ajax成功页面以显示登录的html

$("form").submit((e) => {
	e.preventDefault();

alert("No redirect");
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form>
First name:<br>
<input type="text" name="firstname"><br>
Last name:<br>
<input type="text" name="lastname">
<button type="submit"> Submit </button>
</form>

您需要禁用表单默认行为

event.preventDefault();

$("#formModal").submit(function () {
event.preventDefault();
// rest of your code here

// ajax request 
// or use form.submit()
// form.reset() to reset the form state.
}

由于您是通过 Ajax 发送表单请求的,我认为您不需要使用form.submit(),但您可能会发现form.reset()有用。

您可以在此处阅读有关 HTMLFormElement 如何工作的更多信息。

干杯

更改

@using (Html.BeginForm("Login", "Account", FormMethod.Post, new { id = "formModal" }))

@using (Html.BeginForm("LoginModal", "Account", FormMethod.Post, new { id = "formModal" }))

最新更新