[rspec-users] [Cucumber] Level of features / Feature dependent steps

Jonathan Linowes
2009-02-17T21:33:34Z

On Feb 17, 2009, at 3:27 PM, Lenny Marks wrote:

> Forgive the long post, just looking for input/advice/alternate
> opinions..
>
> Like many I think that going through the exercise of framing user
> requests in Cucumber terms(Features, Scenarios..) really helps
> facilitate necessary conversations and avoid time wasted
> implementing the wrong thing(e.g. as a requirement/specification
> tool). However, I''m a bit confused when it comes to tying this in
> with Cucumber.  I''ve come across many suggestions about audience
> being king as far as language used in features, but when writing
> features as part of a specification for a new feature, I
> consistently find myself writing at a higher level than most any
> examples I''ve come across(See example below).
>
> In the past we''ve typically relied on very informal means of
> specifying new features(Wiki pages, paper, and verbal
> communication). No that''s not our problem..;-) TPI, Even with
> extensive object level specs, the full details of what an
> application does and how it is expected to behave from the outside
> tends to get lost in the app over time. For example, we have a few
> applications that were developed by a consulting company. Even
> concentrating only on the UI and the flow of the application, there
> are many features that are kind of hidden within the app(ex. assign
> to drop down that should keep most recently used names first).
> Without being extremely familiar with the app, all you really know
> (as a developer or tester) is that it renders successfully, which
> is an obvious maintenance problem. Even with newer apps, after a
> feature is implemented it tends to get lost inside the application.
>
> I was thinking that Cucumber could really work here as a full life
> cycle tool because the same artifacts that were initially used to
> specify a feature, could be kept and re-used as documentation for
> users and testers. Unlike alternatives such as keeping a Wiki page
> up to date, having features linked to implemented steps serves as
> integration tests and also ensures that the feature as written, is
> still accurate/up to date. (Even link Cucumber output to Wiki page)
>
> Anyway, reading through Cucumber docs and examples, I almost always
> see much more specific examples.
>
> e.g. (from RSpec book)
> Feature: Pay bill on line
>
> Scenario: Pay a bill
> 	Given a checking account with $50
> 	And a payee named Acme
>         And an Acme bill for $37
> 	When I pay the Acme bill
> 	Then I should have $13 remaining in my checking account
>         And the payment of $37 to Acme should be listed in Recent
> Payments
>
> That makes sense to me from a testing perspective, but it just
> doesn''t seem right to me from the perspective I speak of above. If
> I were flushing out this feature with users, I''d have probably
> wound up with something more like:
>
> Scenario: Pay a bill with sufficient funds
> 	Given I have a bill to pay
>  	And I have enough money in my checking account to cover it
> 	When I pay the bill
> 	Then my checking account should be debited by the amount payed
>         And the payment  should be listed in Recent Payments
>
> One problem is that obviously this way involves always writing an
> extra level of feature dependent steps. It just seems to me that
> the specific version tends to distract from the actual story. I''m
> sure I''m looking at this backwards, but does anyone else use
> Cucumber similarly?

Not sure about your ''life cycle'' discussion, but wrt the
examples, I
do that all the time.

You''ve probably seen earlier discussions about instance variables.
Some have advised against it, but I use them. Its manageable if
you''re consistent.

eg  @account  == ''a checking account'', ''my checking
account'', etc
        @bill == ''the bill'', etc
        @bill.amount == ''the amount'', ''the
payment'', etc
etc

And have default setups
but also more specific ones as needed,

Given /^I have a bill to pay$/ do
	@bill = Bill.create( :company => ''Acme'', :amount => 37
)
end

Given /^I have a bill to pay to "(.+)" for \$(\d+)$/ |who, amount|
	@bill = Bill.create( :company => who,  :amount => amount )
end


so you can have
	Given I have a bill to pay
or
	Given I have a bill to pay to "Acme" for $37

I''d probably change your 2nd step to

	And I have enough money in my checking account to cover the bill

so "my checking account" and "the bill" reference @account
and @bill

If you''re managing both checking and savings accounts, i might have
@checking and @savings instead of @account, and make the account type
another argument, and so on

--linoj

>
> Thanks,
> -lenny