Skip to content

Commit a09631c

Browse files
authored
Adding a test to verify the video file is generated (#1115)
1 parent 5d739a8 commit a09631c

File tree

10 files changed

+213
-60
lines changed

10 files changed

+213
-60
lines changed

.github/workflows/test-video.yml

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
name: Test video files
2+
3+
on:
4+
push:
5+
branches:
6+
- trunk
7+
pull_request:
8+
branches:
9+
- trunk
10+
11+
jobs:
12+
build-and-test:
13+
# Skip job based on the commit message, only works in push to branches for now
14+
if: contains(toJson(github.event.commits), '[skip ci]') == false
15+
name: Test video recorded through Docker Selenium
16+
runs-on: ubuntu-18.04
17+
strategy:
18+
matrix:
19+
use-random-user: [false, true]
20+
steps:
21+
- uses: actions/checkout@v1
22+
- name: Output Docker info
23+
run: docker info
24+
- name: Set up Python 3.8
25+
uses: actions/setup-python@v2
26+
with:
27+
python-version: 3.8
28+
- name: Get branch name (only for push to branch)
29+
if: github.event_name == 'push'
30+
run: echo "::set-env name=BRANCH::$(echo ${PUSH_BRANCH##*/})"
31+
env:
32+
PUSH_BRANCH: ${{ github.ref }}
33+
- name: Get target branch name (only for PRs)
34+
if: github.event_name == 'pull_request'
35+
run: echo "::set-env name=BRANCH::$(echo ${TARGET_BRANCH##*/})"
36+
env:
37+
TARGET_BRANCH: ${{ github.head_ref }}
38+
- name: Output branch name
39+
run: echo ${BRANCH}
40+
- name: Sets build date
41+
run: echo ::set-env name=BUILD_DATE::$(date '+%Y%m%d')
42+
- name: Run Docker Compose to record video
43+
run: USE_RANDOM_USER_ID=${USE_RANDOM_USER} VERSION=${BRANCH} BUILD_DATE=${BUILD_DATE} make test_video
44+
env:
45+
USE_RANDOM_USER: ${{ matrix.use-random-user }}
46+
- name: Upload recorded Chrome video
47+
uses: actions/upload-artifact@v2
48+
with:
49+
name: chrome_video
50+
path: ./tests/videos/chrome_video.mp4
51+
- name: Upload recorded Firefox video
52+
uses: actions/upload-artifact@v2
53+
with:
54+
name: firefox_video
55+
path: ./tests/videos/firefox_video.mp4
56+
- name: Upload recorded Opera video
57+
uses: actions/upload-artifact@v2
58+
with:
59+
name: opera_video
60+
path: ./tests/videos/opera_video.mp4

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ StandaloneO*/selenium.conf
1414
StandaloneC*/start-*.sh
1515
StandaloneF*/start-*.sh
1616
StandaloneO*/start-*.sh
17+
videos
1718

1819
# Created by https://www.gitignore.io/api/virtualenv
1920

Makefile

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -300,6 +300,35 @@ test_opera:
300300
test_opera_standalone:
301301
VERSION=$(TAG_VERSION) NAMESPACE=$(NAMESPACE) ./tests/bootstrap.sh StandaloneOpera
302302

303+
# This should run on its own CI job. There is no need to combine it with the other tests.
304+
# Its main purpose is to check that a video file was generated.
305+
test_video: video hub chrome firefox opera
306+
# Running a few tests with docker-compose to generate the videos
307+
for node in NodeChrome NodeFirefox NodeOpera ; do \
308+
cd ./tests || true ; \
309+
echo VIDEO_TAG=$(FFMPEG_TAG_VERSION)-$(BUILD_DATE) > .env ; \
310+
echo TAG=$(TAG_VERSION) >> .env ; \
311+
echo NODE=$$node >> .env ; \
312+
if [ $$node = "NodeChrome" ] ; then \
313+
echo BROWSER=chrome >> .env ; \
314+
echo VIDEO_FILE_NAME=chrome_video.mp4 >> .env ; \
315+
fi ; \
316+
if [ $$node = "NodeFirefox" ] ; then \
317+
echo BROWSER=firefox >> .env ; \
318+
echo VIDEO_FILE_NAME=firefox_video.mp4 >> .env ; \
319+
fi ; \
320+
if [ $$node = "NodeOpera" ] ; then \
321+
echo BROWSER=opera >> .env ; \
322+
echo VIDEO_FILE_NAME=opera_video.mp4 >> .env ; \
323+
fi ; \
324+
docker-compose -f docker-compose-v3-test-video.yml up --abort-on-container-exit --build ; \
325+
done
326+
# Using ffmpeg to verify file integrity
327+
# https://superuser.com/questions/100288/how-can-i-check-the-integrity-of-a-video-file-avi-mpeg-mp4
328+
docker run -v $$(pwd):$$(pwd) -w $$(pwd) jrottenberg/ffmpeg:4.3.1-ubuntu1804 -v error -i ./tests/videos/chrome_video.mp4 -f null - 2>error.log
329+
docker run -v $$(pwd):$$(pwd) -w $$(pwd) jrottenberg/ffmpeg:4.3.1-ubuntu1804 -v error -i ./tests/videos/firefox_video.mp4 -f null - 2>error.log
330+
docker run -v $$(pwd):$$(pwd) -w $$(pwd) jrottenberg/ffmpeg:4.3.1-ubuntu1804 -v error -i ./tests/videos/opera_video.mp4 -f null - 2>error.log
331+
303332
.PHONY: \
304333
all \
305334
base \

tests/.dockerignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
docker-selenium-tests
2+
.env
3+
videos

tests/Dockerfile

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
FROM python:3.8.6-buster
2+
3+
WORKDIR /usr/src/app
4+
5+
COPY . .

tests/SeleniumTests/__init__.py

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,16 @@
11
import unittest
2+
import os
23
from selenium import webdriver
34
from selenium.webdriver.common.by import By
45
from selenium.webdriver.support.ui import WebDriverWait
56
from selenium.webdriver.support import expected_conditions as EC
67
from selenium.webdriver.common.desired_capabilities import DesiredCapabilities
78

9+
SELENIUM_GRID_HOST = os.environ.get('SELENIUM_GRID_HOST', 'localhost')
10+
811

912
class SeleniumGenericTests(unittest.TestCase):
13+
1014
def test_title(self):
1115
self.driver.get('https://the-internet.herokuapp.com')
1216
self.assertTrue(self.driver.title == 'The Internet')
@@ -64,15 +68,15 @@ class ChromeTests(SeleniumGenericTests):
6468
def setUp(self):
6569
self.driver = webdriver.Remote(
6670
desired_capabilities=DesiredCapabilities.CHROME,
67-
command_executor='http://localhost:4444'
71+
command_executor="http://%s:4444" % SELENIUM_GRID_HOST
6872
)
6973

7074

7175
class FirefoxTests(SeleniumGenericTests):
7276
def setUp(self):
7377
self.driver = webdriver.Remote(
7478
desired_capabilities=DesiredCapabilities.FIREFOX,
75-
command_executor='http://localhost:4444'
79+
command_executor="http://%s:4444" % SELENIUM_GRID_HOST
7680
)
7781

7882
def test_title_and_maximize_window(self):
@@ -87,5 +91,5 @@ def setUp(self):
8791
capabilities['browserName'] = 'operablink'
8892
self.driver = webdriver.Remote(
8993
desired_capabilities=capabilities,
90-
command_executor='http://localhost:4444'
94+
command_executor="http://%s:4444" % SELENIUM_GRID_HOST
9195
)

tests/SmokeTests/__init__.py

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import os
12
import unittest
23
import time
34
import json
@@ -7,6 +8,8 @@
78
except ImportError:
89
from urllib.request import urlopen
910

11+
SELENIUM_GRID_HOST = os.environ.get('SELENIUM_GRID_HOST', 'localhost')
12+
1013

1114
class SmokeTests(unittest.TestCase):
1215
def smoke_test_container(self, port):
@@ -19,7 +22,7 @@ def smoke_test_container(self, port):
1922
while current_attempts < max_attempts:
2023
current_attempts = current_attempts + 1
2124
try:
22-
response = urlopen('http://localhost:%s/status' % port)
25+
response = urlopen('http://%s:%s/status' % (SELENIUM_GRID_HOST, port))
2326
status_json = json.loads(response.read())
2427
self.assertTrue(status_json['value']['ready'], "Container is not ready on port %s" % port)
2528
status_fetched = True
@@ -30,12 +33,6 @@ def smoke_test_container(self, port):
3033
self.assertTrue(status_json['value']['ready'], "Container is not ready on port %s" % port)
3134

3235

33-
class NodeTest(SmokeTests):
34-
def test_hub_and_node_up(self):
35-
self.smoke_test_container(4444)
36-
self.smoke_test_container(5555)
37-
38-
39-
class StandaloneTest(SmokeTests):
40-
def test_standalone_up(self):
36+
class GridTest(SmokeTests):
37+
def test_grid_is_up(self):
4138
self.smoke_test_container(4444)

tests/bootstrap.sh

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,20 @@
11
#!/usr/bin/env bash
2-
cd tests
2+
cd tests || true
33

4-
if [ "${TRAVIS:-false}" = "false" ]; then
4+
if [ "${CI:-false}" = "false" ]; then
55
pip install virtualenv | grep -v 'Requirement already satisfied'
66
virtualenv docker-selenium-tests
77
source docker-selenium-tests/bin/activate
88
fi
99

10-
1110
python -m pip install selenium===3.14.1 \
1211
docker===4.2.0 \
1312
| grep -v 'Requirement already satisfied'
1413

15-
python test.py $1 $2
14+
python test.py $1
1615
ret_code=$?
1716

18-
if [ "${TRAVIS:-false}" = "false" ]; then
17+
if [ "${CI:-false}" = "false" ]; then
1918
deactivate
2019
fi
2120

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
# How to run this?
2+
# docker-compose -f docker-compose-v3-test-video.yml up --abort-on-container-exit --build
3+
# To clean up, `docker-compose -f docker-compose-v3-test-video.yml down`
4+
version: "3"
5+
services:
6+
browser:
7+
image: selenium/node-${BROWSER}:${TAG:-test-video}
8+
volumes:
9+
- /dev/shm:/dev/shm
10+
depends_on:
11+
- selenium-hub
12+
environment:
13+
- SE_EVENT_BUS_HOST=selenium-hub
14+
- SE_EVENT_BUS_PUBLISH_PORT=4442
15+
- SE_EVENT_BUS_SUBSCRIBE_PORT=4443
16+
ports:
17+
- "6900:5900"
18+
19+
browser_video:
20+
image: selenium/video:${VIDEO_TAG:-test-video}
21+
volumes:
22+
- ./videos:/videos
23+
depends_on:
24+
- browser
25+
environment:
26+
- DISPLAY_CONTAINER_NAME=browser
27+
- FILE_NAME=${VIDEO_FILE_NAME}
28+
29+
selenium-hub:
30+
image: selenium/hub:${TAG:-test-video}
31+
container_name: selenium-hub
32+
ports:
33+
- "4442:4442"
34+
- "4443:4443"
35+
- "4444:4444"
36+
37+
tests:
38+
image: docker-selenium-tests:latest
39+
build:
40+
context: ./
41+
dockerfile: ./Dockerfile
42+
depends_on:
43+
- selenium-hub
44+
environment:
45+
- RUN_IN_DOCKER_COMPOSE=true
46+
- SELENIUM_GRID_HOST=selenium-hub
47+
command: ["./bootstrap.sh", "${NODE}"]

0 commit comments

Comments
 (0)