【问题标题】:Adding partial view via ajax通过ajax添加部分视图
【发布时间】:2018-10-31 04:17:45
【问题描述】:

在我的主布局中,我尝试通过 ajax 添加登录部分视图,但是我不断收到“内部服务器错误”。我已经尝试了各种其他发布的解决方案,但没有运气

一切都很标准我有我的 HomeController 和 index.cshtml(它使用 layout.cshtml)

在布局中,一旦文档准备好,我使用ajax查看用户是否通过HomeController登录,如果返回值为false我想显示部分视图。

函数 showLoginPartial 尝试通过 ajax 从 LoginController 获取部分视图失败

“showLoginPartial() 中的错误:内部服务器错误:-: 错误”

我做错了什么?

HomeController 方法:

    public JsonResult IsUserLoggedIn()
    {
        return Json(new { result = (CurrentUser != null) }, JsonRequestBehavior.AllowGet);
    }

布局jquery:

$(document).ready(function () {
    checkLoggedIn();
    function checkLoggedIn() {
        $.ajax({
            url: '@Url.Action("IsUserLoggedIn", "Home", new { })',
            success: function (data) {
                if (data.result == false) {
                    //Show the login partial view
                    showLoginPartial();
                }
            },
            error: function (XMLHttpRequest, textStatus, errorThrown) {
                alert("Error in checkLoggedIn(): " + errorThrown + " :-: " + textStatus);
            }
        });
    }

    function showLoginPartial() {
        $.ajax({
            url: '@Url.Action("LoginDisplay", "Login", new { })',
            success: function (response) {
                //add the partial view after #ib-container div
            },
            error: function (XMLHttpRequest, textStatus, errorThrown) {
                //Error displays
                alert("Error in showLoginPartial(): " + errorThrown + " :-: " + textStatus);
            }
        });
    }
})

登录控制器:

public class LoginController : Controller
{
    // GET: Login
    [ChildActionOnly]
    public ActionResult LoginDisplay()
    {
        return PartialView("_LoginDisplay");
    }
    public JsonResult UserLoggedOut()
    {
        return Json(new { result = Nuclei.Models.CurrentUserAccount.Instance.LoggedOut }, JsonRequestBehavior.AllowGet);
    }

    public JsonResult UserAutoAuthenticate()
    {
        bool l_result = false;
        System.Threading.Thread.Sleep(3000);
        return Json(new { result = l_result }, JsonRequestBehavior.AllowGet);
    }

    public JsonResult UserManualAuthenticate()
    {
        bool l_result = false;
        System.Threading.Thread.Sleep(3000);
        return Json(new { result = l_result }, JsonRequestBehavior.AllowGet);
    }

    public JsonResult SendUserCredentials()
    {
        bool l_result = true;
        System.Threading.Thread.Sleep(3000);
        return Json(new { result = l_result }, JsonRequestBehavior.AllowGet);
    }
}

网站结构:

[编辑]

刚刚尝试通过 RenderAction() 添加局部视图,它工作了,但这不是我想要的,肯定想使用 ajax。

@{ Html.RenderAction("LoginDisplay", "Login"); }

将其余方法也添加到上面的 LoginController 中

_LoginDisplay.cshtml

<div id="login_layer_overlay">
</div>

<div id="login_layer">

    <div id="MainLoginDiv">
        <div id="LoginHeaderDiv" class="text-center">
            <h3 id="LoginHeader" class="page-header" style="color:white;">&nbsp;</h3>
        </div>
        <div id="Spinner" class="spinner">
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
            <i><b></b></i><!--1--><i><b></b></i><!--2--><i><b></b></i><!--3--><i><b></b></i><!--4--><i><b></b></i><!--5--><i><b></b></i><!--6--><i><b></b></i><!--7--><i><b></b></i><!--8--><i><b></b></i><!--9--><i><b></b></i><!--10-->
        </div>
        <div id="ManualLogin" class="box" style="border: none;">
            @using (Html.BeginForm())
            {
                @Html.AntiForgeryToken()
                <div class="form-group">
                    <label class="control-label" style="color:white;">Username</label>
                    @Html.TextBox("username", null, new { id = "username", @class = "form-control", @Value="us" })
                </div>
                <div class="form-group">
                    <label class="control-label" style="color:white;">Password</label>
                    @Html.TextBox("password", null, new { id = "password", @class = "form-control", @Value = "pwd" })
                </div>
                <div class="text-center" style="margin-top:40px;">
                    <input type="button" id="ManualLoginBtn" value="Sign in" class="btn btn-primary" />
                    <br />
                    <input type="button" id="AutoLoginBtn" value="Auto Authenticate" class="btn btn-default" />
                    <input type="button" id="ForgotLoginBtn" value="Forgot Credentials" class="btn btn-default" />
                </div>
            }
        </div>
        <div id="ForgotLogin" class="box" style="border: none;">
            @using (Html.BeginForm())
            {
                @Html.AntiForgeryToken()
                <div class="form-group">
                    <label class="control-label" style="color:white;">Email</label>
                    @Html.TextBox("email", null, new { id = "email", @class = "form-control", @Value = "jhjhblah" })
                </div>
                <div class="text-center" style="margin-top:40px;">
                    <input type="button" id="BackToLoginBtn" value="Back" class="btn btn-default" />
                    <input type="button" id="ForgotSubmitBtn" value="Submit" class="btn btn-primary" />
                </div>
            }
        </div>
    </div>
</div>
<script>
    $(document).ready(function () {

        var spinnerItems = $("#Spinner i b");
        $("#MainLoginDiv").css("opacity", "1");
        checkUserLoggedOut();


        function checkUserLoggedOut() {
            $.ajax({
                //First need to check for logged off
                url: '@Url.Action("UserLoggedOut", "Login", new { })',
                success: function (data) {

                    if (data.result == false) {
                        showAutoAuthenticate();
                    }
                    else {
                        showManualForm();
                    }
                },
                error: function (XMLHttpRequest, textStatus, errorThrown) {
                    alert("Error: " + errorThrown + " :-: " + textStatus);
                }
            });
        }

        function showAutoAuthenticate() {
            $("#LoginHeader").text("Auto Authenticating");
            $("#ManualLogin").css("opacity", "0");
            setTimeout(function () { $("#ManualLogin").css("display", "none"); }, 550);
            $("#Spinner").css("opacity", "1");

            spinnerItems.each(function () {
                $(this).addClass("spinAnimation");
            })
            $.ajax({
                url: '@Url.Action("UserAutoAuthenticate", "Login", new { })',
                success: function (data) {

                    if (data.result == false) {
                        //Switch to manual
                        //showForgotLogin();
                        showManualForm();
                    }
                    else {
                        //Remove login
                        $("#AutoLogin").css("opacity", "0");
                        spinnerItems.each(function () {
                            $(this).removeClass("spinAnimation");
                        })
                    }
                },
                error: function (XMLHttpRequest, textStatus, errorThrown) {
                    alert("Error in showAutoAuthenticate(): " + errorThrown + " :-: " + textStatus);
                }
            });
        }

        function showManualAuthenticate() {
            $("#LoginHeader").text("Authenticating");
            $("#ManualLogin").css("opacity", "0");
            setTimeout(function () { $("#ManualLogin").css("display", "none"); }, 550);
            $("#Spinner").css("opacity", "1");

            spinnerItems.each(function () {
                $(this).addClass("spinAnimation");
            })

            $.ajax({
                url: '@Url.Action("UserManualAuthenticate", "Login", new { })',
                success: function (data) {

                    if (data.result == false) {
                        //Switch to manual
                        //showForgotLogin();
                        showManualForm();
                    }
                    else {
                        //Remove login
                        $("#AutoLogin").css("opacity", "0");
                        spinnerItems.each(function () {
                            $(this).removeClass("spinAnimation");
                        })
                    }
                },
                error: function (XMLHttpRequest, textStatus, errorThrown) {
                    alert("Error in showManualAuthenticate(): " + errorThrown + " :-: " + textStatus);
                }
            });
        }

        function showForgottenProcessing() {
            $("#ForgotLogin").css("opacity", "0");
            setTimeout(function () { $("#ForgotLogin").css("display", "none"); }, 550);
            $("#Spinner").css("opacity", "1");

            spinnerItems.each(function () {
                $(this).addClass("spinAnimation");
            })

            $.ajax({
                url: '@Url.Action("SendUserCredentials", "Login", new { })',
                success: function (data) {

                    if (data.result == false) {
                        //Switch to manual
                        showForgotLoginForm();
                    }
                    else {
                        //Go back to login
                        showManualForm();
                    }
                },
                error: function (XMLHttpRequest, textStatus, errorThrown) {
                    alert("Error in showManualAuthenticate(): " + errorThrown + " :-: " + textStatus);
                }
            });
        }

        function showManualForm() {

            $("#Spinner").css("opacity", "0");
            spinnerItems.each(function () {
                $(this).removeClass("spinAnimation");
            })
            $("#ForgotLogin").css("opacity", "0");
            setTimeout(function () { $("#ForgotLogin").css("display", "none"); }, 550);

            $("#LoginHeader").text("Login");
            $("#ManualLogin").css("display", "block");
            $("#ManualLogin").css("opacity", "1");
        }

        function showForgotLoginForm() {

            $("#Spinner").css("opacity", "0");
            spinnerItems.each(function () {
                $(this).removeClass("spinAnimation");
            })
            $("#ManualLogin").css("opacity", "0");
            setTimeout(function () { $("#ManualLogin").css("display", "none"); }, 550);

            $("#LoginHeader").text("Retrieve Credentials");
            $("#ForgotLogin").css("display", "block");
            $("#ForgotLogin").css("opacity", "1");
        }

        $("#AutoLoginBtn").click(function () {
            showAutoAuthenticate();
        });
        $("#ForgotLoginBtn").click(function () {
            showForgotLoginForm();
        });
        $("#BackToLoginBtn").click(function () {
            showManualForm();
        });
        $("#ManualLoginBtn").click(function () {
            showManualAuthenticate();
        });
        $("#ForgotSubmitBtn").click(function () {
            showForgottenProcessing();
        });
    })
</script>

【问题讨论】:

  • Internal Server Error 表示局部视图中的某处抛出未处理的异常。你能提供_LoginDisplay.cshtml的内容吗?还可以尝试剥离 [ChildActionOnly] 属性。
  • 剥离了 [ChildActionOnly],似乎可以解决问题,它没有显示错误,我已经能够添加视图。谢谢你。有趣的是,当我使用 @{ Html.RenderAction("LoginDisplay", "Login");它需要 [ChildActionOnly] 属性。如果您将此添加为答案,我会接受。

标签: c# jquery ajax asp.net-mvc partial-views


【解决方案1】:

[ChildActionOnly] 属性用法确保动作方法只能作为父视图的子方法调用(即禁用直接导航以加载像 /Login/LoginDisplay 这样的局部视图),并且通常用于使用 @ 渲染局部视图987654325@帮手:

任何标有ChildActionOnlyAttribute的方法都可以被调用 仅适用于 Action 或 RenderAction HTML 扩展方法。

由于您不是通过RenderAction() 调用部分视图,而是使用需要在url 设置中直接进行URL 导航的AJAX,ChildActionOnlyAttribute 立即阻止响应该URL 的请求和运行时错误子操作将抛出只能由子请求访问的(在 AJAX 结果中显示为“内部服务器错误”)。

因此,控制器动作不应使用[ChildActionOnly] 属性:

[HttpGet]
public ActionResult LoginDisplay()
{
    return PartialView("_LoginDisplay");
}

AJAX 调用应该是这样的:

function showLoginPartial() {
    $.ajax({
        url: '@Url.Action("LoginDisplay", "Login")',
        type: 'GET',
        success: function (response) {
            $('#ib-container').html(response);
        },
        error: function (XMLHttpRequest, textStatus, errorThrown) {
           //Error displays
           alert("Error in showLoginPartial(): " + errorThrown + " :-: " + textStatus);
        }
    });
}

参考资料:

System.Web.Mvc.ChildActionOnlyAttribute Class

Using ChildActionOnly in MVC

【讨论】:

  • 很好的解释!现在一切都清楚了,感谢您的时间和精力。
猜你喜欢
  • 2013-01-10
  • 1970-01-01
  • 2018-02-10
  • 1970-01-01
  • 2018-12-19
  • 1970-01-01
  • 1970-01-01
  • 2018-06-30
  • 1970-01-01
相关资源
最近更新 更多