AJAX Post to ASP.NET MVC 6 Controller操作方法和参数为null

时间:2016-02-16 20:19:26

标签: jquery asp.net ajax asp.net-mvc asp.net-core-mvc

我对ASP.NET MVC有一个奇怪的问题并发送了一个AJAX帖子。我在页面上有一个id为'lnkGetExpirDates'的锚标记。当用户点击它时,我试图简单地将这个硬编码数据发送到我的控制器,这样它就可以将它作为参数使用并将结果返回给页面。

但是,在控制器中,参数始终为空/默认值。请参阅下面的代码,如果我犯了一个愚蠢的错误,请告诉我。

这是我的AJAX帖子:

$("#lnkGetExpirDates").click(function () {
    e.preventDefault();

    var data = {
        StartDate: "1/19/2016",
        EndDate: "4/19/2016",
        ProductType: "New",
        Count: 1
    };


    $.ajax({
        url: '/Products/GetExpirationDates',
        type: 'POST',
        data: JSON.stringify(data),
        contentType: 'application/json; charset=utf-8',
        dataType: 'html',
        success: function (data) {
            $('#ExpirationDates').val(data);
        }
    });

});

这是我的控制器的操作方法:

// POST: Product/GetExpirationDates
[HttpPost]
//[ValidateAntiForgeryToken]
public IActionResult GetExpirationDates(GetExpirationDatesViewModel vm)
{
    // TODO: Get expiration dates and return them in the response

    return View();
}

以下是GetExpirationDatesViewModel:

public DateTime StartDate { get; set; }
public DateTime EndDate { get; set; }
public string ProductType { get; set; }
public int Count { get; set; }

请注意,我甚至在没有使用模型的情况下尝试了这一点,只是简单地向Action方法添加参数,例如startDate,endDate,productType和Count,但所有内容都是null。

1 个答案:

答案 0 :(得分:11)

当您将内容类型值指定为application / json时,对服务器发出的ajax请求将在请求主体(以json格式)中将您的js对象作为请求有效负载发送。因此,在您的操作方法中,您应该使用[FromBody]属性。

public IActionResult GetExpirationDates([FromBody] GetExpirationDatesViewModel vm)
{
   return View();
}

当您想要发送具有属性的复杂js对象时,应该执行此操作,该属性又是另一个模型/类型

但您发送的数据是平面视图模型。所以你真的不需要json字符串化js对象。您也可以删除内容类型属性,也不会发送复杂js对象的字符串化版本。

这应该可以正常工作。

$.ajax({
    url: '/Products/GetExpirationDates',
    type: 'POST',
    data: data,      
    dataType: 'html',
    success: function (data) {
        console(data);
    }
});

上面的代码将js对象作为键值对(普通表单数据)发送,模型绑定器将能够将表单数据映射到服务器中的视图模型对象。请查看this post以获取更详细的说明。

另外,我建议您使用Url.Action辅助方法为操作方法生成正确的相对URL。

url: '@Url.Action("GetExpirationDates","Products")',

如果您的js代码位于剃刀视图中,则上述应该有效。如果您的代码位于外部js文件中,请使用this post中描述的解决方案。