[英]ASP.NET MVC: return Redirect and ViewData
我的MasterPage中有一个登录框。 每当登录信息不正确时,我都会对ViewData["loginError"]
进行定值,以向用户显示错误消息。
Login是UserController的一个动作,因此包含登录的表单有action = "/User/Login"
。
由于用户可以尝试从任何页面登录,如果成功,我会将他重定向到他的个人页面,但如果出现错误,我希望他留在他尝试登录的同一页面上。 我发现这有效:
return Redirect(Request.UrlReferrer.ToString());
但似乎,由于我没有返回正确的视图,ViewData上的数据丢失了,所以我无法显示错误消息。
关于如何解决这个问题和类似问题的任何建议?
谢谢
您可能希望使用TempData
属性,这将持久保存到下一个HTTP请求。
为什么不通过AJAX处理登录而不是完整的帖子? 您可以通过JSON轻松提供状态,重定向URL和任何错误消息。
public ActionResult Logon( string username, string password )
{
...
// Handle master page login
if (Request.IsAjaxRequest())
{
if (success)
{
return Json( new { Status = true, Url = Url.Action( "Index", "Home" ) } );
}
else
{
return Json( new { Status = false, Message = ... } );
}
}
else // handle login page logon or no javascript
{
if (success)
{
return RedirectToAction( "Index", "Home" );
}
else
{
ViewData["error"] = ...
return View("Logon");
}
}
}
客户端
$(function() {
$('#loginForm input[type=submit]').click( function() {
$('#loginError').html('');
$.ajax({
url: '<%= Url.Action("Logon","Account") %>',
dataType: 'json',
type: 'post',
data: function() { return $('#loginForm').serialize(); },
success: function(data,status) {
if (data.Status) {
location.href = data.Url;
}
else {
$('#loginError').html( data.Message );
}
}
});
return false;
});
});
通常对于大多数网站,当用户无法进行身份验证时(由于密码等),它将转到另一个帮助用户的页面(如密码检索,或要求用户注册),这很少留在非常相同的页面。 我想你可以重新考虑一下你真的需要你正在使用的导航。
好的,如果你真的想坚持你的模型,一个解决方案就是你可以将登录错误附加到URL。 例如, http ://www.example.com/index.aspx?login_error = 1表示发生错误,您可以使用BEGIN_REQUEST(或HTTP模块)捕获此错误,并告知模型状态错误:
ModelState.AddModelError(...);
顺便说一句,添加模型错误实际上是一种更恰当的方式来通知视图有关任何错误而不是使用ViewState(这类似于抛出异常vs返回关于过去执行结果的整数)。
虽然使用AJAX登录(由tvanfosson建议)是完全可以实现的,它有时在用户体验方面表现优异,但经典的全帖仍然是不可替代的(考虑一些用户将禁用javascript,甚至在我的转储WM6手机上不支持javascript )。
我糊涂了。 不
return View();
只需将当前页面返回给您?
所以在你的情况下,当登录失败时,设置你的viewdata并调用return View();
即
if (!FailedLogin) {
//Go to success page
}else{
//Add error to View Data or use ModelState to add error
return View();
}
你在使用[授权]装饰器吗? MVC登录过程会自动提示登录页面,然后返回您尝试执行的控制器操作。 削减了很多重定向。
以下示例有望帮助您解决此问题:
View.aspx
<%= Html.ValidationSummary("Login was unsuccessful. Please correct the errors and try again.") %>
<% using (Html.BeginForm()) { %>
<div>
<fieldset>
<legend>Account Information</legend>
<p>
<label for="username">Username:</label>
<%= Html.TextBox("username") %>
<%= Html.ValidationMessage("username") %>
</p>
<p>
<label for="password">Password:</label>
<%= Html.Password("password") %>
<%= Html.ValidationMessage("password") %>
</p>
<p>
<%= Html.CheckBox("rememberMe") %> <label class="inline" for="rememberMe">Remember me?</label>
</p>
<p>
<input type="submit" value="Log On" />
</p>
</fieldset>
</div>
<% } %>
AccountController.cs
private bool ValidateLogOn(string userName, string password)
{
if (String.IsNullOrEmpty(userName))
{
ModelState.AddModelError("username", "You must specify a username.");
}
if (String.IsNullOrEmpty(password))
{
ModelState.AddModelError("password", "You must specify a password.");
}
if (!MembershipService.ValidateUser(userName, password))
{
ModelState.AddModelError("_FORM", "The username or password provided is incorrect.");
}
return ModelState.IsValid;
}
在重定向操作后,您将无法捕获ViewData中添加的信息。 所以正确的方法是返回相同的View()并使用ModelState进行错误,如“xandy”所述。
希望这会给表单验证提供一个良好的开端。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.