[rspec-users] Factoring out code that creates specs

Matt Wynne
Tue, 16 Sep 2008 19:01:29 -0000

On 16 Sep 2008, at 14:28, David Chelimsky wrote:

> Hi Matt,
>
> On Mon, Sep 15, 2008 at 12:28 PM, Matt Wynne <matt at mattwynne.net>
> wrote:
>> It''s all gone a bit meta.
>> I''ve started noticing patterns in my specs, where I want more
than
>> one class
>> to satisfy a specific bunch of behaviours.
>> I know I can use it_should_behave_like and this works in simple
>> cases, but I
>> want to be able to iterate around an array of values and generate
>> a my bunch
>> of it "should ..." specs for each item in the array.
>> I know I can do this by going
>> describe "the cheese factory"
>> [:cheddar, :brie, :lancashire].each do |cheese|
>> it "should create a valid piece of #{cheese}" do
>> Factory.create(cheese).should be_valid
>> end
>> it "should create a piece of #{cheese} with valid packaging"
do
>> ... etc
>> end
>> end
>> ...but what if I want to specify other factories too, all of which
>> conform
>> to the it blocks
>
> it blocks == code examples
>
>> I specified above? (e.g. a ToyFactory that creates valid
>> toys with valid packaging). How can I factor that spec logic out?
>> I tried putting the content of the (do |cheese|) block into a
>> method, but
>> ruby doesn''t seem to be able to see that method when the
describe
>> block
>> runs
>
> How are you doing that? Where are you putting the method? How are you
> calling it?
>
>> I guess I need to maybe patch it into some RSpec class instead? Or
>> put it into a module and include it? Am I going down the wrong
>> lines? is
>> there an easier way to achieve this?
>
> Kind of depends on how you want the specs themselves to look. One
> approach is to wrap class level methods in a module and extend the
> example group with that module. This could, for example, give you
> example groups that look like this:
>
> describe CheeseFactory do
>   extend FactoryExamples
>   it_should_create :cheddar, :brie, :lancashire
> end
>
> describe GameFactory do
>   extend FactoryExamples
>   it_should_create :chess, :clue, :mastermind
> end
>
> Here''s some code (that doesn''t do much but actually
works) to
> demonstrate:
>
> http://pastie.org/273290


Bingo! My misunderstanding of include vs extend was to blame, I think.

Thanks as usual.

cheers,
Matt
----
http://blog.mattwynne.net
http://songkick.com

In case you wondered: The opinions expressed in this email are my own
and do not necessarily reflect the views of any former, current or
future employers of mine.