Skip to content

Commit 9746c19

Browse files
Refactor, enable and extend acceptance tests (#306)
1 parent f2f0c72 commit 9746c19

File tree

124 files changed

+7206
-42044
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

124 files changed

+7206
-42044
lines changed

.gitignore

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,4 +5,4 @@ helm/**/*.lock
55
*.tgz
66
.vscode
77
.env
8-
html-reports
8+
reports

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "ffc-grants-slurry-web",
3-
"version": "3.13.5",
3+
"version": "3.13.6",
44
"description": "Web frontend for FTF Slurry Infrastructure scheme",
55
"homepage": "https://github.com/DEFRA/ffc-grants-slurry-web",
66
"main": "app/index.js",

test/acceptance/.dockerignore

+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
node_modules
2+
reports
3+
test-output
4+
.dockerignore
5+
docker-compose*
6+
Dockerfile
7+
README.md

test/acceptance/.gitignore

-7
This file was deleted.

test/acceptance/.snyk

-10
This file was deleted.

test/acceptance/Dockerfile

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
1-
ARG PARENT_VERSION=1.2.16-node16.14.2
1+
ARG PARENT_VERSION=2.3.0-node22.4.0
22
ARG PORT_DEBUG=9229
33

4-
# Development
54
FROM defradigital/node-development:${PARENT_VERSION}
65
ARG PARENT_VERSION
76
LABEL uk.gov.defra.ffc.parent-image=defradigital/node-development:${PARENT_VERSION}
@@ -10,4 +9,5 @@ EXPOSE ${PORT_DEBUG}
109
COPY --chown=node:node package*.json ./
1110
RUN npm install
1211
COPY --chown=node:node . .
13-
CMD [ "npm", "run", "test" ]
12+
#CMD [ "npm", "run", "test" ]
13+
CMD [ "ls" ]

test/acceptance/README.md

+62-182
Original file line numberDiff line numberDiff line change
@@ -1,204 +1,84 @@
11
# Acceptance Tests
2+
This folder contains the acceptance test project for the Slurry Infrastructure Grant web app.
23

3-
> Future Farming and Countryside Programme - Grants Frontend Acceptance Tests
4-
5-
This folder contains the acceptance tests for the FFC Grants service components.
6-
7-
The framework is (Cucumber)[https://cucumber.io/] and (webdriver.io)[https://webdriver.io/] based, containerised, expandable and based on the actively maintained webdriver.io Cucumber boilerplate project.
8-
4+
The framework used is WebdriverIO with Cucumber and the tests are containerised by default, running against a single browser (Chrome)
5+
.
96
## Requirements
7+
- Docker
8+
- Node
9+
- npm
1010

11-
- Docker Desktop 2.2.0.3 (42716) or higher
12-
- Node version 12 (not compatible with v13)
13-
- if you have multiple versions of node, run `nvm use 12` to use version 12 for this alone
14-
15-
# Quick start
16-
17-
Docker is used to create a container for each of selenium-hub, chrome-browser and webdriver-cuke.
18-
* Selenium Hub allows concurrent execution of test cases
19-
* Chrome Browser is the browser specified in the configuration file `wdio.conf.js` by default
20-
* Webdriver.io along with Cucumber is this framework that defines the tests.
21-
22-
## How to run the tests
23-
24-
1. Set the root URL for the environment in the environment variable `TEST_ENVIRONMENT_ROOT_URL`
25-
26-
2. If running against localhost, then no need to set `TEST_ENVIRONMENT_ROOT_URL` as it will default to `docker.host.internal:3000`. Instead make sure the application container is running with `docker-compose up --build` in the root folder of this repository
27-
28-
3. From the directory containing the dockerfile run `docker-compose run --rm wdio-cucumber`. This will run an acceptance test against the FFC-Demo web service.
29-
30-
4. The test reports will be output to `./html-reports`. Note that WSL users need to run `mkdir -m 777 html-reports`. Read more about report configuration in the [rpii/wdio-hmtl-reporter docs](https://github.com/rpii/wdio-html-reporter)
31-
32-
5. Now you are ready to maintain, extend or write your own features in the `./acceptance/features` directory
33-
34-
## How to write a test
35-
36-
Tests are written in [Gherkin syntax](https://cucumber.io/docs/reference)
37-
that means that you write down what's supposed to happen in a real language. All test files are located in
38-
`./acceptance/features/*` and have the file ending `.feature`. You will already find some test files in that
39-
directory. They should demonstrate, how tests could look like. Just create a new file and write your first
40-
test.
41-
42-
__myFirstTest.feature__
43-
```gherkin
44-
Feature:
45-
In order to keep my product stable
46-
As a developer or product manager
47-
I want to make sure that everything works as expected
11+
## Running tests inside a container (default)
12+
Docker is used to create containers for both the tests themselves (`wdio-cucumber`) and the Selenium instance of Chrome (`chrome-browser`).
4813

49-
Scenario: Check title of website after search
50-
Given I open the url "http://google.com"
51-
When I set "WebdriverIO" to the inputfield "#lst-ib"
52-
And I press "Enter"
53-
Then I expect that the title is "WebdriverIO - Google Search"
54-
55-
Scenario: Another test
56-
Given ...
14+
1. Provide the following environment variables in a `.env` file in this directory:
5715

5816
```
59-
60-
This test opens the browser and navigates them to google.com to check if the title contains the search
61-
query after doing a search. As you can see, it is pretty simple and understandable for everyone.
62-
63-
# Using tags
64-
65-
If you want to run only specific tests you can mark your features with tags. These tags will be placed before each feature like so:
66-
67-
```gherkin
68-
@Tag
69-
Feature: ...
17+
TEST_ENVIRONMENT_ROOT_URL
18+
19+
LOGIN_USERNAME
20+
LOGIN_PASSWORD
21+
22+
SHAREPOINT_TENANT_ID
23+
SHAREPOINT_CLIENT_ID
24+
SHAREPOINT_CLIENT_SECRET
25+
SHAREPOINT_HOSTNAME
26+
SHAREPOINT_SITE_PATH
27+
SHAREPOINT_DOCUMENT_LIBRARY
28+
SHAREPOINT_UPLOAD_FOLDER
29+
SHAREPOINT_WORKSHEET
7030
```
7131

72-
To run only the tests with specific tag(s) use the `--cucumberOpts.tagExpression=` parameter like so:
32+
2. For ARM architectures, change the image used for Chrome in `docker-compose.yaml`:
7333

74-
```sh
75-
$ npx wdio wdio.conf.js --cucumberOpts.tagExpression='@Tag or @AnotherTag'
7634
```
35+
selenium:
36+
image: selenium/standalone-chrome
7737
78-
For more tag options please see the [Cucumber.js documentation](https://docs.cucumber.io/tag-expressions/)
79-
80-
# Pending test
38+
CHANGES TO..
8139
82-
If you have failing or unimplemented tests you can mark them as "Pending" so they will get skipped.
40+
selenium:
41+
image: seleniarm/standalone-chromium
42+
```
8343

84-
```gherkin
85-
// skip whole feature file
86-
@Pending
87-
Feature: ...
44+
3. If running against `localhost` ensure the application container is running with `docker-compose up --build` from the root folder of this repository.
8845

89-
// only skip a single scenario
90-
@Pending
91-
Scenario: ...
92-
```
46+
4. From the `/test/acceptance` directory run `docker-compose run --build --rm wdio-cucumber`. This will run all acceptance tests.
9347

94-
# Adding new steps and snippets
48+
5. HTML reports will be output to `./reports`.
9549

96-
The predefined snippets allow you to do a lot of common things but you might need extra snippets which
97-
are better aligned with your aims. To do so you will find all step definitions in `./acceptance/steps`. They
98-
are separated in `given`, `when` and `then`.
50+
## Running tests outside a container
51+
To run the tests outside a container:
9952

100-
You define your snippet using regular expressions. This is pretty powerful as it allows you to create complex
101-
sentences with multiple options. Everything that's within `"([^"]*)?"` gets captured and appended to the
102-
callback. The last argument is always a callback function that you need to call when your step is done.
103-
You can access the browser and your WebdriverIO instance with `browser`.
104-
105-
To assert values this boilerplate project comes with a [Chai](http://chaijs.com/) integration.
106-
107-
# Comments
108-
109-
You can add additional descriptive comments in your feature files.
53+
1. Comment out `hostname` and `port` in `wdio.conf.js`, i.e.:
54+
```js
55+
exports.config = {
56+
//hostname: 'selenium',
57+
//port: 4444,```
58+
```
59+
2. Run `npm run test`, this will execute the following script defined in `package.json`:
60+
```pwsh
61+
npx wdio run ./wdio.conf.js
62+
```
11063
111-
```gherkin
112-
###
113-
This is a
114-
block comment
115-
###
116-
Feature: As a bystander
117-
I can watch bottles falling from a wall
118-
So that I can be mildly amused
64+
3. Run a specific test or tests with a tag:
65+
```pwsh
66+
npx wdio run ./wdio.conf.js --cucumberOpts.tags=@tag
67+
```
11968
120-
# This is a single line comment
121-
Scenario: check if username is present
122-
Given I login as "roboter" with password "test123"
123-
Then the username "roboter" should be present in the header
69+
## Running tests in parallel
70+
Tests can be run in parallel at feature file level by increasing the number of instances available to WebdriverIO in `wdio.conf.js', e.g.:
71+
```js
72+
maxInstances: 3,
12473
```
12574
126-
# List of predefined steps
127-
128-
Check out all predefined snippets. You can see examples of how these can be used in [the webdriver.io cucumber-boilerplate `sampleSnippets.feature`](https://github.com/webdriverio/cucumber-boilerplate/blob/master/src/features/sampleSnippets.feature).
129-
130-
## Given steps
131-
132-
- `I open the (url|site) "([^"]*)?"` <br>Open a site in the current browser window/tab
133-
- `the element "([^"]*)?" is( not)* visible` <br>Check the (in)visibility of an element
134-
- `the element "([^"]*)?" is( not)* enabled` <br>Check if an element is (not) enabled
135-
- `the element "([^"]*)?" is( not)* selected` <br>Check if an element is (not) selected
136-
- `the checkbox "([^"]*)?" is( not)* checked` <br>Check if a checkbox is (not) checked
137-
- `there is (an|no) element "([^"]*)?" on the page` <br>Check if an element (does not) exist
138-
- `the title is( not)* "([^"]*)?"` <br>Check the title of the current browser window/tab
139-
- `the element "([^"]*)?" contains( not)* the same text as element "([^"]*)?"` <br>Compare the text of two elements
140-
- `the (button|element) "([^"]*)?"( not)* contains the text "([^"]*)?"` <br>Check if an element contains the given text
141-
- `the (button|element) "([^"]*)?"( not)* contains any text` <br>Check if an element does not contain any text
142-
- `the (button|element) "([^"]*)?" is( not)* empty` <br>Check if an element is empty
143-
- `the page url is( not)* "([^"]*)?"` <br>Check the url of the current browser window/tab
144-
- `the( css)* attribute "([^"]*)?" from element "([^"]*)?" is( not)* "([^"]*)?"` <br>Check the value of an element's (css) attribute
145-
- `the cookie "([^"]*)?" contains( not)* the value "([^"]*)?"` <br>Check the value of a cookie
146-
- `the cookie "([^"]*)?" does( not)* exist` <br>Check the existence of a cookie
147-
- `the element "([^"]*)?" is( not)* ([\d]+)px (broad|tall)` <br>Check the width/height of an element
148-
- `the element "([^"]*)?" is( not)* positioned at ([\d]+)px on the (x|y) axis` <br>Check the position of an element
149-
- `I have a screen that is ([\d]+) by ([\d]+) pixels` <br>Set the browser size to a given size
150-
- `I have closed all but the first (window|tab)` <br>Close all but the first browser window/tab
151-
- `a (alertbox|confirmbox|prompt) is( not)* opened` <br>Check if a modal is opened
152-
153-
## Then steps
154-
155-
- `I expect that the title is( not)* "([^"]*)?"` <br>Check the title of the current browser window/tab
156-
- `I expect that element "([^"]*)?" does( not)* appear exactly "([^"]*)?" times` <br>Checks that the element is on the page a specific number of times
157-
- `I expect that element "([^"]*)?" is( not)* visible` <br>Check if a certain element is visible
158-
- `I expect that element "([^"]*)?" becomes( not)* visible` <br>Check if a certain element becomes visible
159-
- `I expect that element "([^"]*)?" is( not)* within the viewport` <br>Check if a certain element is within the current viewport
160-
- `I expect that element "([^"]*)?" does( not)* exist` <br>Check if a certain element exists
161-
- `I expect that element "([^"]*)?"( not)* contains the same text as element "([^"]*)?"` <br>Compare the text of two elements
162-
- `I expect that (button|element) "([^"]*)?"( not)* contains the text "([^"]*)?"` <br>Check if an element or input field contains the given text
163-
- `I expect that (button|element) "([^"]*)?"( not)* contains any text` <br>Check if an element or input field contains any text
164-
- `I expect that (button|elementelement) "([^"]*)?" is( not)* empty` <br>Check if an element or input field is empty
165-
- `I expect that the url ( not)* contains "([^"]*)?"` <br>Check if the the URL of the current browser window/tab contains a certain string
166-
- `I expect that the url is( not)* "([^"]*)?"` <br>Check if the the URL of the current browser window/tab is a certain string
167-
- `I expect that the path is( not)* "([^"]*)?"` <br>Check if the path of the URL of the current browser window/tab is a certain string
168-
- `I expect the url to( not)* contain "([^"]*)?"` <br>Check if the URL of the current browser window/tab contains a certain string
169-
- `I expect that the( css)* attribute "([^"]*)?" from element "([^"]*)?" is( not)* "([^"]*)?"` <br>Check the value of an element's (css) attribute
170-
- `I expect that checkbox "([^"]*)?" is( not)* checked` <br>Check if a check-box is (not) checked
171-
- `I expect that element "([^"]*)?" is( not)* selected` <br>Check if an element is (not) selected
172-
- `I expect that element "([^"]*)?" is( not)* enabled` <br>Check if an element is (not) enabled
173-
- `I expect that cookie "([^"]*)?"( not)* contains "([^"]*)?"` <br>Check if a cookie with a certain name contains a certain value
174-
- `I expect that cookie "([^"]*)?"( not)* exists` <br>Check if a cookie with a certain name exist
175-
- `I expect that element "([^"]*)?" is( not)* ([\d]+)px (broad|tall)` <br>Check the width/height of an element
176-
- `I expect that element "([^"]*)?" is( not)* positioned at ([\d]+)px on the (x|y) axis` <br>Check the position of an element
177-
- `I expect that element "([^"]*)?" (has|does not have) the class "([^"]*)?"` <br>Check if an element has a certain class
178-
- `I expect a new (window|tab) has( not)* been opened` <br>Check if a new window/tab has been opened
179-
- `I expect the url "([^"]*)?" is opened in a new (tab|window)` <br>Check if a URL is opened in a new browser window/tab
180-
- `I expect that element "([^"]*)?" is( not)* focused` <br>Check if an element has the focus
181-
- `I wait on element "([^"]*)?"( for (\d+)ms)*( to( not)* (be checked|be enabled|be selected|be visible|contain a text|contain a value|exist))*` <br>Wait for an element to be checked, enabled, selected, visible, contain a certain value or text or to exist
182-
- `I expect that a (alertbox|confirmbox|prompt) is( not)* opened` <br>Check if a modal is opened
183-
- `I expect that a (alertbox|confirmbox|prompt)( not)* contains the text "$text"` <br>Check the text of a modal
184-
185-
## When steps
186-
187-
- `I (click|doubleclick) on the (link|button|element) "([^"]*)?"` <br>(Double)click a link, button or element
188-
- `I (add|set) "([^"]*)?" to the inputfield "([^"]*)?"` <br>Add or set the content of an input field
189-
- `I clear the inputfield "([^"]*)?"` <br>Clear an input field
190-
- `I drag element "([^"]*)?" to element "([^"]*)?"` <br>Drag an element to another element
191-
- `I submit the form "([^"]*)?"` <br>Submit a form
192-
- `I pause for (\d+)ms` <br>Pause for a certain number of milliseconds
193-
- `I set a cookie "([^"]*)?" with the content "([^"]*)?"` <br>Set the content of a cookie with the given name to the given string
194-
- `I delete the cookie "([^"]*)?"` <br>Delete the cookie with the given name
195-
- `I press "([^"]*)?"` <br>Press a given key. You’ll find all supported characters [here](https://w3c.github.io/webdriver/webdriver-spec.html#keyboard-actions). To do that, the value has to correspond to a key from the table.
196-
- `I (accept|dismiss) the (alertbox|confirmbox|prompt)` <br>Accept or dismiss a modal window
197-
- `I enter "([^"]*)?" into the prompt` <br>Enter a given text into a modal prompt
198-
- `I scroll to element "([^"]*)?"` <br>Scroll to a given element
199-
- `I close the last opened (window|tab)` <br>Close the last opened browser window/tab
200-
- `I focus the last opened (window|tab)` <br>Focus the last opened browser window/tab
201-
- `I log in to site with username "([^"]*)?" and password "([^"]*)?"` <br>Login to a site with the given username and password
202-
- `I select the (\d+)(st|nd|rd|th) option for element "([^"]*)?"` <br>Select an option based on it's index
203-
- `I select the option with the (name|value|text) "([^"]*)?" for element "([^"]*)?"` <br>Select an option based on its name, value or visible text
204-
- `I move to element "([^"]*)?"( with an offset of (\d+),(\d+))` <br>Move the mouse by an (optional) offset of the specified element
75+
## Running tests against multiple browsers
76+
Tests can be run against multiple browsers, currently only when running outside a container, by specifying additional capabilities together with more instances in `wdio.conf.js`:
77+
```js
78+
maxInstances: 10,
79+
capabilities: [
80+
{ acceptInsecureCerts: true, browserName: 'chrome' },
81+
{ acceptInsecureCerts: true, browserName: 'firefox' },
82+
{ acceptInsecureCerts: true, browserName: 'edge' }
83+
],
84+
```

test/acceptance/babel.config.js

-12
This file was deleted.

test/acceptance/docker-compose.debug.yaml

-4
This file was deleted.

test/acceptance/docker-compose.override.yaml

-27
This file was deleted.

0 commit comments

Comments
 (0)