From 85a401fd6dab779669b6c0ee583c70166b82c8c1 Mon Sep 17 00:00:00 2001 From: TheFox0x7 Date: Sun, 19 Apr 2026 21:44:16 +0200 Subject: [PATCH 1/5] run playwright via container --- Makefile | 3 ++- tools/test-e2e.sh | 34 +++++++++++++++++++++++++++++++++- 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/Makefile b/Makefile index 0e4d68bffe..136b0ef973 100644 --- a/Makefile +++ b/Makefile @@ -22,6 +22,7 @@ XGO_PACKAGE ?= src.techknowlogick.com/xgo@latest GOVULNCHECK_PACKAGE ?= golang.org/x/vuln/cmd/govulncheck@v1 ACTIONLINT_PACKAGE ?= github.com/rhysd/actionlint/cmd/actionlint@v1.7.11 +CONTAINER_RUNTIME ?= docker DOCKER_IMAGE ?= gitea/gitea DOCKER_TAG ?= latest DOCKER_REF := $(DOCKER_IMAGE):$(DOCKER_TAG) @@ -521,7 +522,7 @@ playwright: deps-frontend @pnpm exec playwright install --with-deps chromium firefox webkit $(PLAYWRIGHT_FLAGS) .PHONY: test-e2e -test-e2e: playwright $(EXECUTABLE_E2E) +test-e2e: $(EXECUTABLE_E2E) @EXECUTABLE=$(EXECUTABLE_E2E) ./tools/test-e2e.sh $(GITEA_TEST_E2E_FLAGS) .PHONY: bench-sqlite diff --git a/tools/test-e2e.sh b/tools/test-e2e.sh index 39405387b5..b4f7d8e1c8 100755 --- a/tools/test-e2e.sh +++ b/tools/test-e2e.sh @@ -1,6 +1,30 @@ #!/bin/bash set -euo pipefail +wait_for_container() { + local max_attempts=$1 + local attempt=1 + local wait_time=1 + sleep 5 # give the container some time to start listening. + + while [ $attempt -le $max_attempts ]; do + if $CONTAINER_RUNTIME logs gitea-e2e-runner 2>&1 | grep -q "Listening on"; then + echo "Container is ready." + return 0 # Success + fi + + if [ $attempt -eq $max_attempts ]; then + echo "Error: Container did not become ready after $max_attempts attempts." + return 1 # Failure + fi + + echo "Attempt $attempt: Container not ready, waiting $wait_time second(s)..." + sleep $wait_time + ((attempt++)) + ((wait_time*=2)) # Exponential backoff + done +} + # Create isolated work directory WORK_DIR=$(mktemp -d) @@ -8,6 +32,7 @@ WORK_DIR=$(mktemp -d) FREE_PORT=$(node -e "const s=require('net').createServer();s.listen(0,'127.0.0.1',()=>{process.stdout.write(String(s.address().port));s.close()})") cleanup() { + $CONTAINER_RUNTIME stop gitea-e2e-runner if [ -n "${SERVER_PID:-}" ]; then kill "$SERVER_PID" 2>/dev/null || true wait "$SERVER_PID" 2>/dev/null || true @@ -15,6 +40,13 @@ cleanup() { rm -rf "$WORK_DIR" } trap cleanup EXIT +# Start playwright worker +$CONTAINER_RUNTIME run --network=host --name gitea-e2e-runner -d --rm --init -it --workdir /home/pwuser --user pwuser mcr.microsoft.com/playwright:v1.59.1-noble /bin/sh -c "npx -y playwright@1.59.1 run-server --port 4000 --host 0.0.0.0" + +if ! wait_for_container 5; then + exit 1 +fi + # Write config file for isolated instance mkdir -p "$WORK_DIR/custom/conf" @@ -112,4 +144,4 @@ export GITEA_TEST_E2E_PASSWORD export GITEA_TEST_E2E_EMAIL export GITEA_TEST_E2E_TIMEOUT_FACTOR -pnpm exec playwright test "$@" +PW_TEST_CONNECT_WS_ENDPOINT=ws://127.0.0.1:4000/ pnpm exec playwright test "$@" From 61dd8820490a96ed69b9c8bc82b6612fcfff6c80 Mon Sep 17 00:00:00 2001 From: TheFox0x7 Date: Sun, 19 Apr 2026 21:58:47 +0200 Subject: [PATCH 2/5] fix makefile not passing envvar --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 136b0ef973..4bd93acb89 100644 --- a/Makefile +++ b/Makefile @@ -523,7 +523,7 @@ playwright: deps-frontend .PHONY: test-e2e test-e2e: $(EXECUTABLE_E2E) - @EXECUTABLE=$(EXECUTABLE_E2E) ./tools/test-e2e.sh $(GITEA_TEST_E2E_FLAGS) + @CONTAINER_RUNTIME=$(CONTAINER_RUNTIME) EXECUTABLE=$(EXECUTABLE_E2E) ./tools/test-e2e.sh $(GITEA_TEST_E2E_FLAGS) .PHONY: bench-sqlite bench-sqlite: integrations.sqlite.test generate-ini-sqlite From 6a6f986aff45faebe538917e99bea6ddb7078df5 Mon Sep 17 00:00:00 2001 From: TheFox0x7 Date: Mon, 20 Apr 2026 22:01:30 +0200 Subject: [PATCH 3/5] gate the container exec --- tools/test-e2e.sh | 20 ++++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) diff --git a/tools/test-e2e.sh b/tools/test-e2e.sh index b4f7d8e1c8..ba42f725d6 100755 --- a/tools/test-e2e.sh +++ b/tools/test-e2e.sh @@ -32,7 +32,9 @@ WORK_DIR=$(mktemp -d) FREE_PORT=$(node -e "const s=require('net').createServer();s.listen(0,'127.0.0.1',()=>{process.stdout.write(String(s.address().port));s.close()})") cleanup() { - $CONTAINER_RUNTIME stop gitea-e2e-runner + if [ -z "$PLAYWRIGHT_CONTAINER" ]; then + $CONTAINER_RUNTIME stop gitea-e2e-runner + fi if [ -n "${SERVER_PID:-}" ]; then kill "$SERVER_PID" 2>/dev/null || true wait "$SERVER_PID" 2>/dev/null || true @@ -40,11 +42,14 @@ cleanup() { rm -rf "$WORK_DIR" } trap cleanup EXIT -# Start playwright worker -$CONTAINER_RUNTIME run --network=host --name gitea-e2e-runner -d --rm --init -it --workdir /home/pwuser --user pwuser mcr.microsoft.com/playwright:v1.59.1-noble /bin/sh -c "npx -y playwright@1.59.1 run-server --port 4000 --host 0.0.0.0" -if ! wait_for_container 5; then - exit 1 +if [ -z "$PLAYWRIGHT_CONTAINER" ]; then + # Start playwright worker + $CONTAINER_RUNTIME run --network=host --name gitea-e2e-runner -d --rm --init -it --workdir /home/pwuser --user pwuser mcr.microsoft.com/playwright:v1.59.1-noble /bin/sh -c "npx -y playwright@1.59.1 run-server --port 4000 --host 0.0.0.0" + + if ! wait_for_container 5; then + exit 1 + fi fi @@ -144,4 +149,7 @@ export GITEA_TEST_E2E_PASSWORD export GITEA_TEST_E2E_EMAIL export GITEA_TEST_E2E_TIMEOUT_FACTOR -PW_TEST_CONNECT_WS_ENDPOINT=ws://127.0.0.1:4000/ pnpm exec playwright test "$@" +if [ -z "$PLAYWRIGHT_CONTAINER" ]; then + export PW_TEST_CONNECT_WS_ENDPOINT=ws://127.0.0.1:4000/ +fi +pnpm exec playwright test "$@" From e420d48e95c106fda80722e0758e88b4c9c0c885 Mon Sep 17 00:00:00 2001 From: TheFox0x7 Date: Tue, 21 Apr 2026 22:33:31 +0200 Subject: [PATCH 4/5] move the detection to the script Assisted-by: gemini-cli:gemini-3-flash --- Makefile | 9 ++++--- tools/test-e2e.sh | 60 ++++++++++++++++++++++++++++++++++++++++++----- 2 files changed, 58 insertions(+), 11 deletions(-) diff --git a/Makefile b/Makefile index 13a2d064fe..e5e6cbab54 100644 --- a/Makefile +++ b/Makefile @@ -519,12 +519,11 @@ test-mssql-migration: migrations.mssql.test migrations.individual.mssql.test .PHONY: playwright playwright: deps-frontend - @# on GitHub Actions VMs, playwright's system deps are pre-installed - @pnpm exec playwright install $(if $(GITHUB_ACTIONS),,--with-deps) chromium firefox $(PLAYWRIGHT_FLAGS) + @./tools/test-e2e.sh install .PHONY: test-e2e -test-e2e: $(EXECUTABLE_E2E) - @CONTAINER_RUNTIME=$(CONTAINER_RUNTIME) EXECUTABLE=$(EXECUTABLE_E2E) ./tools/test-e2e.sh $(GITEA_TEST_E2E_FLAGS) +test-e2e: playwright $(EXECUTABLE_E2E) + @CONTAINER_RUNTIME=$(CONTAINER_RUNTIME) EXECUTABLE=$(EXECUTABLE_E2E) ./tools/test-e2e.sh run $(GITEA_TEST_E2E_FLAGS) .PHONY: bench-sqlite bench-sqlite: integrations.sqlite.test generate-ini-sqlite @@ -820,7 +819,7 @@ generate-manpage: ## generate manpage .PHONY: docker docker: - docker build --disable-content-trust=false -t $(DOCKER_REF) . + $(CONTAINER_RUNTIME) build --disable-content-trust=false -t $(DOCKER_REF) . # support also build args docker build --build-arg GITEA_VERSION=v1.2.3 --build-arg TAGS="bindata sqlite sqlite_unlock_notify" . # Disable parallel execution because it would break some targets that don't diff --git a/tools/test-e2e.sh b/tools/test-e2e.sh index ba42f725d6..bce3973a9d 100755 --- a/tools/test-e2e.sh +++ b/tools/test-e2e.sh @@ -1,14 +1,39 @@ #!/bin/bash set -euo pipefail +# Extract Playwright version from package.json +PLAYWRIGHT_VERSION=$(node -e "process.stdout.write(require('./package.json').devDependencies['@playwright/test'])") + +detect_playwright_mode() { + # If PLAYWRIGHT_MODE is already set to local or container, use it + if [ "${PLAYWRIGHT_MODE:-auto}" = "local" ] || [ "${PLAYWRIGHT_MODE:-auto}" = "container" ]; then + return + fi + + # Default to local + PLAYWRIGHT_MODE="local" + + if [ "$(uname -s)" = "Linux" ]; then + if [ -f /etc/os-release ]; then + # Check ID and ID_LIKE for ubuntu or debian + if ! grep -qE '^ID(_LIKE)?=.*(ubuntu|debian)' /etc/os-release; then + PLAYWRIGHT_MODE="container" + fi + else + PLAYWRIGHT_MODE="container" + fi + fi +} + wait_for_container() { local max_attempts=$1 local attempt=1 local wait_time=1 + echo "Waiting for container to start..." sleep 5 # give the container some time to start listening. while [ $attempt -le $max_attempts ]; do - if $CONTAINER_RUNTIME logs gitea-e2e-runner 2>&1 | grep -q "Listening on"; then + if ${CONTAINER_RUNTIME:-docker} logs gitea-e2e-runner 2>&1 | grep -q "Listening on"; then echo "Container is ready." return 0 # Success fi @@ -25,6 +50,26 @@ wait_for_container() { done } +CMD="${1:-run}" +if [ "$CMD" = "install" ] || [ "$CMD" = "run" ]; then + shift +else + CMD="run" +fi + +detect_playwright_mode + +if [ "$CMD" = "install" ]; then + if [ "$PLAYWRIGHT_MODE" = "local" ]; then + # on Github Actions VMs, playwright's system deps are preinstalled + pnpm exec playwright install "$(if [ -z "${GITHUB_ACTIONS:-}" ]; then echo "--with-deps"; fi)" chromium firefox ${PLAYWRIGHT_FLAGS:-} + else + echo "Running playwright in container as host distro is not supported by playwright directly" + ${CONTAINER_RUNTIME:-docker} pull "mcr.microsoft.com/playwright:v${PLAYWRIGHT_VERSION}-noble" + fi + exit 0 +fi + # Create isolated work directory WORK_DIR=$(mktemp -d) @@ -32,8 +77,8 @@ WORK_DIR=$(mktemp -d) FREE_PORT=$(node -e "const s=require('net').createServer();s.listen(0,'127.0.0.1',()=>{process.stdout.write(String(s.address().port));s.close()})") cleanup() { - if [ -z "$PLAYWRIGHT_CONTAINER" ]; then - $CONTAINER_RUNTIME stop gitea-e2e-runner + if [ "${PLAYWRIGHT_MODE:-}" = "container" ]; then + ${CONTAINER_RUNTIME:-docker} stop gitea-e2e-runner fi if [ -n "${SERVER_PID:-}" ]; then kill "$SERVER_PID" 2>/dev/null || true @@ -43,9 +88,9 @@ cleanup() { } trap cleanup EXIT -if [ -z "$PLAYWRIGHT_CONTAINER" ]; then +if [ "${PLAYWRIGHT_MODE:-}" = "container" ]; then # Start playwright worker - $CONTAINER_RUNTIME run --network=host --name gitea-e2e-runner -d --rm --init -it --workdir /home/pwuser --user pwuser mcr.microsoft.com/playwright:v1.59.1-noble /bin/sh -c "npx -y playwright@1.59.1 run-server --port 4000 --host 0.0.0.0" + ${CONTAINER_RUNTIME:-docker} run --network=host --name gitea-e2e-runner -d --rm --init -it --workdir /home/pwuser --user pwuser "mcr.microsoft.com/playwright:v${PLAYWRIGHT_VERSION}-noble" /bin/sh -c "npx -y playwright@${PLAYWRIGHT_VERSION} run-server --port 4000 --host 0.0.0.0" if ! wait_for_container 5; then exit 1 @@ -137,6 +182,9 @@ GITEA_TEST_E2E_EMAIL="$GITEA_TEST_E2E_USER@$GITEA_TEST_E2E_DOMAIN" if [ -z "${GITEA_TEST_E2E_TIMEOUT_FACTOR:-}" ]; then if [ -n "${CI:-}" ]; then GITEA_TEST_E2E_TIMEOUT_FACTOR=4 + # Container based runs seem slower so bump the default timeout to avoid failing tests + elif [ "${PLAYWRIGHT_MODE}" = "container" ]; then + GITEA_TEST_E2E_TIMEOUT_FACTOR=1.5 else GITEA_TEST_E2E_TIMEOUT_FACTOR=1 fi @@ -149,7 +197,7 @@ export GITEA_TEST_E2E_PASSWORD export GITEA_TEST_E2E_EMAIL export GITEA_TEST_E2E_TIMEOUT_FACTOR -if [ -z "$PLAYWRIGHT_CONTAINER" ]; then +if [ "$PLAYWRIGHT_MODE" = "container" ]; then export PW_TEST_CONNECT_WS_ENDPOINT=ws://127.0.0.1:4000/ fi pnpm exec playwright test "$@" From ae306cb147c66cf0292cb4ab0ab3dde85adea7f3 Mon Sep 17 00:00:00 2001 From: TheFox0x7 Date: Tue, 21 Apr 2026 22:42:47 +0200 Subject: [PATCH 5/5] fix installation --- tools/test-e2e.sh | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/tools/test-e2e.sh b/tools/test-e2e.sh index bce3973a9d..5328ddc4f1 100755 --- a/tools/test-e2e.sh +++ b/tools/test-e2e.sh @@ -62,7 +62,11 @@ detect_playwright_mode if [ "$CMD" = "install" ]; then if [ "$PLAYWRIGHT_MODE" = "local" ]; then # on Github Actions VMs, playwright's system deps are preinstalled - pnpm exec playwright install "$(if [ -z "${GITHUB_ACTIONS:-}" ]; then echo "--with-deps"; fi)" chromium firefox ${PLAYWRIGHT_FLAGS:-} + if [ -z "${GITHUB_ACTIONS:-}" ]; then + pnpm exec playwright install --with-deps chromium firefox ${PLAYWRIGHT_FLAGS:-} + else + pnpm exec playwright install chromium firefox ${PLAYWRIGHT_FLAGS:-} + fi else echo "Running playwright in container as host distro is not supported by playwright directly" ${CONTAINER_RUNTIME:-docker} pull "mcr.microsoft.com/playwright:v${PLAYWRIGHT_VERSION}-noble"