对控制器的Ajax调用导致400错误

时间:2019-01-25 22:07:43

标签: c# jquery asp.net-web-api

我有以下指向控制器函数的Ajax调用:

<script type="text/javascript">
    $(document).ready(function () {
        $('#AddNote').click(function () {
            $('#AddNote').addClass("disabled");

                var txtNote = document.getElementById('note');
                var result = document.getElementById('result');

                result.innerText = "Adding note...";

                $.ajax({
                    url: "@Url.Action("AddNoteAsync", "Leads")",
                    type: "POST",
                    data: { leadId: @Model.Id, note: txtNote.value },
                    async: true,
                    success: function (data) {
                        // removed
                    },
                });
            });
        });
</script>

当我单击AddNote按钮时,我看到“正在添加注释...”消息显示,然后什么也没有发生。当我检查Chrome中的控制台时,它显示为:

:44309/Leads/AddNoteAsync:1 - Failed to load resource: the server responded with a status of 400 ()

所以我知道400意味着错误的请求,但是我不确定为什么会这样。我尝试过:

  • 在数据的“ leadId”和“ note”字段中添加引号-没什么区别。
  • 添加了警报框,以在AJAX调用之前显示@ Model.Id和txtNote.value的值,以验证它们是否正确。
  • 在控制器的AddNoteAsync函数中放置一个断点-永远不会命中
  • 将网址字段硬编码为/Leads/AddNoteAsync-没有区别

由于从未使用过控制器功能,因此我假设&.ajax部分出了问题,但我无法弄清楚是什么。

编辑:控制器方法:

[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> AddNoteAsync(int? leadId, string note)
{
    ViewData["AddedNote"] = false;

    if (leadId == null)
    {
        return RedirectToAction("Index", new { initials = User.Identity.Name });
    }

    var lead = await _context.Leads.FirstOrDefaultAsync(m => m.Id == leadId);
    if (lead == null)
    {
        return RedirectToAction("Index", new { initials = User.Identity.Name });
    }

    var ownsLead = await LeadBelongsToCurrentUser(leadId.Value, User.Identity.Name);
    if (!ownsLead)
    {
        return RedirectToAction("Index", new { initials = User.Identity.Name });
    }

    _context.LeadNotes.Add(new LeadNoteModel()
    {
        LeadId = leadId.Value,
        Note = note,
        NoteDate = DateTime.Now
    });

    await _context.SaveChangesAsync();

    ViewData["AddedNote"] = true;

    return Content("Success");
}

2 个答案:

答案 0 :(得分:1)

在发出POST请求时,您应该接受参数作为Model(推荐)。提议的模型将是-

public class NoteModel
{
    public int? leadId { get; set; }
    public string note { get; set; }
}

“操作”可以为-

public async Task<IActionResult> AddNoteAsync(NoteModel model)
{
}

Jquery也可以-

<script type="text/javascript">
$(document).ready(function () {
    $('#AddNote').click(function () {
        $('#AddNote').addClass("disabled");

            var txtNote = document.getElementById('note');
            var result = document.getElementById('result');
            var postData = { leadId: @Model.Id, note: txtNote.value };
            result.innerText = "Adding note...";

            $.ajax({
                url: "@Url.Action("AddNoteAsync", "Leads")",
                type: "POST",
                data: JSON.stringify(postData),
                async: true,
                success: function (data) {
                    // removed
                },
            });
        });
    });

答案 1 :(得分:0)

解决了这个问题。我的AJAX请求中缺少此信息:

beforeSend: function (xhr) {
   xhr.setRequestHeader("XSRF-TOKEN", $('input:hidden[name="f"]').val());
},

这是从我的Startup.cs中获得的:

services.AddAntiforgery(options =>
{
    options.FormFieldName = "f";
    options.HeaderName = "XSRF-TOKEN";
});