在jQuery + Datatables中设置`processData:false`会将未知内容添加到我的Ajax调用的URL中

时间:2016-08-29 13:12:24

标签: javascript jquery ajax datatables

this post 中,我想自动将我的所有Ajax请求转换为JSON,并且它已正常运行。

但是,我注意到有时jQuery会在反缓存参数(例如&[object%20Object])之前的URL末尾添加一个神秘的_=1472476048876,因为我也有{ {1}}设置。

当我将processData改为true时,神秘部分消失了。有人有什么想法吗?我使用cache: false

编辑:我注意到只有在通过Datatables jQuery 2.1.4 API进行Ajax调用时才会产生错误。还有其他人有这个问题吗?

编辑2 :为了回应@ war10ck的好答案,澄清一下,我发出G​​ET请求,但我没有发送任何数据。我手工创建了URL,因此我认为Datatables正在向我的请求添加一些数据(甚至可能是空对象),这些数据将变为.load()

3 个答案:

答案 0 :(得分:2)

我想我找到了问题的根源。在数据表的内部深处,在一个名为_fnBuildAjax的函数中,即使您不提供任何data参数,也有两行执行以下操作:

var tmp = {};
// ...if data is empty...
data = tmp;

这最终将一个空对象传递给jQuery ajax调用,该调用进一步向下靠近同一函数的底部。通常jQuery会接受这个空对象并且不会更改调用,但由于processDatafalse,jQuery会将其附加到URL(毕竟是GET请求)并将其转换为[object%20Object]即使它是一个空对象。这只发生在Datatables上,因为我的代码中的其他地方我只是没有为Ajax调用指定data参数,jQuery足够聪明,根本不向URL附加任何内容,但是当它看到一个空对象时它不会#39;不知道该做什么并按原样追加。我希望这有助于未来的程序员调试这个边缘情况:)。再次感谢@ war10ck的解释。

答案 1 :(得分:1)

听起来您正在发出GET请求,无论是通过您自己的jQuery调用还是通过Datatables。在GET请求中,参数通过url查询字符串发送到服务器:

example.com?key1=value1&key2=value2

jQuery在$.ajax()中幕后操作的部分抽象是将通过对象中的data参数传入的数据转换为适合请求的格式。对于内容类型为GET的标准application/x-www-form-urlencoded请求,它是由&符号分隔的一串键/值paris。当您在应用程序中使用的数据是JavaScript对象时,这非常有用。举个例子:

var obj = {
    key1: value1,
    key2: value2
};

$.ajax({
    type: "GET",
    url: "www.example.com",
    data: obj
});

被叫网址的结果为:

www.example.com?key1=value1&key2=value2

因为jQuery为你做幕后数据转换。 然而 ,根据docs

  

data参数:

     

要发送到服务器的数据。如果不是字符串,它将转换为查询字符串。它附加到GET请求的URL。请参阅processData选项以防止此自动处理。对象必须是键/值对。如果value是一个数组,jQuery会根据传统设置的值使用相同的键序列化多个值(如下所述)。

  

processData参数

     

默认情况下,作为对象传入数据选项的数据(技术上,不是字符串)将被处理并转换为查询字符串,适合默认内容类型" application / x- WWW窗体-urlencoded&#34 ;.如果要发送DOMDocument或其他未处理的数据,请将此选项设置为false。

processData设置为false会阻止默认数据操作以及从Object格式转换为合适的网址String。相反,当调用url时,浏览器会自动使用.toString()原型在Object原型上转换数据。这是出现的方式:



var obj = {};
alert(obj.toString());




现在,由于默认处理已关闭,因此您的数据示例将变为以下内容:

var obj = {
    key1: value1,
    key2: value2
};

$.ajax({
    type: "GET",
    url: "www.example.com",
    data: obj,
    processData: false
});

被叫网址的结果为:

www.example.com?[object%20Object]

就像您在迷你代码段中看到的那样,额外添加了%20作为空格的网址编码值,如RFC 3986中所述并由RFC 6874更新{ {3}}

编辑以详细说明数据广告导致上述问题的原因:

为了进一步解决为什么只有RFC 7320 .load()出现问题的问题, datatables 对象似乎是jQuery&#的包装器39;默认$.ajax()。在$.ajax() type GET GET参数中,如果没有直接指定,则默认为processData。因此, datatables 会发起false请求,并且public class Conversation { [PrimaryKey, Unique, AutoIncrement] public int ID { get; set; } public string toUser { get; set; } public string FromUser { get; set; } [ManyToMany(typeof(ChatConversation), CascadeOperations = CascadeOperation.All)] public List<ChatMessage> ChatMessages { get; set; } [OneToMany(CascadeOperations = CascadeOperation.All)] public List<ConversationDeleted> DeletedConversations { get; set; } public DateTime CreatedAt { get; set; } public int UserID { get; set; } } 设置为 public class ChatMessage { [PrimaryKey, Unique, AutoIncrement] public int ChatMessageID { get; set; } public string fromUser { get; set; } public string toUser { get; set; } public string Message { get; set; } public bool DeliveryStatus { get; set; } public DateTime CreatedAt { get; set; } [Unique, AutoIncrement, NotNull] public Guid UniqueID { get; set; } [ManyToMany(typeof(ChatConversation), CascadeOperations = CascadeOperation.All)] public List<Conversation> Conversation { get; set; } [OneToMany(CascadeOperations = CascadeOperation.All)] public List<MessageDeleted> MessagesDeleted { get; set; } public int UserId { get; set; } } ,就会出现上述情况。

答案 2 :(得分:0)

谢谢你们!除了帮助我解决问题的研究之外,我想分享相应的解决方案。

在我的情况下,问题是类似于

的调用

http://server/dir/resource.en.json?_=1510566367817

导致了 http://server/dir/[object%20Object]?_=1510566367817

主要提示是daveslab'关于处理空物体的提示。

结合多语言项目环境,我开始考虑丢失资源文件。这就是空对象加入游戏的地方,因为缺少相关的resource.fr.json文件。

在这种情况下,如果processData设置为false或true则无关紧要。 我检查了两个。

摘要

客户端代码调用但在服务器上丢失的Json文件可能会导致同样的问题。

我案中的客户事实: 我使用jquery 3.2.1 AJAX Get-Service和以下配置

{
    dataType: "json",
    async: true,    
    cache: false,
    processData: false 
}