CLOVER🍀

That was when it all began.

Mochaでブラウザで動くテストを書く

Mochaを使った、ブラウザ上でのテストにトライしてみます。

Running Mocha in the Browser

こちらを見ると、以下のようなHTMLを作成すればよいみたいです。

Mochaのテスト結果を書き込むための、#idを持つHTMLタグ。

<div id="mocha"></div>

Mochaのセットアップとテストコード。

  <script src="https://cdn.rawgit.com/jquery/jquery/2.1.4/dist/jquery.min.js"></script>
  <script src="https://cdn.rawgit.com/Automattic/expect.js/0.3.1/index.js"></script>
  <script src="https://cdn.rawgit.com/mochajs/mocha/2.2.5/mocha.js"></script>

  <script>mocha.setup('bdd')</script>
  <script src="test.array.js"></script>
  <script src="test.object.js"></script>
  <script src="test.xhr.js"></script>
  <script>
    mocha.checkLeaks();
    mocha.globals(['jQuery']);
    mocha.run();
  </script>

まあ、このまま書くのもなんなので、Browserify+gulpで似たようなことをやってみようかなと。

まずは、npmプロジェクトを作成。

$ npm init
$ npm install -g gulp
$ npm install --save-dev gulp browserify gulp-load-plugins gulp-uglify gulp-sourcemaps gulp-plumber gulp-mocha gulp-util gulp-open gulp-webserver mocha through2 del
$ npm install --save jquery should

テスト対象側では、jQueryを使うものとします。

テスト対象のコード。
src/message.js

var Message = {};

Message.write = function(selector, message) {
    var $ = require("jquery");
    $(selector).text(message);
};

module.exports = Message;

テストコード。
test/message-test.js

var should = require("should");

describe("write message", function() {
    it("test", function() {
        var selector = "#target";
        var messageText = "Hello World";

        var message = require("../src/message");
        message.write(selector, messageText);

        var $ = require("jquery");
        $(selector).text().should.be.equal(messageText);
    });
});

で、残った準備はどうしましょうかと。

とりあえず、Mochaのセットアップと起動部をスクリプトにしてみました。
test/mocha-setup.js

mocha.setup("bdd")

test/mocha-runner.js

mocha.checkLeaks();
mocha.run();

で、テスト用のHTMLはこちら。
test-html/index.html

<!DOCTYPE>
<html>
<head>
<meta charset="utf-8">
<title>テストHTML</title>
</head>
<body>
<!-- Mocha Test Results -->
<div id="mocha"></div>

<!-- for Test Code -->
<span id="target"></span>

<!-- Load Mocha -->
<script type="text/javascript" src="/node_modules/mocha/mocha.js"></script>

<!-- Setup Mocha -->
<script type="text/javascript" src="/test-dist/mocha-setup.js"></script>

<!-- Test Code -->
<script type="text/javascript" src="/test-dist/message-test.js"></script>

<!-- Run Mocha -->
<script type="text/javascript" src="/test-dist/mocha-runner.js"></script>
</body>
</html>

Mochaをnode_moduleから引き込んでいるのですが、

<script type="text/javascript" src="/node_modules/mocha/mocha.js"></script>

requireとかすると

var mocha = require("mocha");

これにハマり込んで、どうにも抜けられなかったのでnode_moduleを直接見ることにしました…。
browserify breaks at require('./lib-cov/mocha') · Issue #880 · mochajs/mocha · GitHub

あとは、Browserifyを含めたgulpの設定。
gulpfile.js

var gulp = require("gulp");
var $ = require("gulp-load-plugins")();
var browserify = require("browserify");
var through2 = require("through2");
var del = require("del");

gulp.task("clean", function() {
    del.sync(["dist/*", "test-dist/*"]);
});

gulp.task("test-build", function() {
    return gulp
        .src(["test/**/*.js"])
        .pipe(through2.obj(function(file, encode, callback) {
            browserify(file.path)
                .on("error", $.util.log)
                .bundle(function(err, res) {
                    if (err) {
                        $.util.log(err.message);
                        $.util.log(err.stack);
                    }
                    file.contents = res;
                    callback(null, file);
                });
        }))
        .pipe($.uglify())
        .pipe($.sourcemaps.init({loadMaps: true}))
        .pipe($.sourcemaps.write('./'))
        .pipe(gulp.dest('./test-dist/'));
});

gulp.task("webserver", function() {
    gulp
        .src("./")
        .pipe($.webserver({
            port: 9000,
            livereload: true
        }));
});

gulp.task("test-browser", ["webserver", "test-build"], function() {
    gulp
        .src("")
        .pipe($.open({ uri: "http://localhost:9000/test-html/index.html" }));
});

Webサーバーはgulpのものを使うのと、テスト実行時にブラウザで対象ページを開くようにしました。Webサーバーのみを起動して、HTMLファイルを直接ブラウザで開いてもかまわないようです。

以下のコマンドで、ブラウザが起動してテストが実行されます。

$ gulp test-browser
[16:53:40] Using gulpfile ~/path/to/gulpfile.js
[16:53:40] Starting 'webserver'...
[16:53:40] Webserver started at http://localhost:9000
[16:53:40] Finished 'webserver' after 199 ms
[16:53:40] Starting 'test-build'...
[16:53:43] Finished 'test-build' after 2.78 s
[16:53:43] Starting 'test-browser'...
[16:53:43] Finished 'test-browser' after 5.71 ms
[16:53:43] Opening http://localhost:9000/test-html/index.html using the default OS app

結果は、このように。idがmochaの部分に、結果が描画されます。

とまあ、なんとか動かせたのですが、ブラウザ関係のテストについてはもうちょっと調べた方がよさそうな気がしてきました…。
頑張りましょう。