昨日のエントリの続き。
WordPress.com Stats 日本語版の JavaScript を並列読み込み対応にしてみましょう。
WordPress.com Stats 日本語版で JavaScript を読み込み、動作用の JavaScript をフッタに書き出しているのは、stats.php の 107 〜 113 行目の以下のコード。
<script src="http://stats.wordpress.com/e-<?php echo gmdate('YW'); ?>.js" type="text/javascript"></script> <script type="text/javascript"> st_go({<?php echo stats_array($a); ?>}); var load_cmc = function(){linktracker_init(<?php echo "{$a['blog']},{$a['post']},2"; ?>);}; if ( typeof addLoadEvent != 'undefined' ) addLoadEvent(load_cmc); else load_cmc(); </script>
まず、外部 JavaScript http://stats.wordpress.com/e-<?php echo gmdate('YW'); ?>.js
を読み込み、その後 st_go()
関数、linktracker_init()
関数を呼び出しています。
外部 JavaScript の読み込みが完了してからでないと st_go()
関数を呼び出すことはできないため、並列読み込みでは問題が生じます。
# JavaScript のロード完了まで待たないで継続処理を行われると処理不可能。
また、st_go()
関数の中では document.write()
を使って <img>
タグを書き出しているため、単純に DOM 操作で <script>
タグを head 内にブチ込むだけでは、うまくいきません。
まずは、JavaScript のロード完了を待って処理を行う方法。
色々あるとは思いますが、今回は Yahoo! UI Library の Get Utility を使用して JavaScript の動的ロードを行います。
これを使うと以下のようにして、ロード成功時・失敗時のコールバック関数を指定することができます。
YAHOO.util.Get.script( [ 'http://example.com/javascript_1.js', 'http://example.com/javascript_2.js' ] ,{ onSuccess: function(){alert('OK!');}, onFailure: function(){alert('Fail!');} } );
# 第一引数は、ロードしたい外部 JavaScript ファイルの URL
# 第二引数は、オプションでロード成功時・失敗時のコールバック関数等を指定できる
このライブラリを WordPress サイトに読み込むためには、以下のコードを stats.php の適当な場所に追加してください。
// YUI Get Utility の読み込み (管理画面以外の場合のみ) function stats_scripts() { if ( !is_admin() ) { wp_register_script('yui-core', 'http://yui.yahooapis.com/2.5.2/build/yahoo/yahoo-min.js', false, '2.5.2'); wp_register_script('yui-get', 'http://yui.yahooapis.com/2.5.2/build/get/get-min.js', array('yui-core'), '2.5.2'); wp_enqueue_script('yui-get'); } } add_action( 'wp_print_scripts', 'stats_scripts' );
これで準備完了。
次に stats.php の 107 〜 113 行目を以下のように修正すれば、外部 JavaScript を動的にロードした後、アクセス解析処理を行います。
<script type="text/javascript"> YAHOO.util.Get.script('http://stats.wordpress.com/e-<?php echo gmdate('YW'); ?>.js', { onSuccess: function(){ // document.open(), document.close(), document.write() の退避 var _open = document.open; var _close = document.close; var _write = document.write; // document.open(), document.close(), document.write() の再定義 document.open = function(){}; document.close = function(){}; // div 要素を作成して body の最後に追加 document.write = function(h){ var d = document.createElement('div'); d.innerHTML = h; var b = document.getElementsByTagName('body')[0]; b.appendChild(d); }; // stats 開始 (st_go() 関数内で document.write() が呼び出される) st_go({<?php echo stats_array($a); ?>}); // 退避していた document.open(), document.close(), document.write() を元に戻す document.open = _open; document.close = _close; document.write = _write; // linktracker の初期化 var load_cmc = function(){linktracker_init(<?php echo "{$a['blog']},{$a['post']},2"; ?>);}; if ( typeof addLoadEvent != 'undefined' ) addLoadEvent(load_cmc); else load_cmc(); }}); </script>
以下、簡単な説明。
108 行目で JavaScript を動的にロードします。ロード成功後に実行されるスクリプトが 109 〜 136 行目。
126 行目で呼び出している st_go()
関数では document.write()
を使って <img>
タグを書き出しています。
このままだと head 内に document.write()
で書き出されてしまうため、うまくありません。
と言うわけで 114 〜 123 行目で、document.open()
, document.close()
, document.write()
をオーバーライド。
document.write()
が呼び出されたら body の最後に <div>
タグを作って、その中に書き込むように document.write()
の処理を変更します。
これで JavaScript のロードを並列読み込み対応にした WordPress.com Stats プラグインの完成です。
この改造版の WordPress.com Stats プラグインは、昨日から当サイトで丸1日動かしてみてますが、正常にアクセスログを取得できているようなので大丈夫でしょう。
おまけ
Google Analytics を並列読み込み対応にするのは、もうちょっと簡単。以下のようにするだけです。
YAHOO.util.Get.script('http://www.google-analytics.com/urchin.js',{onSuccess:function(){ _uacct = "Google Analytics の ID"; urchinTracker(); }});
ロード対象の外部 JavaScript の中で document.write()
を使ってなければ、Yahoo! UI Library の Get Utility は気軽に使えます。