2
6

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

RSpecでitのdescriptionをスマートに出力させる

Posted at

背景

Rspecの実行の際に、loggerを仕込んでlogを出力させています。
共通処理before、afterの処理にもloggerが仕込まれているため、
ひと目でどのテスト(it)を実行しているのかわかりませんでした。
そのため、itの中身を実行前に表示させることにしました。

記事を読んでできるようになること

it "is not the example object" do
  expect("hogehoge").to eq("fugafuga")
end

上記のテスト実行時に下記の出力結果を出せる

test.log
{"message":": is not the example object","timestamp":"2017-04-06T07:41:02+09:00","severity":"INFO","pid":57870,"program":null}

環境

  • rspec 3.5.4
  • ruby 2.2.2p95 (2015-04-13 revision 50295) [x86_64-darwin14]

設定

単純な出力

itのdescriptionを出力させたいだけなので一番簡単な方法は

it "is not the example object" do
  logger.info("is not the example object")
  expect("hogehoge").to eq("fugafuga")
end

itの中身に直接書いてあげることです。
最初は何も考えず上記を採用していました。:sweat_smile:

ただ、ぱっと見たときに "is not the example object"の文字列が重複しており、dryじゃありません:poop:

meta情報を利用

rpsecを調べるとmetadataをもっており、それを利用しました。

use_metadata
describe "example as block arg to it, before, and after" do
  it "is not the example object" do |example|
    p "テスト名だよ"
    p example.description # logger.info(example.description)
    expect("hogehoge").to eq("hogehoge")
  end
end
実行結果
$ bundle exec rspec spec/server/my_test_spec.rb

example as block arg to it, before, and after
"テスト名だよ"
"is not the example object" # printによる出力結果
  is not the example object

Finished in 0.00425 seconds (files took 0.29218 seconds to load)
1 example, 0 failures

これで取り敢えずdryを解消できました:tada:
しかし、テストが一つだったら問題ないのですが、テストが増えてくると
logger.info(example.description) 自体が重複コードになります:sob:

beforeの利用

じゃあ、before(:each)に突っ込んでやればいいと考えました。

use_before
describe "example as block arg to it, before, and after" do
  before(:each) do |example|
    p "テスト名だよ"
    p example.description # logger.info(example.description)
  end

  it "is not the example object" do
    expect("hogehoge").to eq("hogehoge")
  end

  it "is the example object" do
    expect("fugafuga").to eq("fugafuga")
  end
end
実行結果
$ bundle exec rspec spec/server/my_test_spec.rb

example as block arg to it, before, and after
"is not the example object"
"テスト名だよ"
  is not the example object
"is the example object"
"テスト名だよ"
  is the example object

Finished in 0.00397 seconds (files took 0.21586 seconds to load)
2 examples, 0 failures

カンの良いあなたならもうおわかりですが、これだとspec file毎に

  before(:each) do |example|
    p "テスト名だよ"
    p example.description # logger.info(example.description)
  end

を記述する必要があります。

spec_helperの利用

http://www.rubydoc.info/github/rspec/rspec-core/RSpec/Core/Example#metadata-instance_method
上記のurlに自分のやりたいことの答えがありました。:pencil:

rspec_helperに上記を記述しspec側でrequireしてあげるだけです

spec_helper

RSpec.configure do |config|
  config.before do |example| # 追加
    logger.info(example.description) # 追加
  end # 追加
use_spec_helper
require "spec_helper"

describe "example as block arg to it, before, and after" do
  it "is not the example object" do
    p "テスト名だよ"
    expect("hogehoge").to eq("hogehoge")
  end

  it "is the example object" do
    p "テスト名だよ"
    expect("fugafuga").to eq("fugafuga")
  end
end
log
{"message":"is not the example object","timestamp":"2017-04-06T09:03:28+09:00","severity":"INFO","pid":68487,"program":null}
{"message":"is the example object","timestamp":"2017-04-06T09:03:28+09:00","severity":"INFO","pid":68487,"program":null}

rspecって奥が深いですね。:thinking_

2
6
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
2
6

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?