Test::LoadAllModules で全てのモジュールがuseできるかテストするB!

前置き

みなさんこんにちは、dann です。

こちらは hacker track ということで、僕がつくったモジュールの一つを紹介したいとおもいます。今回ご紹介するモジュールは Test::LoadAllModules です。

本題

Test::LoadAllModules は非常に小粒なツールですが、なかなかいいモジュールなんじゃないかと自分でもおもっています。

モジュールを作るときには、「このモジュールがuseできるか」というようなテストをすることはままあります。00_compile.tなどで以下のようなコードを書いたり、モジュールごとのテストでuse_okするコードなどを書いているのではないでしょうか。

例えば、従来は、毎回以下のようにコードを書いていました。モジュールが増えるとuseできるかのテストするコードが増え、書き忘れたりするため冗長です。

use strict;
use Test::More tests => 1;

BEGIN { use_ok 'Module::Hoge1' }

しかし、Test::LoadAllModules を使えば、以下のように書くだけでいいのです。とても楽ちんですね。

use Test::LoadAllModules;

BEGIN {
    all_uses_ok(search_path => 'MyApp');
}

また、いくつかのファイルを除いてテストしたい時なども簡単に書けます。

例えば、Mouse::Role系などは代表的なものです。

use Test::LoadAllModules;

BEGIN {
    all_uses_ok(
        search_path => 'MyApp',
        except => [
            'MyApp::Role',
            qr/MyApp::Exclude::.*/,
        ]
    );
}

複数のパス以下のファイルをコンパイルしたい場合なども以下のように簡単に書く事ができます。

use Test::LoadAllModules;

BEGIN {
    all_uses_ok(
        search_path => 'MyApp',
        lib => [
            'lib',
            't/lib',
        ]
    );
}

関連モジュール

本モジュールは開発時に使うことを想定しているため、META.yamlからではなく、libに指定したパスからファイルを探すことでテストをします。こうすることで、prove単体で直接テストをすることができ、テストを早くすることができます。

Test::Compileという類似したモジュールもあるのですが、こちらのモジュールは本当にすべてのpmファイルをuseしてしまうため、除外ルールを指定できないため、MouseのRoleなどuseしてテストをしたくないものがある場合に使えません。

また、MANIFEST に記述されたファイルをテストするTest::UseAllModulesなどもあります。しかし、META.yamlにモジュールを追加してからテストしなければいけないので、開発時には向いていません。このモジュールは、リリーステストに向いているといえるでしょう。

まとめ

今回は Test::LoadAllModules について、解説しました。

このモジュールは、同様の処理を何度も書いたり見かけたりしているうちに、「もうめんどくさいからモジュールにしちゃおう」とおもって作りました。普段から「定型的なコードがないだろうか」と気をつけていることが重要ですね。

というわけで今回はここまで。明日はMr.XSこと id:gfx さんです。