script.aculo.usを読み解く

第9回 unittest.js(前編)

この記事を読むのに必要な時間:およそ 9 分

Ruby on RailsがリポジトリをGitHubに移したのにあわせて,Script.aculo.usも,リポジトリWikiを移転しました。私もこれからGitを覚えようと思っています。

今回解説するunittest.jsは,JavaScript用のテストライブラリです。たくさんの種類のアサートが用意されているのが特徴です。テストの結果はきれいな表組みになって,成功,失敗の数や,エラーの理由が,一覧表示されます。機能はそれだけにとどまらず,テストとテストの間に指定時間のウェイトを挟む機能,マウスの動きやキーボードイベントをシミュレートする機能,処理時間を計測する機能もあります。さらに,これは実験的にですが,RSpecのようなBDDスタイルの記述をサポートしています。

Script.aculo.us自体も,このライブラリを使って入念なテストが書かれています。このテストは,単純にバグを減らすだけにとどまらず,仕様書としての役割もあり,開発者同士の理解に役立っています。このようなテストの重要性については,[動画で解説]和田卓人のテスト駆動開発講座もあわせてご覧ください。

それではコードを見ていきましょう。

0001:// script.aculo.us unittest.js v1.8.1, Thu Jan 03 22:07:12 -0500 2008
0002:
0003:// Copyright (c) 2005-2007 Thomas Fuchs (http://script.aculo.us, http://mir.aculo.us)
0004://           (c) 2005-2007 Jon Tirsen (http://www.tirsen.com)
0005://           (c) 2005-2007 Michael Schuerig (http://www.schuerig.de/michael/)
0006://
0007:// script.aculo.us is freely distributable under the terms of an MIT-style license.
0008:// For details, see the script.aculo.us web site: http://script.aculo.us/
0009:

1~9行めは著作権表示です。

Event.simulateMouse

0010:// experimental, Firefox-only
0011:Event.simulateMouse = function(element, eventName) {
0012:  var options = Object.extend({
0013:    pointerX: 0,
0014:    pointerY: 0,
0015:    buttons:  0,
0016:    ctrlKey:  false,
0017:    altKey:   false,
0018:    shiftKey: false,
0019:    metaKey:  false
0020:  }, arguments[2] || {});
0021:  var oEvent = document.createEvent("MouseEvents");
0022:  oEvent.initMouseEvent(eventName, true, true, document.defaultView, 
0023:    options.buttons, options.pointerX, options.pointerY, options.pointerX, options.pointerY, 
0024:    options.ctrlKey, options.altKey, options.shiftKey, options.metaKey, 0, $(element));
0025:  
0026:  if(this.mark) Element.remove(this.mark);
0027:  this.mark = document.createElement('div');
0028:  this.mark.appendChild(document.createTextNode(" "));
0029:  document.body.appendChild(this.mark);
0030:  this.mark.style.position = 'absolute';
0031:  this.mark.style.top = options.pointerY + "px";
0032:  this.mark.style.left = options.pointerX + "px";
0033:  this.mark.style.width = "5px";
0034:  this.mark.style.height = "5px;";
0035:  this.mark.style.borderTop = "1px solid red;"
0036:  this.mark.style.borderLeft = "1px solid red;"
0037:  
0038:  if(this.step)
0039:    alert('['+new Date().getTime().toString()+'] '+eventName+'/'+Test.Unit.inspect(options));
0040:  
0041:  $(element).dispatchEvent(oEvent);
0042:};
0043:

10~43行目のEvent.simulateMouseは,マウスイベントを発生するための関数です(Firefox専用です)。1番めの引数にマウスイベントの発生源となる要素をとり,2番めの引数に次に挙げるイベント名のいずれかをとります。click,mousedown,mouseup,mouseover,mousemove,mouseout。3番めの引数にオプションをとることができます。

initMouseEventに渡す値をオプションで設定します。設定の詳細についてはGecko DOM ReferenceのinitMouseEventの項を参照してください。

pointerX,pointerY
マウスポインタの座標です。
buttons
どのボタンでクリックするかです。0なら通常の左ボタン,1なら中ボタン,2なら右ボタンです。
ctrlKey,altKey,shiftKey,metaKey
ctrlKeyは,Ctrlキーが押されているかです。その他も同様です。

21行目のdocument.createEventで,引数に"MouseEvents"を渡して,マウスイベントを作ります。

22~25行目でinitMouseEventでイベントの詳細な内容を設定します。

27~37行目でdiv要素を作って,マウスポインタの位置に5pxの赤い四角を表示します。

38行目でthis.stepがtrueなら,アラートで日時とイベントの情報を表示します。この機能は現在使われていません。

41行目で実際にイベントを発生させます。

Event.simulateKey

0044:// Note: Due to a fix in Firefox 1.0.5/6 that probably fixed "too much", this doesn't work in 1.0.6 or DP2.
0045:// You need to downgrade to 1.0.4 for now to get this working
0046:// See https://bugzilla.mozilla.org/show_bug.cgi?id=289940 for the fix that fixed too much
0047:Event.simulateKey = function(element, eventName) {
0048:  var options = Object.extend({
0049:    ctrlKey: false,
0050:    altKey: false,
0051:    shiftKey: false,
0052:    metaKey: false,
0053:    keyCode: 0,
0054:    charCode: 0
0055:  }, arguments[2] || {});
0056:
0057:  var oEvent = document.createEvent("KeyEvents");
0058:  oEvent.initKeyEvent(eventName, true, true, window, 
0059:    options.ctrlKey, options.altKey, options.shiftKey, options.metaKey,
0060:    options.keyCode, options.charCode );
0061:  $(element).dispatchEvent(oEvent);
0062:};
0063:

44~62行目のEvent.simulateKeyは,キーイベントを発生するための関数です(Firefox 1.0.4以下専用です)。1番めの引数にキーイベントの発生源となる要素をとり,2番めの引数に次に挙げるイベント名のいずれかをとります。keydown,keyup,keypresskey。3番めの引数にオプションをとることができます。設定の詳細についてはGecko DOM ReferenceのinitKeyEventの項を参照してください。

ctrlKey,altKey,shiftKey,metaKey
ctrlKeyは,Ctrlキーが押されているかです。その他も同様です。
keyCode,charCode
キーコードです。

57行目のdocument.createEventで,引数に"KeyEvents"を渡して,キーイベントを作ります。

58~60行目のinitKeyEventでイベントの詳細な内容を設定します。

61行目で実際にイベントを発生させます。

0064:Event.simulateKeys = function(element, command) {
0065:  for(var i=0; i<command.length; i++) {
0066:    Event.simulateKey(element,'keypress',{charCode:command.charCodeAt(i)});
0067:  }
0068:};
0069:

64~69行目のEvent.simulateKeysは,上述のsimulateKeyを連続して呼ぶ関数です。引数にキーイベントの発生源となる要素と,文字列を取ります。この文字列の1文字1文字のcharCodeで,keypressイベントが連続して発生します。

著者プロフィール

源馬照明(げんまてるあき)

名古屋大学大学院多元数理科学研究科1年。学部生のときにSchemeの素晴らしさを知ったのをきっかけに,関数型言語の世界へ。JavaScriptに,ブラウザからすぐに試せる関数型言語としての魅力と将来性を感じている。

ブログ:Gemmaの日記

コメント

コメントの記入