ajaxリクエストは、ユーザーの入力で満たされた標準のJSON配列を返します。入力はサニタイズされており、eval()関数を使用して、JavaScriptオブジェクトを簡単に作成し、ページを更新できます...
これが問題です。入力をサニタイズしようとしても、eval()関数は使いたくありません。「evalなしでAJAXのJSON」を使用する方法についてグーグルをチェックし、さまざまな方法に出くわしました...
どちらを使うべきですか?これを行うための標準的で実績のある安全な方法はありますか?
ajaxリクエストは、ユーザーの入力で満たされた標準のJSON配列を返します。入力はサニタイズされており、eval()関数を使用して、JavaScriptオブジェクトを簡単に作成し、ページを更新できます...
これが問題です。入力をサニタイズしようとしても、eval()関数は使いたくありません。「evalなしでAJAXのJSON」を使用する方法についてグーグルをチェックし、さまざまな方法に出くわしました...
どちらを使うべきですか?これを行うための標準的で実績のある安全な方法はありますか?
json.org には素敵なJavaScript ライブラリがあります
簡単な使い方:
JSON.parse('[{"some":"json"}]');
JSON.stringify([{some:'json'}]);
編集:コメントで指摘されているように、ソースを調べると、これは eval を使用します(ただし、最初にサニタイズされているように見えます)
完全に回避するには、json_parseまたはjson-sans-evalを見てください
json2.js は安全でない、json_parse.js は遅い、json-sans-eval.js は検証されない
これを行うための標準的で実証済みの安全な方法はありますか?
JavaScript の今後の ECMAScript 3.1 バージョンで、これを行う標準的な方法が提案されています: JSON.parse。
IE8、Firefox 3.1/3.5、および将来的には他の一般的なブラウザーでサポートされる予定です。当面は、eval() にフォールバックするか、eval() のみを使用できます。それは悪であるかもしれないし、そうでないかもしれません。確かに JSON.parse より遅くなります。しかし、これが今日の JSON を解析する通常の方法です。
攻撃者が、JSON を介して吐き出しているコンテンツに悪意のある JavaScript を挿入できる場合、eval-is-evil よりも心配すべき問題が大きくなります。
入力がサニタイズされたら、evalが最善の方法だと思います。サーバーが危険にさらされた場合でも、ユーザーは必要なスクリプトをクライアントに送信できるようになります。したがって、評価を行うことは大きなセキュリティリスクではありません。クライアントに到達する前にパケットを操作する人が心配な場合は、スクリプト自体を変更できます。
評価について心配する必要はありません。ただし、JSONが破損した場合にユーザーがJSエラーを受け取らないように、必ずtry...catchブロックでラップしてください。
:)
JSON を JS オブジェクトに安全に変換するには、このライブラリが提供する JSON.parse() 関数などの JSON パーサーを使用する必要があります。
コマンドデザインパターンと比較してください:http://en.wikipedia.org/wiki/Command_pattern。これにより、クライアントが実行できる操作を正確に定義でき、アプリケーションは基本的な解釈と同じくらい安全になります。
あなたが衛生状態で達成しようとしていることに依存します。JSONと安全な評価に対するプロトタイプフレームワークのサポートにより、私は大きな成功を収めました。
問題: eval がもたらす問題は、eval がグローバル スコープで実行されることです。
eval.call(document, "console.log(this)")
eval.call(navigator, "console.log(this)")
eval.call(window, "console.log(this)")
(function(){eval.call(document, "console.log(this)")})()
>Window
シナリオ:
属性onvisibleなど、さまざまなドキュメント要素のマークアップ コードで個々の属性を使用しているとします。
<img src="" onvisible="src='http://www.example.com/myimg.png';">
この属性を持つすべての要素を取得し、onvisible-content-string をクロージャーに変えて、それを EventHandler キューに入れたいとします。ここで、JS Function コンストラクターの出番です。
Function === 0..constructor.constructor
>true
Function('return [this, arguments]').call(window, 1,2,3)
>Window, Arguments[3]]
Function('return [this, arguments]').call(document, 1,2,3)
>Document, Arguments[3]]
Function('return [this, arguments]').call(navigator, 1,2,3)
>Navigator, Arguments[3]]
すべてを一緒に入れて:
var eventQueue = [];
var els = document.querySelectorAll('[onvisible]');
for (var el in els) {
var jscode = els[el].getAttribute('onvisible');
eventQueue.push( {el:els[el], cb:Function(jscode)} )
}
//eventQueue[0].cb.call(scope, args);
jQueryから「盗まれた」
// Try to use the native JSON parser first
return window.JSON && window.JSON.parse ?
window.JSON.parse( data ) :
(new Function("return " + data))();