Series Navigation
← Part 16: CI/CD Integration — Jenkins
→ Part 18: Selenium 4 — New Features, Relative Locators and CDP
Why Headless Mode?
CI/CD servers have no display. A browser that requires a GUI cannot open. Headless mode runs Chrome/Firefox without rendering a visible window — same browser engine, same behaviour, no display required.
Headed Chrome: Opens visible window → Cannot run on headless Linux CI server
Headless Chrome: No window → Runs anywhere, slightly faster
Headless Chrome
ChromeOptions options = new ChromeOptions();
options.addArguments("--headless");
options.addArguments("--disable-gpu"); // required on Windows
options.addArguments("--window-size=1920,1080"); // important: set explicit size
options.addArguments("--no-sandbox"); // required on Linux
options.addArguments("--disable-dev-shm-usage"); // prevents crashes in Docker
options.addArguments("--disable-extensions");
options.addArguments("--proxy-server='direct://'"); // bypass proxy for local
WebDriverManager.chromedriver().setup();
WebDriver driver = new ChromeDriver(options);
Headless Firefox
FirefoxOptions options = new FirefoxOptions();
options.setHeadless(true);
options.addArguments("--width=1920");
options.addArguments("--height=1080");
WebDriverManager.firefoxdriver().setup();
WebDriver driver = new FirefoxDriver(options);
Virtual Display on Linux (Alternative to Headless)
Some older tests break in headless mode (file uploads, certain JavaScript). Use Xvfb (virtual framebuffer):
# Install Xvfb
sudo apt-get install xvfb
# Start virtual display
Xvfb :99 -screen 0 1920x1080x24 &
export DISPLAY=:99
# Run tests normally (non-headless) on the virtual display
mvn test -Dheadless=false
Dockerfile for Selenium Tests
# Dockerfile
FROM maven:3.8-openjdk-11-slim
# Install Chrome
RUN apt-get update && apt-get install -y \
wget curl gnupg2 unzip \
&& wget -q -O - https://dl-ssl.google.com/linux/linux_signing_key.pub | apt-key add - \
&& echo "deb http://dl.google.com/linux/chrome/deb/ stable main" > /etc/apt/sources.list.d/google-chrome.list \
&& apt-get update \
&& apt-get install -y google-chrome-stable \
&& rm -rf /var/lib/apt/lists/*
WORKDIR /app
# Copy pom.xml and download dependencies (cached layer)
COPY pom.xml .
RUN mvn dependency:resolve -q
# Copy source code
COPY src/ src/
# Default command: run all tests headless
CMD ["mvn", "test", "-Dheadless=true", "-Dbrowser=chrome"]
Build and run:
# Build image
docker build -t selenium-tests:latest .
# Run tests
docker run --rm \
-e BASE_URL=https://staging.example.com \
-e BROWSER=chrome \
-v $(pwd)/test-output:/app/test-output \
selenium-tests:latest
# Override with specific suite
docker run --rm \
selenium-tests:latest \
mvn test -DsuiteXmlFile=src/test/resources/smoke-testng.xml -Dheadless=true
Docker Compose — Full Stack Testing
# docker-compose.test.yml
version: "3.8"
services:
# Your application under test
app:
image: your-app:latest
ports:
- "8080:8080"
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:8080/health"]
interval: 10s
timeout: 5s
retries: 5
# Selenium Grid Hub
selenium-hub:
image: selenium/hub:4.1.0
ports:
- "4444:4444"
chrome-node:
image: selenium/node-chrome:4.1.0
depends_on: [selenium-hub]
environment:
SE_EVENT_BUS_HOST: selenium-hub
SE_EVENT_BUS_PUBLISH_PORT: 4442
SE_EVENT_BUS_SUBSCRIBE_PORT: 4443
SE_NODE_MAX_SESSIONS: 4
volumes:
- /dev/shm:/dev/shm
# Test runner
selenium-tests:
build: .
depends_on:
app:
condition: service_healthy
selenium-hub:
condition: service_started
environment:
BASE_URL: http://app:8080
GRID_URL: http://selenium-hub:4444
BROWSER: chrome
volumes:
- ./test-output:/app/test-output
command: >
mvn test
-Dbase.url=http://app:8080
-DgridUrl=http://selenium-hub:4444
-Dbrowser=chrome
-DsuiteXmlFile=src/test/resources/testng.xml
# Run the full stack
docker-compose -f docker-compose.test.yml up --abort-on-container-exit
# Check exit code (0=pass, non-zero=failure)
echo "Exit: $?"
# Get reports from container
docker cp selenium-tests:/app/test-output ./test-output
What's Next
In Part 18 — the final post in the series — we explore Selenium 4's new features: relative locators, native Windows API, CDP (Chrome DevTools Protocol) integration, and the upgraded WebDriver API.
Discussion
Loading...Leave a Comment
All comments are reviewed before appearing. No links please.