isyumi_netブログ

isyumi_netがプログラミングのこととかを書くブログ

現在時刻を外から入れよう

時刻によって動作が変わるプログラムを書いた時、どうやってテストしているだろうか。手作業で書き換えているかもしれない。

String getAisatu() {
// var date = new DateTime.now();
var date = new DateTime(2017, 10, 28, 18, 0);
if (date.hour > 17) {
return "こんばんは";
}
return "こんにちは";
}

 

 もっといい方法を紹介しよう。プログラム言語のinterface機能を使ったことがあるだろうか。あったら申し訳ない。このブログは初心者を対象にしている。interfaceプログラミングの詳細な説明は省く。とりあえずおなじinterfaceを実装していれば中身をすげ替えてもいいというルールがある。これを使おう。CurrentTImeService interfaceと現在時刻を返すクラスとダミー日付を返すクラスを作ろう。Dartでinterfaceはabstruct classという宣言をすることになっているが、適宜読み替えて欲しい。

// 共通のinterface
abstract class CurrentTimeService {
DateTime getDateTime();
}

// 本当に現在時刻を返す
class ProdCurrentTimeService implements CurrentTimeService {

@override
DateTime getDateTime() {
return new DateTime.now();
}
}

// ダミー日付を返す
class DummyCurrentTimeService implements CurrentTimeService {
DateTime dateTime;

DummyCurrentTimeService(DateTime dateTime){
this.dateTime = dateTime;
}

@override
DateTime getDateTime() {
return dateTime;
}
}

そして、現在時刻を取得する関数は引数にCurrentTimeServiceを取り、それに現在時刻を問い合わせるようにしよう。

String getAisatu(CurrentTimeService currentTimeService) {
var date = currentTimeService.getDateTime();
if (date.hour > 17) {
return "こんばんは";
}
return "こんにちは";
}

そして、呼び出し側でProdとDummyを差し替えられるようにしておこう。環境変数なので自動で切り替えられるようにしておくといい。

void main() {
var currentTimeService = new DummyCurrentTimeService(new DateTime(2017, 10, 28, 18, 0));
// var currentTimeService = new ProdCurrentTimeService();

print(getAisatu(currentTimeService));

}

 

 これで時刻を色々指定して動作確認ができるようになった。この手法はHTTPリクエストや乱数の生成など、挙動が予想できないメソッドのテストに有効だ。