Skip to content

Instantly share code, notes, and snippets.

@soramugi
Last active August 29, 2015 14:22
Show Gist options
  • Save soramugi/0258747ff84d15b45ac7 to your computer and use it in GitHub Desktop.
Save soramugi/0258747ff84d15b45ac7 to your computer and use it in GitHub Desktop.

Railsのテストの書き方


テストとは

説明

  • あるURLにアクセスした際に、予期した画面が表示されるか
  • ある正しい操作をした際に、アプリケーションの状態が正しく変更されるか
  • ある正しくない操作をした際に、適切なエラーメッセージが表示されるか

上記の確認作業をブラウザで確認するのではなく、プログラムで確認出来るようにするのが目的 (変更箇所によって別の機能が動かなくなることや、確認漏れをなくす効果が期待できる)


テストとは

テストには大きく分けて3種類ある

  • 単体テスト
  • 機能テスト
  • 総合テスト

テストとは

単体テスト

  • モデルの検索系メソッドが正しい値を取得できるか
  • モデルの更新系メソッドが正しくデータベースを更新できるか
  • モデルの更新系メソッドが不正な入力に対して、適切なエラーを発生させるか

テストとは

機能テスト

  • 適切なテンプレートが選択されているか
  • インスタンス変数に適切な値が格納されているか
  • 適切にレンダリングされているか
  • 更新系のアクションが正しくデータベースを更新されるか

テストとは

総合テスト

  • ログインして、新しいメンバーを追加して、ログアウトするといった一連の動きをテスト

参照 : http://railsdoc.com/test


Railsのテスト

railsでテストを行う時のテストフレームワークには様々な種類がある

  • rspec
  • minitest
  • test-unit
  • capybara
  • cucumber

今回はminitestを使ったテストの方法を解説する (個人的好み & railsデフォルトのため選定)


Railsのテスト

rails new & rails g scaffold item & rake でテストの実行が出来ます

$ rails new rails-minitest
$ cd rails-minitest
$ rails g scaffold item
$ rake db:migrate
$ rake
Run options: --seed 61987

# Running:

.......

Finished in 1.786684s, 3.9179 runs/s, 7.2760 assertions/s.

7 runs, 13 assertions, 0 failures, 0 errors, 0 skips

Railsのテスト

作成されたテストコード

$ tree test/
test/
├── controllers
│   └── items_controller_test.rb
├── fixtures
│   └── items.yml
├── helpers
├── integration
├── mailers
├── models
│   └── item_test.rb
└── test_helper.rb

6 directories, 4 files

controllers下のファイルにテストコードが書かれている

fixturesはテストデータ

modelsにはテストは書かれていない、単体テストを行う時に記述する


Railsのテスト

items_controller_test.rbのテストコード抜粋(本当はもうちょっと長いが最低限の部分のみ)

require 'test_helper'

class ItemsControllerTest < ActionController::TestCase

  test "should get index" do
    get :index
    assert_response :success
    assert_not_nil assigns(:items)
  end

  test "should create item" do
    assert_difference('Item.count') do
      post :create, item: {  }
    end

    assert_redirected_to item_path(assigns(:item))
  end

Railsのテスト

indexアクションのテストコード

  test "should get index" do
    # indexアクションにgetアクセス
    get :index
    # レスポンスコード200が返るか確認
    assert_response :success
    # インスタンス変数 @items はnilではないのを確認
    assert_not_nil assigns(:items)
  end

Railsのテスト

createアクションのテストコード

  test "should create item" do
    # Item.countを実行してブロック終了時に +1 しているか確認
    assert_difference('Item.count') do
      # createアクションにpostアクセス、パラメータ付き
      post :create, item: {  }
    end

    # リダイレクトされてるか確認
    assert_redirected_to item_path(assigns(:item))
  end

Railsのテスト

ついでにmodels下の単体テストの書き方

require 'test_helper'

class ItemTest < ActiveSupport::TestCase
  # test "the truth" do
  # assertでtrueかどうかの確認
  #   assert true
  # end
end

Railsのテスト

こんな風に書く

  test "saveできるか" do
    item = Item.new(name: 'waiwai')
    # saveしてtrueが返るか、save出来るか
    assert item.save
  end

まとめ

  • minitestのassert記法は簡単にテストを始められる
  • 基本的にはtrueかどうかを確認するのがテスト
  • trueかどうかを確認できる粒度にコードを細分化するのがテストしやすいいいコード
  • 便利なassertの書き方は色々あるけど、trueかどうかを確認出来るようにするのが先、便利なのを探すのは後
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment