问题描述
这是可能再次新手的问题。
This is probably again a newbie question.
当我创建一个ASP.NET应用程序MVC2,用行动帐户登录控制器这样创建:
When I create an ASP.NET MVC2 application, an Account Controller with an Action LogIn is created like this:
[HttpPost]
public ActionResult LogOn(LogOnModel model, string returnUrl)
{
if (ModelState.IsValid)
{
if (MembershipService.ValidateUser(model.UserName, model.Password))
{
FormsService.SignIn(model.UserName, model.RememberMe);
if (!String.IsNullOrEmpty(returnUrl))
{
return Redirect(returnUrl);
}
else
{
return RedirectToAction("Index", "Home");
}
}
else
{
ModelState.AddModelError("", "The user name or password provided is incorrect.");
}
}
// If we got this far, something failed, redisplay form
return View(model);
}
现在,我不希望有一个登录页面,我想有登录控件作为一个更大的页面的一部分。所以,我改变的Login.aspx到Login.ascx,我在我的无论是与Html.RenderPartial或Html.RenderAction主视图相集成。
Now, I don't want to have a login page, I want to have login controls as part of a bigger page. So, I changed Login.aspx to Login.ascx and I am integrating it in my main view either with Html.RenderPartial or Html.RenderAction.
这两部作品一样,如果登录名是全成一个魅力。如果不是,则
Both works like a charm if the login is successfull. If it is not, the
return View(model)
是我的命。
我要的是回到我的主网页(称为主页/索引),但局部视图的出错信息。
is killing me.What I want is to go back to my main page (call it Home/Index) but with the error information of the partial view.
return RedirectToAction("Index", "Home")
显然是行不通的。
Obviously doesn't work.
提示?
推荐答案
这当然不是一个新手的问题,我已经梳理向上和向下的网站为回答这个问题,到目前为止,最好的解决办法,我发现是那种隐藏在这个教程此处。这就是达林季米特洛夫与阿贾克斯刷新建议。我将总结该链接的重要组成部分,为什么这是不容易解决:/
This is certainly not a newbie question and I have combed up and down the web for an answer to this problem and so far the best solution I've found was kind of hidden in this tutorial here. This is what Darin Dimitrov was suggesting with the Ajax refresh. I'll summarize the important parts of that link and why this isn't easily fixed : /
阿贾克斯刷新基于怪异的情人
与下面的函数了ajax刷新pretty多铰链(怪异的情人使用ControllerContext,但它并没有为我存在,所以我不得不ControllerExtension)解决方案:
The solution with the ajax refresh pretty much hinges on the following function (weird lover uses ControllerContext but it didn't exist for me so I have ControllerExtension):
ControllerExtension.RenderPartialViewToString(this,"mypartial", (object)model)
这功能就是把你的模型+的ModelState和重新渲染你的局部视图到HTML字符串。然后,您可以采取的字符串,并将其发送回一个JSON对象一些JavaScript刷新视图。我用jQuery和它看起来像这样,
This function is what takes your model + modelstate and rerenders your partial view into an html string. You can then take that string and send it back in a json object to some javascript to refresh the view. I used jquery and it looks like this,
$(document).ready(function () {
var partialViewUpdate = function (e) {
e.preventDefault(); //no postback
var partialDiv = $(this).parent(".partial");
$.post($(this).attr("action"),
$(this).serialize(),
function (json) {
if (json.StatusCode != 0) {
// invalid model, return partial
partialDiv.replaceWith(json.Content);
}
else if (json.Content != null && json.Content != "") {
window.location.replace(data.Content);
};
});
$(".partial").find("form")
.unbind('submit')
.live("submit", partialViewUpdate);
};
jQuery的解释是:
Jquery explanation:
- 查找包含我的部分(类=部分)div和发现的div 中的形式
- 解除绑定任何其他与形式提交事件(我得到了一些奇怪的双提交bug,直到我做了解除绑定)。
- 使用实时,这样一旦内容被替换它再重新绑定
- 一旦我们进入功能partialViewUpdate ...
- prevent从完成提交,以便它可以全部由AJAX来处理的形式。
- 获取包含DIV我的部分(将使用这个版本)
- 设置jQuery的URL后从形式服用,$(本).attr(行动)
- 采取的形式(即我们的模型)和序列化的控制器功能,$(本).serialize()
- 创建将处理AJAX返回值的功能。
- 我用我个人的JSON对象,其中一个状态code 1是坏的。所以,如果是不好的话,我拿的是什么内容,这是 RenderPartialViewToString 的给了我,我只是替换包含我的部分的div的内容。 字符串
- Look up the div that contains my partial (class="partial") and find the form within that div
- Unbind any other "submit" events with that form (I got some strange double submit bug until I did that unbind).
- use "live" so that once the content is replaced it rebinds again
- Once we enter the function partialViewUpdate...
- Prevent the form from finishing the submit so that it can all be handled by ajax.
- fetch the div that contains my partial (will use this later)
- Setup the jquery post url by taking it from the form, $(this).attr("action")
- Take the form (i.e. our model) and serialize it for the controller function, $(this).serialize()
- Create the function that will handle the ajax return value.
- I use my own personal json object, where a StatusCode 1 is bad. So if it's bad then I take what's in Content, this is the string that RenderPartialViewToString gave me, and I just replace the contents of the div that contains my partial.
为什么它不只是工作正常
所以,谐音不只是ModelState中验证工作的原因是,你不能用POST返回视图(模型),因为MVC会解决的局部视图(login.ascx)的路径,而不是地址的,其中部分被嵌入(的Index.aspx)
So the reason the partials' don't just work with modelstate validation is that you can't return View(model) with the POST because MVC will resolve that to the route address of the partial view (login.ascx) instead of where the partial is embedded (index.aspx).
您也不能使用RedirectAction(),因为这将发送到(的Index.aspx)控制功能,这是清除一切并刷新页面的Index.aspx的等价物。但是,如果您使用ActionFilter建议的奇诺和Thabaza那么你的页面被刷新,而且login.ascx控制器功能被触发再次关闭它会拿起TempData的时候。然而,这是否刷新页面会导致客户端code麻烦,如弹出式模态(即,如果您刷新弹出消失)不起作用。
You also can't use RedirectAction() because that will send it to (index.aspx) controller function, which is the equivalent of clearing everything and refreshing the index.aspx page. However if you use that ActionFilter suggested by Chino and Thabaza then when your page is refreshed and the login.ascx controller function is fired off again it will pick up that tempdata. This however doesn't work if refreshing the page causes a hassle with client-side code such as popup modals (i.e. if you refresh your popup is gone).
说这是不是这样
我想preFER,如果它只是工作,因此,如果有人知道这样做pleaaaase分享正确的/更好的办法!我仍然觉得,阿贾克斯刷新ActionFilter解决方案不这样做,因为它几乎使它看起来像部分景色与形式是不可能没有某种形式的绝招,使用的清洁方法。
I would prefer if it "just worked" so if anyone knows the correct/better way of doing this pleaaaase share it! I still feel that the Ajax refresh and ActionFilter solutions are not a clean way of doing it because it almost makes it look like partial views with forms are impossible to use without some sort of "trick".
这篇关于ASP.Net MVC保持他们的模型状态的部分看法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!