2009-12-11 25 views
14

Webフレームワークで使用されるJSを開発しています。頻繁に他の開発者(エラーが発生する可能性が高い)のjQueryコードと混在しています。残念ながら、jQuery(document).readyブロックのエラーは、私の実行を妨げています。次の簡単なサンプルを取る:jQueryのエラー処理(ドキュメント).ready

<script type="text/javascript"> 
    jQuery(document).ready(function() { 
     nosuchobject.fakemethod();  //intentionally cause major error 
    }); 
</script> 
<script type="text/javascript"> 
    jQuery(document).ready(function() { 
     alert("Hello!");     //never executed 
    }); 
</script> 

二準備のブロックにかかわらず、前に何が起こったかの実行ではないでしょうか?以前のエラーの場合でも実行されるjQuery(ドキュメント).readyを実行する "安全な"方法はありますか?

EDIT:エラーが発生しやすいブロックは、他の作者によって書かれ、任意に混合されているため、コントロール/可視性がありません。

答えて

13

と同じであり、潜在的な混乱を避けるために、それが動作するはずです(少なくとも、アイデアべきとにかく)。 jqueryの後にそれを含めてくださいが、バグの可能性があるスクリプトの前に必ず入れてください。(不要、コメントを参照してください。)

var oldReady = jQuery.ready; 
jQuery.ready = function(){ 
    try{ 
    return oldReady.apply(this, arguments); 
    }catch(e){ 
    // handle e .... 
    } 
}; 
+0

これは、バグの可能性のあるスクリプトの前後にかかわらず、うまく機能しているようです。私がやることは、準備ブロックの内容(サンプルのアラート(「こんにちは!」)をキャッチブロックの直後に移動することだと思います。そうすれば、私の準備ブロックは、前の準備ブロックの終わりに自分自身を「追加」することができます。 – 3hough

+0

すばらしい解決策。決してそれを考えたことはありません。 –

+0

私は何を考えていたのか分かりませんが、タグであり、いくつかのonloadイベントではない限り、どこに行くにしてもうまくいくでしょう。私たちはDOMロードで呼び出される前にreadyメソッドをハイジャックしています。 – jvenema

1

try ... catch bracketでエラーが発生しやすいコマンドをラップしようとしましたか?

$(function(){ 
    try { 
     noObject.noMethod(); 
    } catch (error) { 
     // handle error 
    } 
}); 

$(function(){ 
    try { 
     alert("Hello World"); 
    } catch (error) { 
     // handle error 
    } 
}); 

$(function(){ ... });は、機能的に $(document).ready(function(){ ... });私はこのコードを試していない

+0

問題は、私は、エラーをスローブロックを制御/可視性を持っていないということです。上記のサンプルでは、​​最初のjQuery(document).readyブロックは他人のコードから来ています。したがって、私はtry/catchブロックでラップする方法はありません。 これは、Webフレームワークの一部で、任意のプラグインをドキュメントの先頭に一緒に読み込むことができます。 – 3hough

+2

あなたは自分のコードにアクセスできないことをあなたの質問で述べるべきです。 – Sampson

-2

あなたはあなたのコードブロックのそれぞれの前にjQueryを参照し直すことができます。あなたのコードは、ライブラリの新しいインスタンスを使用し、実行されます。私はOSXのSafari 4.0.3でこれをテストしました。あなたの質問に答えるために

<html> 
<head> 
    <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"></script> 
    <script type="text/javascript"> 
     jQuery(document).ready(function() { 
            nosuchobject.fakemethod();       //intentionally cause major error 
        }); 
    </script> 
    <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"></script>  
    <script type="text/javascript"> 
        jQuery(document).ready(function() { 
            alert("Hello!");                 //executed! 
        }); 
    </script> 

</head> 
<body> 

<p>hello world</p> 

</body> 
</html> 
+0

恐ろしいアイデア...これは少なくともユーザーにライブラリを2度ダウンロードさせることになり、静的変数やオブジェクトを上書きする際に問題を引き起こす可能性があります。 – jvenema

+0

ユーザーのブラウザは、キャッシュ・バスターが配置されている場合にのみリモート・ファイルを再ダウンロードします。私の例では、ブラウザはキャッシュから2番目のjQueryリファレンスを読み込みます。それはかろうじてではありませんが、元の問題を解決するのに役立ちます。静的変数やオブジェクトに関する問題については、jQueryライブラリ自体、またはユーザー定義の静的変数やオブジェクト内での意味ですか?上書きの場合、jQueryはそれ自身をマップします。私の例では、正しく書き込まれた2番目のブロックはjQueryの新しいインスタンスを参照します。あなたが言及した問題について詳しく説明していただけますか?ありがとう! – simeonwillbanks

+0

jqueryの冒頭に、jQuery.fn = jQuery.prototype = {...}と表示されます。これらのオブジェクトは拡張されていませんが、インスタンス化されているため、これらのプロパティを変更または変更するもの(実際にはjqueryレベルで静的に設定されているもの)はすべて破棄されます。ブラウザがjsをキャッシュしても、それを再解析して宣言されたすべての要素を再ロードしなければならないため、ユーザーエクスペリエンスが低下します(domのクリーンアップがないためメモリリークが発生する可能性がありますイベント)。 – jvenema

2

readyブロックの両方が、本質的にはjQueryが動作する方法与えられた一つに結合されています

<script type="text/javascript"> 
    jQuery(document).ready(function() { 
     nosuchobject.fakemethod();  //intentionally cause major error 
     alert("Hello!");     //never executed 
    }); 
</script> 

その上記のエラーごとに警告していないだから、なぜです。私はすべてのready関数が以前の失敗に関係なく動作するようにこれを修正する方法があるとは思わない。ここで

1

が解決され、それはtry-catchブロックで準備に送信された任意の関数をラップします:

(function($){ 
    $.fn.oldReady = $.fn.ready; 
    $.fn.ready = function(fn){ 
     return $.fn.oldReady(function(){ try{ if(fn) fn.apply($,arguments); } catch(e){}}); 
    } 
})(jQuery);