LoginSignup
153
170

More than 5 years have passed since last update.

Rspecの文法の基礎

Posted at
spec/order_spec.rb
describe Order do
  before do
    order.add_entry(LineItem.new(:item => Item.new(
      :price => Money.new(1.11, :USD)
    )))
  end

  let(order) { Order.new }

  it "sums the prices of its line items" do
    order.add_entry(LineItem.new(:item => Item.new(
      :price => Money.new(2.22, :USD),
      :quantity => 2
    )))
    expect(order.total).to eq(Money.new(5.55, :USD))
  end
end

Rspecrspec-core, rspec-expectations, rspec-mocksの3つにわかれており、それぞれRspecの基本文型、多様な比較演算、モックオブジェクトを定義している。このドキュメントは、文法に焦点を当てるため、rspec-coreの中の基礎的な部分と、Rails用にrspec-rails, capybaraが拡張する文法について触れる。
テストの中身の書き方については、http://qiita.com/awakia/items/d880250adc8cdbe7a32f を参照

基本文型

https://github.com/rspec/rspec-core
https://www.relishapp.com/rspec/rspec-core/v/3-0/docs/example-groups/basic-structure-describe-it

spec/models/class_spec.rb
describe <クラス名> do
  it "<期待する動作の内容>"
    # ...
  end

  context "<条件の内容>" do
    it "<contextの条件下で期待する動作の内容>" do
      # ...
    end
  end
end

ここで、

  • contextは、describeに置き換え可能
  • itは、specifyまたはexampleに置き換え可能

なので、文脈に合わせて使いやすい用語を使えば良い。

なお、デフォルトの設定では、名前として<クラス名>_spec.rbというようにサフィックスとして_spec.rbがないとrspecコマンドで全体を走らせた時に無視されるようになるので気をつけること。

何をしているか

なお、topレベルのdescribeはExampleGroupを生成するが、役割はそれだけではない。

Railsを使っている場合

rspec-railsというのを使う。

これは、expect ... toの後に使える

  • be_a_new
  • render_template
  • redirect_to
  • route_to
  • be_routable

などのRails用のMatcherを提供する他、

  • Model
  • Controller
  • View
  • Request
  • Feature
  • Mailer
  • Routing
  • Helper

など、それぞれのタイプの特徴に合わせたスペックの書き方を提供する。

例えばモデルタイプのテストだとspec/modelsの下におくか
describe ... type: :modelとしてテストを書く。

それぞれのタイプにより何がロードされるかや、使えるメソッドなどが異なり、ここに書ききれないので、それぞれのテストを書く際にドキュメントを参照すると良い。

ドキュメントは以下だが、概要はgithubの方がわかりやすいので詳しく知りたくなった時のみこちらを参照すると良い。
https://www.relishapp.com/rspec/rspec-rails/v/3-0/docs/directory-structure

Capybaraを使っている場合

rspec-railsのfeatureテストはほぼcapybaraの使用を前提としている。

Capybaraはユーザーがブラウズする課程をテストでそのまま書くようなFeatureテストを作成するときに便利なgem
https://github.com/jnicklas/capybara#using-capybara-with-rspec

これを使っている場合、

  • describe ... type: :featureの代わりにfeature
  • beforeの代わりに、background
  • itの代わりに、scenario
  • letの代わりにgiven

が使えるようになり、より自然な英語で以下のように書けるようになる。

spec/features/signing_in_spec.rb
feature "Signing in" do
  background do
    User.make(:email => 'user@example.com', :password => 'caplin')
  end

  given(:other_user) { User.make(:email => 'other@example.com', :password => 'rous') }

  scenario "Signing in as another user" do
    visit '/sessions/new'
    within("#session") do
      fill_in 'Login', :with => other_user.email
      fill_in 'Password', :with => other_user.password
    end
    click_link 'Sign in'
    expect(page).to have_content 'Invalid email or password'
  end
end
153
170
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
153
170