我已经查看了本网站上提供的许多解决方案以及其他解决我的问题的解决方案,但它们似乎都不适用于我的解决方案.
在我的布局页面上,我在屏幕顶部有一个登录区域.除非用户登录,否则始终存在.此登录表单上有一个ValidationSummary,每次我使用网站上的其他表单回发时,都会触发此登录表单的验证.
我几乎可以肯定,这取决于我如何从布局页面调用此登录页面.它不是Shared文件夹中的局部视图,它位于我项目的Area中.在我的布局页面上,我将这样的登录表单调用:
@Html.Action("LogOn", "Account", new { area = "Store" })
登录页面包含以下内容:
@model Project.ViewModels.LogOn_ViewModel
@{
Layout = null;
}
@using (Ajax.BeginForm("LogOn", "Account", new { @area = "Store" }, new AjaxOptions { HttpMethod = "Post", UpdateTargetId = "LoginContainer", LoadingElementId = "actionLoaderImage" }, new { id="LogonForm" }))
{
@Html.AntiForgeryToken()
<div class="loginArea">
<div class="notRegistered">
<h4>Not registered yet?</h4>
Register now<br/>
@Html.ActionLink("Register", "Index", "SignUp", new { area = "Store" }, new { @class = "greenButton" })
</div> <!-- /notRegistered -->
<div class="loginForm">
<div class="formFields">
<label class="inline">@Html.LabelFor(m => m.UserName)</label>
@Html.TextBoxFor(m => m.UserName)
<label class="inline">@Html.LabelFor(m => m.Password)</label>
@Html.PasswordFor(m => m.Password)
<input type="submit" name="LogIn" value="Log in" class="blueButton" />
<img id="actionLoaderImage" src="@Url.Content("~/Content/web/images/loader.gif")" alt="icon" style="margin-right:15px; display:none;" />
@Html.ValidationSummary()
</div>
</div> <!-- /loginForm -->
</div> <!-- /loginArea -->
}
登录控制器是标准的东西:
// GET: /Account/Logon
public ActionResult LogOn()
{
// if logged in show logged in view
if (User.Identity.IsAuthenticated)
return View("LoggedIn");
return View();
}
// POST: /Account/Logon
[HttpPost]
public ActionResult LogOn(LogOn_ViewModel model)
{
if (ModelState.IsValid)
{
if (SecurityService.Login(model.UserName, model.Password, model.RememberMe))
{
return View("LoggedIn");
}
else
{
ModelState.AddModelError("", "The user name or password provided is incorrect.");
}
}
return PartialView(model);
}
我怀疑这里发生的事情是,如果帖子在页面的其他地方发生,Html.Action正在“发布”登录表单.这是有道理的,因为布局页面本身将作为表单发布操作的一部分发布.
我尝试从其他一些SO问题和博客(http://blogs.imeta.co.uk/MBest/archive/2010/01/19/833.aspx)实现自定义Validator示例,但我发现使用这些示例不会显示验证摘要与客户端验证,这对我没有多大用处.
我正在寻找的解决方案需要允许客户端和服务器端验证以正确的形式出现.有没有人使用MVC有这样的例子?如果可能的话,我想避免使用jquery手动查看客户端验证,只是为了使用框架来处理我的工作.
谢谢你的建议,
丰富
最佳答案 在解决这个问题的时间超过了我承认的时间之后,一旦你知道如何,答案一直很简单!
对于遇到此问题的任何其他人来说,此问题的解决方案是重命名您的操作,以便您的POST操作与您的GET操作的名称不同.这样,当回发布局页面并触发PartialView也被回发时,PartialView只有一个GET动作,因此不会触发ValidationSummary.
基于我上面的例子,我已经将表单更改为回发到我的登录部分视图的另一个操作,这已经为我解决了这个问题.
在我的布局页面中,商店区域中部分的链接保持不变:
@Html.Action("LogOn", "Account", new { area = "Store" })
然后将登录表单操作更改为指向新操作 – 不会与GET操作同名:
@using (Ajax.BeginForm("ConfirmLogon", "Account", new { @area = "Store" }, new AjaxOptions { HttpMethod = "Post", UpdateTargetId = "LoginContainer", LoadingElementId = "actionLoaderImage" }, new { id="LogonForm" }))
{
....
}
然后我只是重命名我的控制器操作,以便它具有不同的POST操作的动作名称,以便在使用帖子调用布局页面时,部分加载了POST操作,它不会调用我的登录POST操作:
// POST: /Account/ConfirmLogon
[HttpPost]
public ActionResult ConfirmLogon(LogOn_ViewModel model)
{
if (ModelState.IsValid)
{
if (SecurityService.Login(model.UserName, model.Password, model.RememberMe))
{
return PartialView("LoggedIn");
}
else
{
ModelState.AddModelError("", "The user name or password provided is incorrect.");
}
}
return PartialView("Logon",model);
}
希望这可以帮助其他人解决这个问题.现在似乎很明显,但是让我疯狂:D