Railsでテストを書いてみる(Rspec:Controller編)
コントローラもテストしてみる。
- ページにアクセスしてサクセスが返ることと、期待するテンプレートを表示することを確認するシンプルなケース
- 画面にアクセスするのは get :アクション名
- 成功が返るのは response.should be_success
- テンプレートの表示判定は response.should render_template("XXXX")
describe '登録画面にアクセスしたら' do before do get :add_index end it 'サクセスであること' do response.should be_success end it '登録画面を表示すること' do response.should render_template("tunes/add") end end
- フォームからデータを送信したケースのテスト
- post でアクションに対してパラメータを送ったことにする
- データが登録されたことを直接DBを見て判定している。
- リダイレクトの判定と、リダイレクト先を判定している
describe '登録画面で曲を登録したら' do before do post :add_tune,{ :name => "Believe", :album => "Eternal Chain", :tuning => "CGDGBD"} end it '曲データが登録されること' do tune = Tune.find(:all, :conditions=>[ "name=?", 'Believe']) tune.length.should == 1 tune[0].name.should == "Believe" tune[0].album.should == "Eternal Chain" tune[0].progress.should == 0 end it '曲一覧画面を表示すること' do response.should be_redirect response.should redirect_to(:action => 'list') end end
直接DBの値を見ているけれど、DB登録したかどうかの判定は一枚モデルに登録用のラッパーをかませてそれを mock で判定したほうが良いのだろうか。まだよくわからない。
- DBからデータを読み出して表示するページのテスト
- mock を使って DB読み出ししたかを判定している。
- mock の後に get しないとダメっぽい。before でまとめて get できないか。
describe '曲一覧画面を表示した場合' do before do # get :list end it 'サクセスであること' do get :list response.should be_success end it 'DBから全曲を読み出すこと' do Tune.should_receive(:find).with(:all) get :list end end
mock が非常に使いやすい。上の例だと list アクション内で Tune.find(:all)しているかどうかを判定している
- テスト対象のコードはこんな感じになった。意外とスカスカ
class TunesController < ApplicationController def add_index end def add_tune new_tune = Tune.new new_tune.name = params[:name] new_tune.album = params[:album] new_tune.tuning = params[:tuning] new_tune.progress = 0 new_tune.save redirect_to :action => "list" end def list @tunes = Tune.find(:all) end end
add_tune のアクション内で直接DB登録しているけれど、Slim3だったらサービスクラスに当たる登録用のラッパーをかませた方がいいような気がする。
- それと、rake で spec の結果をいい感じの表示にする方法がわからない。 いろいろ調べると rake spec:doc かと思うんだけど、エラーになってしまうんだよなぁ‥。
$ rake spec:doc (in /Users/hoge/rails_work/practice) rake aborted! Don't know how to build task 'spec:doc' (See full trace by running task with --trace) $ rake (in /Users/hoge/rails_work/practice) /System/Library/Frameworks/Ruby.framework/Versions/1.8/usr/bin/ruby -S bundle exec rspec ./spec/controllers/tunes_controller_spec.rb ./spec/helpers/tunes_helper_spec.rb ./spec/models/tune_spec.rb ......... Finished in 0.16196 seconds 9 examples, 0 failures