【问题标题】:Trouble with AJAX and data formatAJAX 和数据格式的问题
【发布时间】:2017-06-13 23:22:17
【问题描述】:

我有一些使用 jQuery 的 $.ajax() 的代码。

我发现我必须通过JSON.stringify() 传递我的数据。

$.ajax({
    url: '/Resource/ReportError',
    type: 'POST',
    data: JSON.stringify({
        ResourceId: popup.data('id'),
        Reason: reason,
        Description: $('#report-error-description').val(),
        Email: $('#report-error-email').val()
    }),
    contentType: 'application/json; charset=utf-8',
    success: function (data) {
        // ...
    },
    error: function () {
        // ...
    }
});

到目前为止,一切都很好。但现在我用它来获取一些数据,只传入一个 ID。所以我想我应该改用 GET

$.ajax({
    url: '/Resource/GetInitialReviewData',
    type: 'GET',
    data: JSON.stringify({ resourceId: resourceId }),
    contentType: 'application/json; charset=utf-8',
    success: function (data) {
        // ...
    },
    error: function () {
        // ...
    }
});

但这失败了,因为服务器上的resourceIdnull 的错误。

如果我删除对JSON.stringify() 的调用,那么它可以工作!

data: { resourceId: resourceId },

谁能用通俗易懂的方式解释一下?为什么 POST 需要 JSON.stringifyGET 不需要。

【问题讨论】:

  • 如果模型的属性是简单类型,则不需要 JSON.stringify() 进行 POST(但您需要删除 contentType: 'application/json; charset=utf-8',。在 GET 中添加 contentType: 'application/json; charset=utf-8', 也是没有意义的(它有没有身体)
  • @StephenMuecke:所以是contentType 把我搞砸了?希望看到您将此评论进一步充实为答案。
  • 我需要考虑如何在不写小书章节的情况下做到这一点

标签: javascript jquery json ajax asp.net-mvc


【解决方案1】:

data 属性与type: 'GET' 结合使用时会将指定的值转换为查询字符串并将其附加到 URL。因此,如果您使用数据 {name: 'Tom'} 调用 URL http://www.test.com,您最终会得到以下 URL:

http://www.test.com?name=Tom

如果您传递一个字符串,该字符串将附加到 URL,因此调用 JSON.stringify 时生成的 URL 将是:

http://www.test.com{"name":"tom"}

当您将datatype: 'POST' 一起使用时,data 将在请求正文中发送。请求正文需要是字符串,调用JSON.stringify的原因。

【讨论】:

  • 最后一段不正确。默认的contentType'application/x-www-form-urlencoded; charset=UTF-8'(名称/值对的集合)
【解决方案2】:

您不需要将JSON.stringify() 用于 POST,尽管您可以(但通常没有必要,除非您手动生成与 c# 点和索引器符号不匹配的复杂类型或数组)。 $.ajax() 方法的默认contentType'application/x-www-form-urlencoded; charset=UTF-8',它本质上就像一个成功的表单控件名称/值对的巨大查询字符串。要查看它的外观,您可以使用console.log($('form').serialize());

如果您省略 contentType,那么您可以使用该对象而不用对其进行字符串化。

$.ajax({
    url: '/Resource/ReportError',
    type: 'POST',
    data: {
        ResourceId: popup.data('id'),
        Reason: reason,
        Description: $('#report-error-description').val(),
        Email: $('#report-error-email').val()
    },
    success: function (data) {

然后DefaultModelBinder 将使用FormValueProvider 读取数据并将其绑定到您的方法参数。

当您使用 JSON.stringify() 时,它会将您的对象转换为 JSON 格式的文本 - 一个包含名称/值对的巨大字符串(注意结果值周围的引号),您可以通过一个 string 参数接收它在您的方法中并自己反序列化它。通过添加contentType: 'application/json; charset=utf-8'DefaultModelBinder 现在将使用JsonValueProviderFactory 读取字符串,对其进行反序列化(使用JavaScriptSerializer)并将数据绑定到您的方法参数。

在 GET 的情况下,没有正文,contentType 选项不适用(将被忽略),因为DefaultModelBinder 只会从查询字符串(或路由值)中读取值。正如 maddockst 的回答中所述,通过在您的 $.ajax() GET 调用中使用 JSON.stringify(),您可以生成一个 url

.../Resource/GetInitialReviewData{"resourceId":"someValue"}

而不是必需的

.../Resource/GetInitialReviewData?resourceId=someValue

【讨论】:

    猜你喜欢
    • 2011-03-23
    • 1970-01-01
    • 1970-01-01
    • 2011-03-08
    • 2014-07-11
    • 1970-01-01
    • 2017-07-26
    • 2021-02-20
    • 2022-01-27
    相关资源
    最近更新 更多