Rspecを使用して有効性をテストしたい結果セットを返すプロセスがあります。プロセスはパラメーターに基づいて異なる結果を返しますが、それらすべてに共通する多くの例があるため、それらすべてに対して実行できる一連の共通例を作成したいと思います。
推奨される方法は、letを使用して結果を構築することです。問題は、各プロセスが結果を生成するのに1〜2分かかり、おそらく30の例があることです。さまざまなパラメーターに基づくすべての順列で、約500の例を実行しています。各例の結果を再構築する必要がある場合、テストは1日以上実行されます。
したがって、代わりにbefore(:all)ブロックで結果を作成し、それを次のような属性に割り当てます。
RSpec.describe 'Test Description' do
attr_reader :result
before(:all)
@result = build_result({some_parameters})
end
context 'Some context' do
it 'Looks lik a result' do
expect(result.something).to ...
end
it 'Feels lik a result' do
expect(result.something).to ...
end
end
end
たぶん、属性を使用するよりも良い方法があるでしょう。私はこのようなことをしたいです:
RSpec.describe 'Test Description' do
attr_reader :result
before(:all)
@result = build_result({some_parameters})
end
context 'Some context' do
it_behaves_like "A result" result
end
end
このコンテキストで属性を使用すると失敗します。これを行う別の方法はありますか?
結果に対するすべてのアサーションを1つの例にグループ化できます。このように、letは一度だけ評価されます。
RSpec.describe 'Test Description' do
context 'for params x and y' do
let(:expected_x) { 'x' }
let(:expected_y) { 'y' }
subject { build_result({x: 'x', y: 'y'}) }
specify :aggregate_failures do
expect(subject.x).to eq(expected_x)
expect(subject.y).to eq(expected_y)
end
end
end
「1つのテスト、1つのアサーション」のガイドラインに反しますが、操作に非常にコストがかかる場合は、合理的なアプローチだと思います。 :aggregate_failures
アサーションごとに個別のエラーが発生するため、それを見逃すことはありません。
次のように引数を共有サンプルに渡すことができます:
shared_examples_for "A result" do |argument|
# some tests with argument
end
そして、次のようにmy_argument
を渡します。
it_behaves_like "A result", my_argument
let
を使用できます。
let(:result) { build_result({some_parameters}) }
これにより、後でテストで使用できるインスタンス変数が作成されます。
let
に関するドキュメントに従ってください、
Beforeブロックを使用してインスタンス変数を作成する代わりに変数を割り当てる必要がある場合は、letを使用します。 let変数を使用すると、テストで初めて使用されたときにのみ変数がロードされ、その特定のテストが完了するまでキャッシュされます。
[〜#〜]悪い[〜#〜]
describe '#type_id' do before { @resource = FactoryGirl.create :device } before { @type = Type.find @resource.type_id } it 'sets the type_id field' do expect(@resource.type_id).to equal(@type.id) end end
[〜#〜]良い[〜#〜]
describe '#type_id' do let(:resource) { FactoryGirl.create :device } let(:type) { Type.find resource.type_id } it 'sets the type_id field' do expect(resource.type_id).to equal(type.id) end end
引数をshared_exampleスペックファイルに渡したい場合は、次のようなものを使用する必要があります
it_behaves_like 'SHARED_EXAMPLE_NAME', { params1: param2, param2: param2 }
ハッシュカプセル化せずにパラメーターを渡すこともできます。これは、そのパラメーターを共有ファイルにどのように使用するかによって異なります。私の場合、動的パラメーターでAPIを呼び出す必要があります。
RSpec.shared_examples 'SHARED_EXAMPLE_NAME' do |params = {}|
FYI:Factoryデータをパラメーターとしてshared_exampleスペックファイルに渡すことはできません。ファクトリをshared_exampleスペックファイルに明示的に呼び出す必要があります。