0

こんにちは、js ファイルから MVC コントローラーのアクションにデータを渡そうとすると問題が発生します。これは私のコントローラーです。

    [HttpPost]
    [CustomAuthorize(Roles.Administrator, Roles.ContextOwner, Roles.DataOwner, Roles.DataSteward)]
    public JsonResult SaveChangesOnGrid(int id, string json)
    {
        var codeViewModels = JsonConvert.DeserializeObject<CodeViewModel[]>(json);

        var error = string.Empty;
        CodeViewModel newViewModel = null;

        foreach (var viewModel in codeViewModels)
        {
            viewModel.CodeListId = id;
            if (ModelState.IsValid)
            {
                error = codeService.Validate(viewModel);

                if (string.IsNullOrEmpty(error))
                {
                    newViewModel = codeService.SaveToStage(viewModel);
                }
            }
            else
            {
                error = "Could not save";
            }
        }

        if (id > 0 && string.IsNullOrEmpty(error))
        {
            // notify
            var codeList = codeListService.GetCurrentCodeListById(id);
            notifyGroup.NotifyDataOwnerGroup(codeList);
        }

        return Json(new
        {
            error,
            newViewModel
        });
    }

HTTPPOst アノテーションを使用すると、もうアクセスできなくなります。ビューのボタンを使用してアクションにアクセスしようとしています。2 つの異なる方法を試しましたが、どちらも機能しません。

<a id="review_btn" class="btn btn-primary" href='@Url.Action("SaveChangesOnGrid", "Code", new {id = Model.CodeListId })'>Submit for Review</a>

編集:ボタンの HTML 出力は

<div class="btn-group offset10" style="margin-top: 20px; margin-bottom: 20px">
        <a id="review_btn" class="btn btn-primary" href='/ReferenceData.Web/Code/SaveChangesOnGrid/13'>Submit for Review</a>
</div>

私の JS ファイルには、JSon 配列をコントローラー アクションに渡そうとする関数があります。EDIT Ajaxが更新されました。ボタンが押されると、内部サーバー エラー Http 500 が発生するようになりました。開発者ツールでネットワーク パッケージを確認すると、HTTP パケットと JSON パケットが表示されますHTTP 情報のスクリーンショット

    function rowsToJson(obj) {
    var selRowIds = $("#CodeGrid").jqGrid('getGridParam', 'selarrrow');

    if (selRowIds.length > 0) {

        var rowData = jQuery('#CodeGrid').jqGrid('getRowData', selRowIds[0]);
        var selectedRowsData = [{ "Code": rowData.Code, "ParentCode": rowData.ParentId, "Name": rowData.Name, "Description": rowData.Description }];

        for (var i = 1; i < selRowIds.length; i++) {

            rowData = jQuery('#CodeGrid').jqGrid('getRowData', selRowIds[i]);

            selectedRowsData.push({ "CodeId": rowData.CodeId, "Code": rowData.Code, "ParentCode": rowData.ParentId, "Name": rowData.Name, "Description": rowData.Description });
        }

        $.ajax({
            url: window.g_baseUrl + 'Code/SaveChangesOnGrid',
            type: 'POST',
            data: JSON.stringify(selectedRowsData),
            dataType: 'json',
            contentType: 'application/json; charset=utf-8',
            async: true,
            processData: false
        });

        //$(obj).attr('href', obj.href + "?json=" + JSON.stringify(selectedRowsData));
        return true;
    }
    else {
        alert("Please select a code");
        return false;
    }
};

$(function () {
    $('#review_btn').click(function () {
        if (confirm('These Selected Changes will be submitted for approval \n\n Are you sure you wish to proceed?')) {
            return rowsToJson(this);
        } else {
            $('#CodeGrid').jqGrid('resetSelection');
            return false;
        }
    });
});

コメントアウトした内容からわかるように、AJAX を使用して、JSON を文字列として URL の末尾に追加するだけです。

ボタンから href を削除して AJAX を使用すると、エラー 500 が発生します。コントローラーにデバッグするときに href をそのままにしておくと、json パラメーターが null になります。

URL の末尾に HTTPPost アノテーションを付けて JSON 配列を追加すると、json パラメータは null になります。アノテーションを削除すると、JSON が渡されますが、コードをステップ実行すると、エラーがスローされ、JSON と Get に関連するセキュリティの問題について通知されます

URL でデータがユーザーに表示されないようにするため、可能であれば Ajax を使用することをお勧めします。しかし、私は本当に何かを機能させたいだけです。

4

2 に答える 2

1

まず、GET の使用を忘れてください。見た目が悪く、JSON が大きくなりすぎると失敗する可能性があります。ここでアクションがどのように設定されているかを見てください。

NHibernate と MVC を使用して Jquery Ajax から IList<T> を返す WebMethod を呼び出す

そしてここ:

http://haacked.com/archive/2010/04/15/sending-json-to-an-asp-net-mvc-action-method-argument.aspx

上記の例に従って、これを単純化してみてください。

ここでは JSON.Stringify が必要だと思います。また、コードが機能するようになるまで、役割の注釈を削除してください。

于 2013-11-06T18:33:08.267 に答える
0

投稿しているデータは、アクション シグネチャと一致しません。例外の詳細は、デバッグ コンソールの [プレビュー]または[応答] タブで確認できます。

アクション署名:

[HttpPost]
public JsonResult SaveChangesOnGrid(int id, string json)

あなたの POST は以下を送信しています:

var selectedRowsData = [{ "Code": rowData.Code, "ParentCode": rowData.ParentId, "Name": rowData.Name, "Description": rowData.Description }];
selectedRowsData.push({ "CodeId": rowData.CodeId, "Code": rowData.Code, "ParentCode": rowData.ParentId, "Name": rowData.Name, "Description": rowData.Description });

$.ajax({
    ...
    data: JSON.stringify(selectedRowsData)
});

期待されるものは次のとおりです。

var selectedRowsData = [{ "Code": "", "ParentCode": "", "Name": "", "Description": "" }];

$.ajax({
    ...
    data: JSON.stringify({ "id": "1", "json": JSON.stringify(selectedRowsData) });
});

それはおそらくあなたが意図したものではないので...

代わりにこれを試してください

フレームワークにバインドと逆シリアル化を行わせます。

var selectedRowsData = [];
for (var i = 1; i < selRowIds.length; i++) {
    rowData = jQuery('#CodeGrid').jqGrid('getRowData', selRowIds[i]);
    selectedRowsData.push({ "CodeId": rowData.CodeId, "Code": rowData.Code, "ParentCode": rowData.ParentId, "Name": rowData.Name, "Description": rowData.Description });
}

$.ajax({
    ...
    data: JSON.stringify(selectedRowsData)
});

次に、JSON オブジェクトをミラーリングするモデルを作成します。(あなたのCodeViewModel?)

public class Country
{
    public int CodeId { get; set; }
    public string Code { get; set; }
    public string ParentCode { get; set; }
    public string Name { get; set; }
    public string Description { get; set; }
}

アクション署名を変更する

[HttpPost]
public JsonResult SaveChangesOnGrid(Country[] codes)

...その後、データを手動で逆シリアル化することを忘れてください。

于 2013-11-07T20:14:46.833 に答える