cucumber-jvm icon indicating copy to clipboard operation
cucumber-jvm copied to clipboard

Add Step information in @BeforeStep and @AfterStep hook #1805

Open BenVercammen opened this issue 5 years ago • 21 comments

Related to https://github.com/cucumber/cucumber-jvm/issues/1805

Added "related step" to HookTestStep, referring to the (PickleStep)TestStep the BeforeStep/AfterStep annotated HookTestStep relates to. This way the actual PickleStepTestStep can be added to the signature of the BeforeStep/AfterStep annotated method.

BenVercammen avatar Oct 06 '20 10:10 BenVercammen

Coverage Status

Coverage increased (+0.03%) to 86.508% when pulling 8363d39c337113e7efc2493ee665387558ee9ad5 on BenVercammen:1805-add-step-information into bb97c6943659018e5e8496aff6a18d73eec06f26 on cucumber:main.

coveralls avatar Oct 06 '20 11:10 coveralls

Haven't updated the version yet, didn't help in the previous pull request either. Otherwise I've implemented the suggested changes.

BenVercammen avatar Oct 07 '20 08:10 BenVercammen

Cheers! I'm going to have to find some time to take a good look at this.

mpkorstanje avatar Oct 07 '20 10:10 mpkorstanje

I've tagged this with hacktoberfest-accepted just in case you were participating and I don't get around to reviewing this before the end of it.

mpkorstanje avatar Oct 08 '20 09:10 mpkorstanje

@mpkorstanje @BenVercammen I'm using the cucumber for our test automation framework. I have a requirement on reusing the step parameters in step with data table input. here is a simple example for this feature requirement:

Given a book "<bookName>"
Check book from db:
| bookName       |  status   |
| ${bookName}  |    1          |

Examples:
|bookName|
|bookA|
|bookB|

Currently, I'm thinking on using this pr for a solution: save step info(parameters) afterStep and format the data table input with already saved step parameters in beforeStep. My question is that what's plan for this pr, when it can be released?

hjh188 avatar Oct 26 '20 08:10 hjh188

when it can be released

When I can find enough time to give it the review it deserves.

mpkorstanje avatar Oct 26 '20 20:10 mpkorstanje

@BenVercammen Can you review it? I am so glad that you worked with it, and cant wait for using it in my code. :) Thank you for help guys :)

@krisztianzagonyi-mintestio if you can't wait, perhaps you could improve on this merge request @BenVercammen and submit those improvements as PR.

mpkorstanje avatar Nov 04 '20 13:11 mpkorstanje

@krisztianzagonyi-mintestio I'll try to clean up the PR as per the comments of @mpkorstanje , but I'll need to wrap my head around the existing architecture so it might take a while...

BenVercammen avatar Nov 05 '20 14:11 BenVercammen

Codecov Report

Merging #2143 (b6266cd) into main (f3fa40d) will decrease coverage by 0.19%. The diff coverage is 66.34%.

Impacted file tree graph

@@             Coverage Diff              @@
##               main    #2143      +/-   ##
============================================
- Coverage     82.79%   82.60%   -0.20%     
- Complexity     2324     2357      +33     
============================================
  Files           306      311       +5     
  Lines          8294     8392      +98     
  Branches        762      776      +14     
============================================
+ Hits           6867     6932      +65     
- Misses         1118     1147      +29     
- Partials        309      313       +4     
Impacted Files Coverage Δ Complexity Δ
...main/java/io/cucumber/core/backend/PickleStep.java 0.00% <0.00%> (ø) 0.00 <0.00> (?)
...rc/main/java/io/cucumber/core/runner/HookStep.java 0.00% <0.00%> (ø) 0.00 <0.00> (?)
.../main/java/io/cucumber/core/runner/PickleStep.java 0.00% <0.00%> (ø) 0.00 <0.00> (?)
...in/java/io/cucumber/core/runner/TestCaseState.java 87.34% <0.00%> (-11.23%) 23.00 <0.00> (ø)
...cucumber/java/InvalidMethodSignatureException.java 86.11% <0.00%> (-13.89%) 2.00 <0.00> (ø)
...main/java/io/cucumber/java/JavaHookDefinition.java 96.00% <ø> (-0.30%) 10.00 <0.00> (ø)
...ain/java/io/cucumber/core/runner/HookTestStep.java 88.88% <66.66%> (-11.12%) 4.00 <1.00> (+1.00) :arrow_down:
...ber/core/gherkin/messages/GherkinMessagesStep.java 77.08% <81.81%> (+12.21%) 17.00 <4.00> (+7.00)
.../java/io/cucumber/java/JavaStepHookDefinition.java 87.75% <87.75%> (ø) 20.00 <20.00> (?)
...rc/main/java/io/cucumber/core/runner/TestCase.java 96.09% <100.00%> (+0.19%) 30.00 <2.00> (+2.00)
... and 9 more

Continue to review full report at Codecov.

Legend - Click here to learn more Δ = absolute <relative> (impact), ø = not affected, ? = missing data Powered by Codecov. Last update f3fa40d...cf97524. Read the comment docs.

codecov[bot] avatar Nov 05 '20 15:11 codecov[bot]

@mpkorstanje I've pushed some new commits that should resolve most of your previous concerns. Can you already have a look at those?

In the meantime, I'll see if I can split up the JavaHookDefinition to account for the differences between Before/After and BeforeStep/AfterStep.

BenVercammen avatar Nov 06 '20 15:11 BenVercammen

@mpkorstanje I think I've taken all your feedback into account, so if you have time to have another look at the code...

BenVercammen avatar Nov 23 '20 17:11 BenVercammen

I'll try and have a look soon!

mpkorstanje avatar Dec 10 '20 22:12 mpkorstanje

The java module and the plugin module evolve at different speeds. Users of the java module should only ever have to import classes from io.cucumber.java. At a glance Location and StepArgument are currently exposed.

At a glance this has not been addressed. Currently users of the java module will still have to use imports from plugin or core. Simply providing step arguments as an Object hides this.

Additionally the additon of PickleStep.Keyword seems rather odd. Could you provide an explanation of how you intend to use the methods of Step?

mpkorstanje avatar Jan 01 '21 16:01 mpkorstanje

Additionally the additon of PickleStep.Keyword seems rather odd. Could you provide an explanation of how you intend to use the methods of Step?

The use case we have in mind is the following:

    @AfterStep
    public void doSomethingAfterEveryGiven(Step step) {
        if (Step.Keyword.GIVEN.equals(step.getKeyword())) {
            ...
        }
    }

I added the PickleStep.Keyword enum (in cucumber-core) in order not to expose the GwtStepType (from cucumber-gherkin). I'm not sure if that's really necessary, but there aren't any io.cucumber.core.gherkin.* imports in cucumber-java (except for a few Test classes).

BenVercammen avatar Jan 04 '21 11:01 BenVercammen

The java module and the plugin module evolve at different speeds. Users of the java module should only ever have to import classes from io.cucumber.java. At a glance Location and StepArgument are currently exposed.

At a glance this has not been addressed. Currently users of the java module will still have to use imports from plugin or core. Simply providing step arguments as an Object hides this.

I don't understand. The java module is heavily depending on core but I don't see any links with the plugin module? I guess I'm missing something, so could you please elaborate a bit?

BenVercammen avatar Jan 04 '21 11:01 BenVercammen

I added the PickleStep.Keyword enum (in cucumber-core) in order not to expose the GwtStepType (from cucumber-gherkin).

I was looking for a use case. Though I think I may have missed your explanation of it in https://github.com/cucumber/cucumber-jvm/issues/1805#issuecomment-703457441

I'm looking for something similar, however I don't need it for logging, but to do something after each @given step. I'll try to come up with a pull request...

Generally speaking we try to discourage scoping steps to keywords. It tends to lead to ambiguous language. This seems to veer into the same direction. Without further explanation I don't think I'd consider this acceptable.

I don't understand. The java module is heavily depending on core but I don't see any links with the plugin module? I guess I'm missing something, so could you please elaborate a bit?

Cucumber is organized such that a user implementing step definitions with Cucumber Java never has to interact with the core directly. This makes change and estimating the impact of it easier. So the api for a user writing step definitions is cucumber-java, not cucumber-core nor cucumber-plugin.

Currently by having io.cucumber.java.step implement io.cucumber.plugin.event.Step the io.cucumber.plugin.event.StepArgument and io.cucumber.plugin.event.Location as well as io.cucumber.plugin.event.Step itself are exposed to the user.

For now I would suggest exposing only the following (duplicating the location class):

public final class Step {

    String getKeyword();

    String getText();

    URI getUri();

    Location getLocation();

}

mpkorstanje avatar Feb 14 '21 16:02 mpkorstanje

Generally speaking we try to discourage scoping steps to keywords. It tends to lead to ambiguous language. This seems to veer into the same direction. Without further explanation I don't think I'd consider this acceptable.

Our specific use case is as follows:

  • we have a revisioning system (envers) in place that increments the revision number of an entity on each change
  • depending on the changes in the revision, we do some extra post processing (eg: sending out events)
  • we have scenario's in which we want to test whether or not the extra processing occurs
  • unfortunately, changes made during execution of our given statements also trigger the revisioning system
    • grouping all relevant properties into a single given statement would render the scenario unreadable
    • therefore we have multiple given steps to set up the entity under test
  • in order for us to be able to check if the post processing was triggered during a given or the when statement, we need to know the last revision number before the actual when statement
  • therefore, we'd like to keep track of the last revision number after each given statement
  • at the moment, we're making use of a "dummy" statement that retrieves and stores the current revision number in our state before the relevant when statement is executed
    • this however makes the scenario less readable
    • and it exposes the fact that we're working with revisions, which business should not be concerned with

So we basically want to do some "implicit state housekeeping" in between steps, and therefore need to distinguish between the actual keywords used for that step.

Another thing to note is that we use Cucumber on an "integration test" level in which we start our full Spring application, while stubbing/mocking external interfaces. We are not able to stub/disable the revisioning system in our tests.

BenVercammen avatar Apr 19 '21 12:04 BenVercammen

Cucumber is organized such that a user implementing step definitions with Cucumber Java never has to interact with the core directly. This makes change and estimating the impact of it easier. So the api for a user writing step definitions is cucumber-java, not cucumber-core nor cucumber-plugin.

Am I correct to say that importing and/or exposing the io.cucumber.plugin.event classes in JavaHookDefinition is to be avoided? So the main issue is in my change in the JavaHookDefinition class?

Currently by having io.cucumber.java.step implement io.cucumber.plugin.event.Step the io.cucumber.plugin.event.StepArgument and io.cucumber.plugin.event.Location as well as io.cucumber.plugin.event.Step itself are exposed to the user.

This part is confusing, as I don't have anything implementing that io.cucumber.plugin.event.Step class. Are you sure you've looked at my latest commit? I did squash all commits, maybe a bit prematurely?

BenVercammen avatar Apr 19 '21 12:04 BenVercammen

Hi,

I have a use case along the lines of: https://github.com/cucumber/cucumber-jvm/issues/1805#issuecomment-778688360 A fair amount of work seems to have been going into this PR. Is the plan to get it merged soon ? Thanks

danic-wd avatar Aug 25 '21 09:08 danic-wd

No, not in the current state.

mpkorstanje avatar Aug 25 '21 18:08 mpkorstanje