82 lines
2.8 KiB
Bash
Executable File
82 lines
2.8 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
# Run the dockerized integration tests in isolation: builds the app image, starts it on a
|
|
# random port, runs the suite against it, then tears everything down and exits with the
|
|
# suite's exit code.
|
|
#
|
|
# With COVERAGE=1 (see script/integration-coverage) the app runs under Cloverage
|
|
# (docker-compose.coverage.yml); after the suite finishes the app is stopped gracefully so
|
|
# it writes its report, which is copied to target/coverage/integration.
|
|
set -euo pipefail
|
|
cd "$(dirname "$0")/.."
|
|
root=$PWD
|
|
source script/lib/docker.sh
|
|
|
|
# Picks a random port in [lo, hi] that's currently free on this host; retries on
|
|
# collision since another process could grab it first.
|
|
free_port_in_range() {
|
|
local lo=$1 hi=$2 port attempt
|
|
for attempt in $(seq 20); do
|
|
port=$((lo + RANDOM % (hi - lo + 1)))
|
|
# A successful connect means something is already listening.
|
|
if ! (exec 3<>"/dev/tcp/127.0.0.1/$port") 2>/dev/null; then
|
|
echo "$port"
|
|
return 0
|
|
fi
|
|
done
|
|
echo "no free port found in range $lo-$hi" >&2
|
|
return 1
|
|
}
|
|
|
|
port=$(free_port_in_range 30000 40000)
|
|
echo "[test] starting vibe-app on random port $port${COVERAGE:+ (under coverage instrumentation)}"
|
|
|
|
compose=(docker compose)
|
|
if [[ -n "${COVERAGE:-}" ]]; then
|
|
compose+=(-f docker-compose.yml -f docker-compose.coverage.yml)
|
|
fi
|
|
|
|
use_builder
|
|
|
|
cd integration-test
|
|
export VIBE_PORT=$port
|
|
|
|
teardown() {
|
|
local status=$?
|
|
trap - EXIT
|
|
"${compose[@]}" down -v || true
|
|
exit "$status"
|
|
}
|
|
trap teardown EXIT
|
|
trap 'exit 130' INT
|
|
trap 'exit 143' TERM
|
|
|
|
# Build the app image with buildx directly instead of through compose: compose delegates
|
|
# builds to bake, which fails on the CI runner with "failed to find target default". The
|
|
# image name matches `image:` in docker-compose.yml, so `run` below finds it and never
|
|
# builds. DEPS_ALIASES must match build.args in docker-compose.coverage.yml.
|
|
docker buildx build --load \
|
|
--build-arg "DEPS_ALIASES=run${COVERAGE:+:cov}" \
|
|
-t vibe-app-integration \
|
|
-f "$root/Dockerfile" "$root"
|
|
|
|
# `run` returns the test container's own exit code; `up --abort-on-container-exit` can leak
|
|
# the app's SIGTERM exit (143) during teardown instead.
|
|
status=0
|
|
"${compose[@]}" --ansi never run --rm integration-test || status=$?
|
|
|
|
if [[ -n "${COVERAGE:-}" ]]; then
|
|
# SIGTERM is what makes Cloverage write its report, so stop (not kill) the app and pull
|
|
# the report out of the stopped container before `down` removes it.
|
|
out_dir=$root/target/coverage
|
|
echo "[test] stopping vibe-app to flush coverage report"
|
|
"${compose[@]}" stop -t 120 vibe-app || true
|
|
rm -rf "$out_dir/integration"
|
|
mkdir -p "$out_dir"
|
|
if ! "${compose[@]}" cp vibe-app:/app/target/coverage/integration "$out_dir" \
|
|
|| [[ ! -f $out_dir/integration/lcov.info ]]; then
|
|
echo "[test] WARNING: no integration coverage report was produced"
|
|
fi
|
|
fi
|
|
|
|
exit "$status"
|