| = Cucumber JVM |
| :index-group: Testing Techniques |
| :jbake-type: page |
| :jbake-status: published |
| |
| |
| == About Cucumber |
| Cucumber is a tool that enables support for link:https://en.wikipedia.org/wiki/Behavior-driven_development[Behaviour-Driven Development (BDD)] by the execution of *scenarios* written in plain text and validates that the software does what those scenarios say. The format used to describe the scenarios is the link:https://docs.cucumber.io/gherkin/reference/[gherkin syntax]. |
| |
| Cucumber was originally written in the Ruby programming language, but now supports a variety of different programming languages through various implementations, including Java. |
| |
| |
| == About Cucumber JVM |
| |
| Is the pure Java implementation of Cucumber that can integrates with all the popular Dependency Injection containers. |
| |
| == Dependencies |
| For this examples we are adding two dependencies in the `pom.xml` dependencies section. `cucumber-openejb` for integration with Open EJB and `cucumber-junit` to use JUnit to execute cucumber scenario(s). |
| |
| [source,xml] |
| ---- |
| <dependency> |
| <groupId>io.cucumber</groupId> |
| <artifactId>cucumber-openejb</artifactId> |
| <version>4.2.3</version> |
| <scope>test</scope> |
| <exclusions> |
| <exclusion> |
| <groupId>org.apache.openejb</groupId> |
| <artifactId>openejb-core</artifactId> |
| </exclusion> |
| </exclusions> |
| </dependency> |
| <dependency> |
| <groupId>io.cucumber</groupId> |
| <artifactId>cucumber-junit</artifactId> |
| <version>4.2.3</version> |
| <scope>test</scope> |
| </dependency> |
| ---- |
| |
| |
| |
| |
| == Test entry point |
| |
| The class `org.superbiz.cucumber.CucumberTest` is the entry point we can identify when the test phase from maven gets executed. The `@RunWith(Cucumber.class)` is the annotation that enable the cucumber integration and from there it scans the available feature files (`hello.feature`) and their corresponding programmatic mapping (HelloStepDef.java) |
| |
| [source,java,numbered] |
| ---- |
| package org.superbiz.cucumber; |
| |
| import cucumber.api.junit.Cucumber; |
| import org.junit.runner.RunWith; |
| |
| @RunWith(Cucumber.class) |
| public class CucumberTest { |
| // the suite, will load automatically the features |
| } |
| ---- |
| |
| |
| == Feature file |
| The `hello.feature` file contains the `gherkin` syntax that indicates the sequence of steps that cucumber will execute. Check the link:https://docs.cucumber.io/gherkin/reference/[cucumber gherkin reference documentation] to understand the available keywords, rules and conditionals. |
| |
| |
| [source,bash] |
| ---- |
| Feature: Hello |
| |
| Scenario: Say Hello |
| Given A name 'foo' |
| Then The bean says 'hello foo' |
| ---- |
| |
| == Step Definitions |
| |
| This are the programmatic set of instruction that will match the Feature file scenarios and their corresponding actions. The class `HelloStepDef.java` has the annotations `Given` and `Then` from the `cucumber.api.java.en` package. For this examples we are using English but the tool can support different languages. |
| |
| A step definition’s expression can either be a Regular Expression or a Cucumber Expression. In this example we are using Regular Expression but you can check the link:https://docs.cucumber.io/cucumber/step-definitions/[Step Definition reference] documentation for more information. |
| |
| [source,java,numbered] |
| ---- |
| package org.superbiz.cucumber; |
| |
| import cucumber.api.java.en.Given; |
| import cucumber.api.java.en.Then; |
| |
| import javax.inject.Inject; |
| |
| import static org.junit.Assert.assertEquals; |
| |
| public class HelloStepDef { |
| |
| @Inject |
| private Hello hello; |
| |
| private String name; |
| |
| @Given("^A name '([a-z]*)'$") |
| public void initName(final String name) { |
| this.name = name; |
| } |
| |
| @Then("^The bean says '([ a-z]*)'$ ") |
| public void checkResult(final String result) { |
| assertEquals(result, hello.hello(name)); |
| } |
| } |
| ---- |
| |
| In the above code you can see how JUnit came into play on the line `assertEquals(result, hello.hello(name));` when the result obtained from the execution of the method hello from the Hello bean is compared with the value `result` from the feature file `hello.feature` |
| |
| |
| == Running |
| In order to run this example, make sure you have cloned the `https://github.com/apache/tomee` repository to your local computer and navigate to `tomee/examples/cucumber-jvm` folder |
| |
| Then you just need to execute: |
| |
| [source,bash] |
| ---- |
| mvn clean test |
| ---- |
| |
| |
| === Output |
| [source,bash] |
| ---- |
| ------------------------------------------------------- |
| T E S T S |
| ------------------------------------------------------- |
| Running org.superbiz.cucumber.CucumberTest |
| INFO - ******************************************************************************** |
| INFO - OpenEJB http://tomee.apache.org/ |
| INFO - Startup: Tue Feb 26 14:01:02 CST 2019 |
| INFO - Copyright 1999-2018 (C) Apache OpenEJB Project, All Rights Reserved. |
| INFO - Version: 8.0.0-SNAPSHOT |
| INFO - Build date: 20190226 |
| INFO - Build time: 11:17 |
| INFO - ******************************************************************************** |
| INFO - openejb.home = /Users/norm/git/tomee/examples/cucumber-jvm |
| INFO - openejb.base = /Users/norm/git/tomee/examples/cucumber-jvm |
| INFO - Created new singletonService org.apache.openejb.cdi.ThreadSingletonServiceImpl@769f71a9 |
| INFO - Succeeded in installing singleton service |
| INFO - Using 'javax.ejb.embeddable.EJBContainer=true' |
| INFO - Cannot find the configuration file [conf/openejb.xml]. Will attempt to create one for the beans deployed. |
| INFO - Configuring Service(id=Default Security Service, type=SecurityService, provider-id=Default Security Service) |
| INFO - Configuring Service(id=Default Transaction Manager, type=TransactionManager, provider-id=Default Transaction Manager) |
| INFO - Creating TransactionManager(id=Default Transaction Manager) |
| INFO - Creating SecurityService(id=Default Security Service) |
| INFO - Found EjbModule in classpath: /Users/norm/git/tomee/examples/cucumber-jvm/target/classes |
| INFO - Beginning load: /Users/norm/git/tomee/examples/cucumber-jvm/target/classes |
| INFO - Configuring enterprise application: /Users/norm/git/tomee/examples/cucumber-jvm |
| INFO - Configuring Service(id=Default Managed Container, type=Container, provider-id=Default Managed Container) |
| INFO - Auto-creating a container for bean cucumber-jvm.Comp351520508: Container(type=MANAGED, id=Default Managed Container) |
| INFO - Creating Container(id=Default Managed Container) |
| INFO - Using directory /var/folders/xg/3840xb4543j_n48v_y19_kv00000gn/T for stateful session passivation |
| INFO - Enterprise application "/Users/norm/git/tomee/examples/cucumber-jvm" loaded. |
| INFO - Assembling app: /Users/norm/git/tomee/examples/cucumber-jvm |
| INFO - Existing thread singleton service in SystemInstance(): org.apache.openejb.cdi.ThreadSingletonServiceImpl@769f71a9 |
| INFO - Some Principal APIs could not be loaded: org.eclipse.microprofile.jwt.JsonWebToken out of org.eclipse.microprofile.jwt.JsonWebToken not found |
| INFO - OpenWebBeans Container is starting... |
| INFO - Adding OpenWebBeansPlugin : [CdiPlugin] |
| INFO - All injection points were validated successfully. |
| INFO - OpenWebBeans Container has started, it took 331 ms. |
| INFO - Deployed Application(path=/Users/norm/git/tomee/examples/cucumber-jvm) |
| ..INFO - Undeploying app: /Users/norm/git/tomee/examples/cucumber-jvm |
| INFO - Destroying OpenEJB container |
| |
| 1 Scenarios (1 passed) |
| 2 Steps (2 passed) |
| 0m2.117s |
| |
| |
| Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 2.339 sec |
| |
| Results : |
| |
| Tests run: 1, Failures: 0, Errors: 0, Skipped: 0 |
| |
| [INFO] ------------------------------------------------------------------------ |
| [INFO] BUILD SUCCESS |
| [INFO] ------------------------------------------------------------------------ |
| [INFO] Total time: 5.462 s |
| [INFO] Finished at: 2019-02-26T14:01:04-06:00 |
| [INFO] Final Memory: 29M/619M |
| [INFO] ------------------------------------------------------------------------ |
| |
| ---- |