8

ASP.netはまだ少し新しいので、この奇妙な問題があります。それは非常に基本的なシナリオですが、何かが起きていて、私はそれを理解することができません。Deployは、モデルCompiledAppModelに入力されたDeployという名前のビューを返す必要があります。ただし、ビューで[インストール]をクリックすると、return View()メソッドを呼び出してもページを離れることはありません。何か案は?

これが私のコントローラーです:

[HttpPost]
public ActionResult Deploy(string key_name, string custom_folder = "")
{
    string userId = Membership.GetUser().ProviderUserKey.ToString();
    UserDataModel user_info = _user_data_service.getUserDataByPrimaryIDNoDB(userId, HttpContext.Cache);
    log.Trace("Deploy was called. key_name:" + key_name + " UID: " + user_info.UID);

    // first we'll call the info to install remote application
    bool serviceInstall = _fms_app_service.DeployFmsApp(user_info, key_name, custom_folder);

    // then we'll call to generate client side info
    bool clientInstall = _fms_app_service.CompileClientApp(user_info, key_name);

    var model = _fms_app_service.getInstalledAppInfo(user_info, key_name);
    if (serviceInstall && clientInstall)
    {
        return RedirectToAction("Deploy", model);
    }

    return View("Error");
}

と私の見解:

@model IEnumerable<Models.Applications.FmsAppModel>

@foreach (var item in Model) {
    <div class="col">
        <h2>@Html.DisplayFor(modelItem => item.friendly_name)</h2>
        <p>@Html.DisplayFor(modelItem => item.app_description)</p>
        <p><strong>Tags:</strong> @Html.DisplayFor(modelItem => item.app_type)</p>

        <a href="#" class="btn btn-primary install-app" data-key-name="@(item.key_name)">Install</a>

        @Html.ActionLink("Details", "Detailss", new {  id=item.app_id  })
    </div>
}
</div>

<script type="text/javascript">
   (function () {
        $('.install-app').on('click', function (e) {
            e.preventDefault();
            var data_key_name = $(this).data('key-name');
            //ajax install app
            $.ajax({
                type: "POST",
                url: '@Url.Action("Deploy")',
                data: {
                    key_name: data_key_name
                }
            });
        });
    })();
</script>

そしてモデル。

public class CompiledAppModel
{
    [Display(Name = "Admin URL")]
    public string adminURL { get; set; }

    [Display(Name = "Viewer URL")]
    public string viewerURL { get; set; }

    [Display(Name = "Embed URL")]
    public string embedURL { get; set; }
}
4

3 に答える 3

5

ajax呼び出しを行った後、本当にリダイレクトしたいと思います。

私の知る限り、次のようなカスタムActionResultを実装する必要があります。

public class AjaxAwareRedirectResult : RedirectResult
{       
    public AjaxAwareRedirectResult(String url)
        : base(url)
    {
    }

    public override void ExecuteResult(ControllerContext context)
    {
        if ( context.RequestContext.HttpContext.Request.IsAjaxRequest() )
        {
            String destinationUrl = UrlHelper.GenerateContentUrl(Url, context.HttpContext);

            JavaScriptResult result = new JavaScriptResult()
            {
                Script = "window.location='" + destinationUrl + "';"
            };
            result.ExecuteResult(context);
        }
        else
        {
            base.ExecuteResult(context);
        }
    }
}

コントローラで、次の手順を実行します。

    [HttpPost]
public ActionResult Deploy(string key_name, string custom_folder = "")
{
    string userId = Membership.GetUser().ProviderUserKey.ToString();
    UserDataModel user_info = _user_data_service.getUserDataByPrimaryIDNoDB(userId, HttpContext.Cache);
    log.Trace("Deploy was called. key_name:" + key_name + " UID: " + user_info.UID);
    // first we'll call the info to install remote application
    bool serviceInstall = _fms_app_service.DeployFmsApp(user_info, key_name, custom_folder);
    // then we'll call to generate client side info
    bool clientInstall = _fms_app_service.CompileClientApp(user_info, key_name);

    var model = _fms_app_service.getInstalledAppInfo(user_info, key_name);
    if (serviceInstall && clientInstall)
    {
        return RedirectToAction("Deploy", model);
    }
    return AjaxAwareRedirectResult("/foo");
}

しかし、私が言ったように、これはあなたが本当にajax呼び出しの後にリダイレクトしたいと思っていると仮定しているだけです。

于 2012-10-16T09:50:17.703 に答える
1

ajax呼び出しの後にHTTPリダイレクトを実行しても、あまり意味がない場合があります。これは、htmlフォームと通常のPOSTを使用するだけで実行できます。

ただし、本当にリダイレクトが必要であり、それでもAJAXを介したPOSTが必要な場合は、次の回答で提案されているように、リダイレクトの代わりにJsonを返すことでそれを行うことができます。

その場合、Jsonオブジェクト内のターゲットアクションURLを返し、Neilの回答に示されているように、成功ハンドラーでその情報を使用できます。

また、これRedirectToActionは単なる302リダイレクトであるため、ビューを直接レンダリングしないため、本格的なViewModelを渡さず、ブラウザがGETを発行するためのアクションURLのみを渡すことに注意してください。

そのターゲットGETアクションは、 POST-REDIRECT-GETパターンに従って、インストール済みアプリ情報を取得し、それをパラメーターとしてビューに渡す役割を果たします。

于 2012-10-16T03:39:43.083 に答える
1

Ajax呼び出しを使用してサーバーに投稿を返すように見えます。この場合、少し余分な作業を行わないと、結果はページにレンダリングされません。ajax呼び出しで成功ハンドラーを定義して、ajax呼び出しが戻ったときにアクションを実行できます。だから何かのような

<script type="text/javascript"> (function () {
    $('.install-app').on('click', function (e) {
        e.preventDefault();
        var data_key_name = $(this).data('key-name');
        //ajax install app
        $.ajax({
            type: "POST",
            url: '@Url.Action("Deploy")',
            data: {
                key_name: data_key_name
            },
            success: function(data) { alert(data) }
        });
    });
})();

リクエストが完了すると、ajax呼び出しから返されたHTMLを含むアラートメッセージが表示されます。

また、FirebugまたはChromeの開発者ツールを使用して、返されたHTMLを表示します。サーバーで例外が発生した場合は、これらのツールを使用してこれをより詳細に検査できるはずです。

于 2012-10-16T03:24:36.580 に答える