数日前、オデッサの典型ではない比較的暖かい冬の夜に家に帰るとき、私は「6か月前にボグダンが尋ねたことをやってみたらどうだろう? 家に着いて、私はコンピューターの電源を入れ、数分以内に、私が計画していたことをしました。 まず、組み込みメソッドが再定義された場合の動作に興味があり、その後、再定義前の以前の状態を何らかの方法で思い出すことができます。 オブジェクトが再定義された場合、その参照は破棄されず、以前の外観が保持されることを知っていました。 組み込み関数に関しては、疑問がありました。 それはあなたができることが判明しました。
ほとんどの場合、そのようなツールを使用する必要はありませんが、純粋に仮説的に、誰かが関数の呼び出しを追跡するタスクを持ち、各呼び出しでレポートを受け取り、
- 実行結果
- 渡された引数
- 呼び出しのコンテキスト(呼び出し時のこれは何ですか)
- ハンドラー作成後の関数呼び出しの数
(このリストは、ハンドラーに渡される引数と完全に一致しています)
addCallListener = function(func, callback){ var callNumber = 0; return function(){ var args = [].slice.call(arguments); var result; try { result = func.apply(this, arguments); callNumber++; } catch (e) { callback(e, args, this, callNumber); throw e; } callback(result, args, this, callNumber); return result; } }
非常にシンプルで簡潔ですね。
次に、いくつかの関数を次のように再定義します。
someFunct = addCallListener(someFunct, function(result, args, self, callNumber){ //Do Something }); // Constructor.prototype.method = addCallListener(Constructor.prototype.method, function(result, args, self, callNumber){ //Do Something });
明らかに、これが発生するコードのその部分で「見える」はずです。
いくつかの例
例を実行するには、開いているコンソールが必要です(ChromeではCtrl + Shift + iで呼び出されます)。アニメーション追跡:
jsfiddle.net/finom/DnRD8
配列内のプッシュメソッド実行のイベント:
jsfiddle.net/finom/bbHhH/1
他の機能の実行イベント:
jsfiddle.net/finom/ah5My/3
終わり。
批評と追加についてjavascript.ruフォーラムの仲間に感謝します。
UPD
関数を少し拡張しました。1つのコールバックではなく、2番目の引数がオブジェクトになりました
- before(関数が実行される前に呼び出されます)
- 成功(関数が正常に機能した場合に呼び出されます)
- エラー(エラーが発生した場合)
- 後(とにかく、成功に関係なく呼び出されます)
オブジェクトは各ハンドラーに渡されます。
- args
- 自己(コンテキスト)
- name(関数名)
- ステータス(「エラー」または「成功」)
- successNumber(成功した呼び出しの数)
- errorNumber(エラーのある呼び出しの数)
- 結果(結果がある場合)
- エラー(エラーがある場合)
また、addCallListener関数は、ウィンドウまたはプロセスへのアクセスを回避するために、Functionコンストラクターオブジェクトの一部になりました。
ここで分岐およびテストできます: jsfiddle.net/finom/SGhzd/5