Reputation: 915
I am automating a system using BDD with Serenity + Cucumber-jvm, and I have some cases, that the same step can be used as any keyword step definition. Example:
Given something
When do something
Then other thing
And do something
As you can see, do something
is used with both when
and then
, but If I define the same method with these 2 annotations:
@When("do something")
@Then("do something")
public void doSomething() {
}
I get the following error:
cucumber.runtime.DuplicateStepDefinitionException: Duplicate step definitions in ...
How do I resolve this issue
Upvotes: 1
Views: 3227
Reputation: 17602
"Given" describes the context in which the scenario takes place. It either describes a state, or it describes something that has happened. So phrase it in either the continuous present, or the past tense.
Given the invoice is two weeks late <-- continuous present
Given the invoice was submitted <-- past
You'll also notice that it doesn't say anything about who submitted the invoice. That's fine for the context, because it doesn't matter how it got there. We call this the "passive" as opposed to the "active" voice.
"When" describes an event that happens. I like to put this in the present tense, active voice. "The dog bit the boy" is active voice. "The boy was bitten" is passive since it doesn't mention who did it. By mentioning who does it, we remind people that there's a user involved, even if that user is another system.
When I check my accounts
When the admin creates a new record
When the ETL begins
"Then" describes what ought to happen, in that context, for that event. I like to use the word "should", which is a conditional tense. It's also in the passive voice because the "when" should cover how it happened.
Then the invoice should be marked as paid
Then I should receive an email <-- "I" am not the doer so this is still passive voice
The word "should" has an additional benefit. Back in the days of Waterfall development, we used to try to get all the requirements right, but we never quite managed it.
By using the word "should", we encapsulate the idea that uncertainty still exists. It encourages people to question whether the requirements are accurate, and in the face of changing technology and innovation, whether they're still accurate. It's easier to change an idea when it isn't using "must" or "will", as those are words which express certainty, and if you're convinced that someone else is certain about something, you're less likely to push back.
By pushing back and making other suggestions we get "exploration by example", and it's the precursor to specification or test by example, which are nice by-products. Ideally you'll be talking through more scenarios than you actually keep, and deciding which ones are in and out of scope. The word "should" really helps with that, and keeping it when you capture those scenarios and write them down helps too.
And, of course, it helps to differentiate "Given" and "Then" (but hopefully not "When" since that will be phrased in the active voice anyway).
So, if I were to use your "do something" example, I might say:
Given something was done
When someone does something
Then something else should have happened.
Now none of your scenario steps are similar, and you've clarified what you really mean by them, too.
I wrote a blog post on this a while back if it helps as a reference.
Upvotes: 3
Reputation: 3576
For Cucumber The keyword in front a step definition (Given,When,Then,And..) does not make any difference it is for lexical clarity and beauty. That said when you do
@When("do something")
@Then("do something")
is equivalent to:
@When("do something")
@When("do something")
or
@Then("do something")
@Then("do something")
So not to get duplicate step definitions you need just to look at the text not the keyword :)
Upvotes: 0