mrubyのCIをdocker+rake+travis-ciでやる

はじめに

こんばんは、GMOペパボの久米です。 今回は「mruby-mtestでngx_mrubyやmod_mrubyで使うmrubyのテストコードを書く」でご紹介しましたmrubyのテストをより便利にしていきたいと思います。 やり方を忘れないように備忘録的に記述します。

概要

本エントリでは以下のことを目的としている。

  • 開発を行うにあたり、動作確認をより簡単に行えるようにする。
  • 継続的インテグレーションを行いたい。

今回利用するコンポーネントは以下のような役割を担う。

  • docker
    • mrubyの実行環境を即座に提供する
  • rake
    • 実行環境であるdockerのビルドやテストの実行などのタスクを定義して簡単に呼び出せるようにする
  • travis-ci
    • github.comにpushした時に自動でrakeを実行してdockerのビルドやテストの実行を行う

本エントリで何ができるようになるか。

  • ソースコードをgithubにpushすることで、自動的にテストが実行されcommitに対してテスト結果を得ることができる。
  • ローカルマシン上での開発時に簡単に動作確認を行える。

Let’s develop!!

今回のテストは以下の様な動作を想定している。

  • githubにコードをpush
    • travis-ciが通知を受け取る
  • travis-ciが “rake” コマンドを実行
    • dockerのbuildが実行される。
    • dockerのbuild完了後にdockerの起動がされる。
  • Dockerfile内でRakefileおよびテスト対象コードをコンテナ内にマウントする。
  • Dockerfile内で “rake test” を実行する。
    • “rake test” を実行すると、mruby-testを含んだmrubyのバイナリを使用してテストコードを実行する。
    • テスト結果を得る。
まずはリポジトリを作成する

github.comに「mruby-mtestでngx_mrubyやmod_mrubyで使うmrubyのテストコードを書く」こちらで書いたコードを、githubのリポジトリに上げます。 本エントリではリポジトリ名を ci-test とします。

[text] ci-test/ └ src/ └ mruby.rb [/text]

mrubyのbuild_config.rbを作成する

[text] ci-test/ └ src/ | └ mruby.rb └ misc/ └ build_config.rb ★ [/text]

build_config.rb

[ruby] MRuby::Build.new do |conf|

toolchain :gcc

conf.gembox ‘full-core’

conf.gem :github => ‘iij/mruby-io’ conf.gem :github => ‘iij/mruby-env’ conf.gem :github => ‘iij/mruby-dir’ conf.gem :github => ‘iij/mruby-digest’ conf.gem :github => ‘iij/mruby-process’ conf.gem :github => ‘iij/mruby-pack’ conf.gem :github => ‘iij/mruby-socket’ conf.gem :github => ‘matsumoto-r/mruby-sleep’ conf.gem :github => ‘matsumoto-r/mruby-userdata’ conf.gem :github => ‘matsumoto-r/mruby-uname’ conf.gem :github => ‘matsumoto-r/mruby-mutex’ conf.gem :github => ‘matsumoto-r/mruby-cache’

conf.gem :github => ‘iij/mruby-mtest’ end [/ruby]

  • このファイルはdockerでmrubyをビルドする際にコンテナ内に放り込む
ビルド環境であるDockerfileを作成する

[text] ci-test/ └ src/ | └ mruby.rb └ misc/ | └ build_config.rb └ Dockerfile ★ [/text]

Dockerfile

[ruby] FROM centos:latest

RUN yum install -y
gcc
git
rubygems
openssl-devel
curl
bison

RUN curl http://curl.haxx.se/ca/cacert.pem -o /opt/cacert.pem ENV SSL_CERT_FILE=/opt/cacert.pem

RUN gem install bundler RUN gem install mgem RUN gem install rake

RUN git clone https://github.com/mruby/mruby.git

ローカルのbuild_config.rbをmrubyのソース内に入れる

ADD misc/build_config.rb mruby/

ビルドする

RUN cd mruby && rake

パスが通っているところに生成されたmrubyのバイナリをコピーする

RUN cp mruby/bin/mruby /usr/local/bin [/ruby]

dockerの動作確認

[shell] docker build -t takumakume:ci-test . docker run -it takumakume:ci-test /bin/bash [/shell]

docker内で以下を実行

[shell] [[email protected] tmp]# mruby –version mruby 1.2.0 (2015-11-17) [/shell]

  • 正常にdocker内でmrubyが実行できればOK

問題がなければ、Dockerfileに以下を追記

[ruby] ADD . /tmp WORKDIR /tmp CMD rake test [/ruby]

  • ローカルのファイルをコンテナ内の “/tmp” にマウント
  • “rake test” コマンドを実行
    • “rake build” -> “rake run” の順に実行され、dockerが起動した最後の処理にテストを実行するようにする。
    • こうすることで、travis-ciから “rake” を実行するだけで、dockerのbuildとテストの実行ができる。
Rakefileの作成

[text] ci-test/ └ src/ | └ mruby.rb └ misc/ | └ build_config.rb ├ Dockerfile └ Rakefile ★ [/text]

Rakefile

[ruby] task default: :run

desc “build” task :build do sh “docker build -t takumakume:ci-test .” end

desc “run” task :run => [:build] do sh “docker run -t takumakume:ci-test” end

desc “test” task :test do sh “mruby /tmp/src/mruby.rb” end [/ruby]

  • “rake” コマンドを引数無しで実行した場合にテストが実行されるようにする。
  • “rake run” でDockerを立ち上げる。(その前に rake build が実行されてコンテナが作成される)
  • “rake test” を実行すると対象コードをmrubyバイナリで実行してテストする。
rake動作確認

[shell] rake [/shell]

shell Successfully built b83c3f8f877b docker run -t takumakume:ci-test mruby /tmp/src/mruby.rb

Running tests:

..

Finished tests in 0.000285s, 7017.5439 tests/s, 7017.5439 assertions/s. [/shell]

  • テスト成功!
後はgithubにpushした時にtravis-ciがテストを実行してくれるように設定

[text] ci-test/ └ src/ | └ mruby.rb └ misc/ | └ build_config.rb ├ Dockerfile ├ Rakefile ├ Gemfile ★ └ .travis.yml ★ [/text]

Gemfile

[ruby] gem “rake” [/ruby]

.travis.yml

[ruby] language: ruby sudo: required services: - docker before_install: - bundle install script: - bundle exec rake [/ruby]

travis-ciに “ci-test” リポジトリを登録する。

GUIでごにょる

githubにpushしてCIが走ることを確認!!

[shell] git add * git add .travis.yml git push origin master [/shell]

ローカルマシンで開発するときは

Rakefile に以下のような記述を追加しておけば、 “rake dev” と実行するだけでソースファイルをマウントした実行環境にアクセスできる。

[ruby] desc “dev” task :dev do sh “docker run -v pwd:/tmp -it takumakume:ci-test /bin/bash” end [/ruby]

ソースファイルを変更するたびにコンテナ内で

[ruby] rake test [/ruby]

[ruby] mruby /tmp/src/hoge.rb [/ruby]

を実行することで素早く動作確認を行うことができる!

このやり方さえ覚えれば色々なものにCI適応できる!