jQuery使用(new Function(“return”+ data))();而不是eval(数据);解析JSON,为什么?

时间:2010-03-15 17:46:18

标签: javascript jquery json

This link向您展示jQuery对旧版浏览器使用(new Function("return " + data))();来解析JSON字符串而不是eval()

这有什么好处?如果JSON字符串不是安全

,该怎么办?

3 个答案:

答案 0 :(得分:32)

尼克答案中的引言暗示了这一点。这并不是一个很大的区别,但感觉evalnew Function更糟糕。不是在安全性方面 - 面对不受信任的输入,它们同样无用,但希望你的webapp不会返回不受信任的JSON字符串 - 但是在语言级别的怪异方面,因此对优化的抵制。

具体做法是:

function victim() {
    var a= 1;
    eval('a= 2');
    return a;
}

给出2eval ed字符串已在victim的局部变量范围内运行!这是常规用户编写的功能永远不会做的事情; eval只能这样做,因为它是黑魔法。

使用常规函数取消了这个魔法元素:

function victim() {
    var a= 1;
    (new Function('a= 2;'))();
    return a;
}

在上面,返回的a仍为1;新函数只能在自己的局部变量或全局window.a上运行。

这些知识允许代码分析工具(可能包括JavaScript引擎,特别是聪明的minifiers)应用更多优化。例如,第二个victim函数可以将a变量完全优化到return 1eval的一种用法和许多潜在的优化是不可行的。

当然,在像JSON eval这样的小函数的实践中,不会有明显的区别,但总的来说,思路是:

  • 尽可能避免两种方法(在ECMAScript第五版的严格模式中都不允许使用它们);
  • 如果必须使用一个,new Function优于eval,除非您确实需要代码来访问调用函数的局部变量。

答案 1 :(得分:11)

至于为什么jQuery专门使用new Function()John Resig answered this on the jQuery forums

  

使用eval会导致代码缩小器出现各种问题,因为不清楚eval中可能执行的是什么。查看该运行的最后结果,看起来新函数与eval相当,有时甚至略快。一个例外是Safari 4 - 但这些结果已过时,Safari 4附带了我们使用的原生JSON.parse实现。

答案 2 :(得分:3)

http://www.json.org/js.html

  

eval功能非常快。但是,它可以编译并执行任何JavaScript程序,因此可能存在安全问题。当来源信任且胜任时,会显示eval的使用情况。 使用JSON解析器更安全。在基于XMLHttpRequest的Web应用程序中,只允许与提供该页面的同一源进行通信,因此它是可信的。但它可能不能胜任。如果服务器的JSON编码不严格,或者它没有严格验证其所有输入,那么它可能会传送无效的JSON文本,这些文本可能带有危险脚本。 eval函数将执行脚本,释放其恶意。

您对安全的具体含义是什么? 至少不执行恶意代码;)

另请参阅:Alternatives to JavaScript eval() for parsing JSON

另一点可能是,new Function()被认为是little faster而不是eval

<强>更新

您基本上可以在comments on jQuery's .parseJSON() function中阅读相同的参数。