自社開発プロダクト all-in...
TRANSCRIPT
• 中小企業向けクラウドERPソフト
• 経営を支援する「ビジネス・コックピット」→ 詳しくはこちらの動画にまとめられていますので、是非ご覧ください
• Ruby on Rails
• 2015年7月にファーストリリース
• 鋭意開発中
ALL-IN
• 時間がかかるのは主に外部リソースアクセス(I/O)。
• DB
• File
• Web API
• ALL-IN の場合、外部の Web API をあまり使っていないので、I/O は DB アクセスがメイン。
スピードアップのポイント
• テストケース数が増えてくると、個々のテストのちょっとしたスローダウンが、全体で見ると大きな影響に…
• 0.1 sec * 20000 = 2000 sec = 33 min
スピードアップのポイント
• プロダクションコードで非効率な I/O を発生させないのは当然大切!
• N+1 問題発生してない?
• includes とか eager_load を使う
• 大量のデータをメモリに展開していない?
• find_each、find_in_batches を使う
• kaminari gemとか offset、limit でページングする
スピードアップのポイント
• テストのセットアップも大切!
• 不要なテストデータを DB に入れてない?
• 同じようなデータをテストのたびに毎回DBに入れてない?
→ 適切なタイミングで、必要なデータを投入する!
スピードアップのポイント
• テスト用のモデルインスタンス+DBへのデータ登録が楽にできる
• デフォルト値でよければcreateするだけ
• テストケースに合わせて、柔軟に特定の属性だけ上書きできる
• create_list(:customer, n) で n個まとめてインスタンス生成+DB登録できる
FactoryGirlを使うと
• モデルのインスタンスさえあれば、DBにデータが入っていなくてもいいテストはある
• モデルのバリデーションのテスト
• モデル → JSON のレンダリングのテスト
• DBアクセスを伴わない計算ロジックのテスト
• etc
• これらのテストケースまで create でインスタンスを作るのは無駄
DB登録は本当に必要?
• use_transactional_fixturesでテストケースごとにトランザクションを効かせていても、このデータはテスト完了後もDBに残る
• 何がしかの対策が必要
• テスト起動時にDBをクリーンにするとか
• ユーザーIDを固定して、すでにあったら作らないとか
• やりすぎ注意
• セットアップ時に色々登録すると、デフォルトで何が入ってるのか分からなくなる
デメリットもある
• 本当に1テスト1Assertにすべきか?→ 意味的に同じことをテストしているのであれば、そこまで原理主義的にテストを分割しなくていい→ DBアクセスが発生するテストは、テストメソッド数を減らすことでコストが下がる
テストの最小単位とは?
• 無駄なデータを作らない
• FactoryGirlを上手に使う
• 同じようなデータを登録しない
• テストスィートセットアップ時に登録してしまう
• まとめられるテストケースはまとめる
• 分割しすぎず意味ある単位で1つにまとめる
スピードアップの施策まとめ