fix: each browser-suite run builds and removes an image of its own (closes #547)
check / check (push) Successful in 5m23s
e2e / e2e-chrome (push) Successful in 4m50s
e2e / e2e-firefox (push) Successful in 2m26s

script/test-e2e and script/test-e2e-firefox tagged their image with one
fixed name. When two clones ran a suite at once, the second build moved
that tag, the image store deleted the first run's now-untagged image, and
that suite exited 125 without running a test. Each run now tags its image
with the suite's name and twelve random hex digits, runs it by that tag,
and removes it in the scripts' existing exit and interrupt cleanup, so no
run leaves an image behind. The image-ID file that guarded against a
moving tag is no longer needed. README.md's End-to-End Tests section says
so.

Model: opus-5-5
This commit is contained in:
2026-10-14 07:35:45 +00:00
parent fd5921f62e
commit 5daa6e1db4
3 changed files with 27 additions and 30 deletions
+13 -15
View File
@@ -22,13 +22,18 @@ set -eu
SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd -P)"
ROOT="$(cd "$SCRIPT_DIR/.." && pwd -P)"
IMAGE="$("$SCRIPT_DIR/projectname")-e2e-chrome"
IIDFILE=""
# Each run builds, runs and then removes an image under a tag of its own.
# Under one tag shared by every run, a second clone's build moves the tag
# off this run's image, and the image store can then delete that untagged
# image before or while this run uses it. The tag is random rather than
# $$ because CI jobs share one docker daemon, but each job's container
# numbers its processes from scratch.
IMAGE="$("$SCRIPT_DIR/projectname")-e2e-chrome:$(od -An -N6 -tx1 /dev/urandom | tr -d ' \n')"
cleanup() {
if [ -n "$IIDFILE" ]; then
rm -f "$IIDFILE"
# No image to remove when the build failed or was interrupted.
if docker image inspect "$IMAGE" >/dev/null 2>&1; then
docker image rm "$IMAGE" >/dev/null
fi
}
@@ -40,22 +45,15 @@ main() {
exit 1
fi
IIDFILE="$(mktemp)"
trap cleanup EXIT
trap 'cleanup; exit 130' INT TERM
echo "Building the Chrome e2e image (extension included)..."
# --no-cache: the image build runs make build and its checks, and a
# cached layer is a check that did not run.
docker build --no-cache --iidfile "$IIDFILE" -t "$IMAGE" \
-f tests/e2e/Dockerfile .
docker build --no-cache -t "$IMAGE" -f tests/e2e/Dockerfile .
echo "Running e2e suite in the pinned Playwright container..."
# The image is run by ID, not by tag: where two clones of this repo run
# the suite at once, the other build can move the tag between this
# build and this run, and the suite would then silently test the other
# checkout.
#
# --ipc=host: Chromium's shared-memory needs more than the default
# 64MB /dev/shm or renderers crash.
# HOME=/tmp: the image's root home is not a reliable place for the
@@ -79,7 +77,7 @@ main() {
-e HOME=/tmp \
-e PW_EXPERIMENTAL_SERVICE_WORKER_NETWORK_EVENTS=1 \
-e "E2E_TRACE_NETWORK=${E2E_TRACE_NETWORK:-0}" \
"$(cat "$IIDFILE")" \
"$IMAGE" \
node tests/e2e/run.js
# Where chrome.storage.local lives, and what moves it: two unpacked loads
@@ -95,7 +93,7 @@ main() {
docker run --rm \
--ipc=host \
-e HOME=/tmp \
"$(cat "$IIDFILE")" \
"$IMAGE" \
node tests/e2e/storagePartition.js
}