Skip to content

Commit

Permalink
Merge pull request #12 from Ragin-LundF/develop
Browse files Browse the repository at this point in the history
Release 1.15.0
  • Loading branch information
Ragin-LundF authored Sep 18, 2020
2 parents 9271ba1 + c62fd6a commit c0f4537
Show file tree
Hide file tree
Showing 7 changed files with 112 additions and 4 deletions.
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,15 @@
# Release 1.15.0
Adding support in the paths to support templates.
If the path contains something like:
```
/api/v1/${dynamicElement}/
```
In this case, the `dynamicElement` will be replaced, if it exists in the ScenarioContext.

Support for adding static key/value pairs to the context:
- [Set a static value to the context](README.md#set-a-static-value-to-the-context)
- [Set multiple static values to the context](README.md#set-multiple-static-values-to-the-context)

# Release 1.14.0

Adding support for the JSON path to the "I set the value of" sentence.
Expand Down
42 changes: 42 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@ See [Changelog](CHANGELOG.md) for release information.
- [JSON-Unit](#json-unit)
- [Given](#given-1)
- [Set path base directory for request/result/database files](#set-path-base-directory-for-requestresultdatabase-files)
- [Set a static value to the context](#set-a-static-value-to-the-context)
- [Set multiple static values to the context](#set-multiple-static-values-to-the-context)
- [Set base path for URLs](#set-base-path-for-urls)
- [Define that a token without scopes should be used.](#define-that-a-token-without-scopes-should-be-used)
- [Set a URI path for later execution](#set-a-uri-path-for-later-execution)
Expand Down Expand Up @@ -128,6 +130,8 @@ The conversion of the database result to CSV is done internally.
## REST
The REST API steps can be prepared with some given steps.

If a path contains a template placeholder with `${}` like `${elementFromContext}` the library tries to replace this with `elementFromContext` in the context, if it exists.

### JSON-Unit

The library contains already two matchers:
Expand Down Expand Up @@ -160,6 +164,42 @@ It is used for:
- Database query files (`.sql`)
- Database CSV result files (`.csv`)

#### Set a static value to the context
```gherkin
Scenario: Test with static key/value added to the context
Given that the context contains the key "staticKey" with the value "staticValue"
And that the API path is "/api/v1/${staticKey}/myApi"
When executing a GET call with previously given URI
```

or use it in an outline scenario:

```gherkin
Scenario Outline: Test with static key/value added to the context in an outline scenario
Given that the context contains the key "<staticKey>" with the value "<staticValue>"
And that the API path is "/api/v1/${staticURLElement}"
When executing a GET call with previously given URI
Examples:
| staticKey | staticValue |
| staticURLElement | resourceA |
| staticURLElement | resourceB |
| staticURLElement | resourceC |
```

It adds the key/value pairs to the context. Please ensure, that those static values are unique to avoid overwriting them in later steps.

#### Set multiple static values to the context
```gherkin
Scenario: Test with static key/value added to the context via table
Given that the context contains the following 'key' and 'value' pairs
| staticFirstElement | resourceA |
| staticSecondElement | resourceB |
And that the API path is "/api/v1/${staticFirstElement}/${staticSecondElement}"
When executing a GET call with previously given URI
```

It adds the key/value pairs to the context. Please ensure, that those static values are unique to avoid overwriting them in later steps.

#### Set base path for URLs
```gherkin
Scenario:
Expand All @@ -169,6 +209,8 @@ Scenario:
Sets an internal `base URL path` for all URLs in the `Scenario` or `Feature`.
This is very useful to avoid repeating e.g. `/api/v1/myapitotest` before every concrete endpoint.

It is also possible to use placeholders with `${placeholder}` syntax. They will be replaced from the context.

#### Define that a token without scopes should be used.
```gherkin
Scenario:
Expand Down
2 changes: 2 additions & 0 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@ dependencies {

api 'javax.validation:validation-api:2.0.1.Final'

api 'org.apache.commons:commons-text:1.9'

implementation 'org.liquibase:liquibase-core'
implementation 'org.springframework.boot:spring-boot-starter-web'
implementation 'org.springframework.boot:spring-boot-starter-test'
Expand Down
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
group=com.ragin.bdd
version=1.14.0
version=1.15.0

systemProp.sonar.host.url=https://sonarcloud.io/
systemProp.sonar.organization=ragin-lundf-github
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import javax.annotation.PostConstruct;
import javax.validation.constraints.NotNull;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.text.StringSubstitutor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.web.client.TestRestTemplate;
import org.springframework.boot.web.server.LocalServerPort;
Expand Down Expand Up @@ -77,6 +78,7 @@ protected void executeRequest(
} else {
path = ScenarioStateContext.current().getUriPath();
}
path = replacePathPlaceholders(path);

// Prepare headers
HttpHeaders headers = RESTCommunicationUtils.createHTTPHeader(authorized);
Expand All @@ -99,13 +101,27 @@ protected void executeRequest(
);
}

/**
* Replace placeholder like ${myContextItem} with the available items from the context
*
* @param path Path which can contain the placeholder
* @return replaced path
*/
protected String replacePathPlaceholders(final String path) {
// Build StringSubstitutor
StringSubstitutor sub = new StringSubstitutor(ScenarioStateContext.current().getScenarioContextMap());

// Replace
return sub.replace(path);
}

/**
* Full URL for URI path
*
* @param path Path of URI
* @return full URL as protocol:server_host:port/basePath/path
*/
protected String fullURLFor(String path) {
protected String fullURLFor(final String path) {
return SERVER_URL + port + ScenarioStateContext.current().getUrlBasePath() + path;
}
}
36 changes: 36 additions & 0 deletions src/main/java/com/ragin/bdd/cucumber/glue/GivenRESTStateGlue.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,11 @@

import com.ragin.bdd.cucumber.core.BaseCucumberCore;
import com.ragin.bdd.cucumber.core.ScenarioStateContext;
import io.cucumber.datatable.DataTable;
import io.cucumber.java.en.Given;
import java.io.IOException;
import java.util.Map;
import java.util.Set;
import javax.validation.constraints.NotNull;
import org.springframework.beans.factory.annotation.Value;

Expand Down Expand Up @@ -73,4 +76,37 @@ public void givenThatTheFileIsUsedAsTheBody(@NotNull String pathToFile) throws I
public void givenThatTheBodyOfRequestIs(@NotNull final String body) {
ScenarioStateContext.current().setEditableBody(body);
}

/**
* Offers the possibility to set static values to the context
*
* @param key Key in the context map
* @param value Value that should be used
*/
@Given("that the context contains the key {string} with the value {string}")
public void givenThatContextContainsKeyValue(@NotNull final String key, @NotNull final String value) {
ScenarioStateContext.current().getScenarioContextMap().put(key, value);
}

/**
* With this sentence it is possible to add static values to the context map.
*
* <p>
* DataTable looks like:
* <pre>
* | key | value |
* | resourceId | abc-def-gh |
* | subResourceId | zyx-wvu-ts |
* </pre>
*
* @param dataTable DataTable with the key "key" and value "value"
*/
@Given("that the context contains the following 'key' and 'value' pairs")
public void givenThatContextContainsKeyValuePairFromDataTable(final DataTable dataTable) {
final Map<String, String> contextDataTableMap = dataTable.asMap(String.class, String.class);
final Set<String> keySet = contextDataTableMap.keySet();
for (String key : keySet) {
ScenarioStateContext.current().getScenarioContextMap().put(key, contextDataTableMap.get(key));
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ public void whenExecutingAnAuthorizedGETCallToUrl(final String path) {
* @param dataTable DataTable which contains the mapping of dynamic elements and values
*/
@When("executing an authorized GET call with previously given API path and these dynamic 'URI Elements' replaced with the 'URI Values'")
public void whenExecutingAnAuthorizedGETCallToPathWithDynamicURLElement(DataTable dataTable) {
public void whenExecutingAnAuthorizedGETCallToPathWithDynamicURLElement(final DataTable dataTable) {
executeRequest(dataTable, HttpMethod.GET, true);
}

Expand All @@ -99,7 +99,7 @@ public void whenExecutingAnAuthorizedGETCallToPathWithDynamicURLElement(DataTabl
* @param dataTable DataTable which contains the mapping of dynamic elements and values
*/
@When("executing a GET call with previously given API path and the dynamic 'URI Elements' replaced with the 'URI Values'")
public void whenExecutingAGETCallToPathWithDynamicURLElement(DataTable dataTable) {
public void whenExecutingAGETCallToPathWithDynamicURLElement(final DataTable dataTable) {
executeRequest(dataTable, HttpMethod.GET, false);
}
}

0 comments on commit c0f4537

Please sign in to comment.