feat: deploy portable workspace registry
This commit is contained in:
Executable
+114
@@ -0,0 +1,114 @@
|
||||
#!/usr/bin/env bash
|
||||
# Exercises the registry through an isolated Compose project. An optional WORKSPACE_GIT_REMOTE
|
||||
# is contacted read-only as a connectivity preflight; all pull/fallback mutations target a fresh
|
||||
# temporary bare repository so this smoke test can never alter an operator's shared registry.
|
||||
set -euo pipefail
|
||||
|
||||
root="$(cd "$(dirname "$0")/.." && pwd -P)"
|
||||
tmp="$(mktemp -d "${TMPDIR:-/tmp}/thoth-workspace-registry-smoke.XXXXXX")"
|
||||
project="thoth-workspace-registry-smoke-$$"
|
||||
remote="$tmp/remote.git"
|
||||
seed="$tmp/seed"
|
||||
branch="workspace-registry-smoke"
|
||||
|
||||
cleanup() {
|
||||
compose down --volumes --remove-orphans >/dev/null 2>&1 || true
|
||||
rm -rf "$tmp"
|
||||
}
|
||||
trap cleanup EXIT HUP INT TERM
|
||||
|
||||
compose() {
|
||||
docker compose --project-name "$project" -f - "$@" <<EOF
|
||||
services:
|
||||
core:
|
||||
build:
|
||||
context: $root
|
||||
dockerfile: docker/core.Dockerfile
|
||||
image: thothii-workspace-registry-smoke:local
|
||||
environment:
|
||||
HOST: 0.0.0.0
|
||||
PORT: "8787"
|
||||
AUTH_MODE: none
|
||||
THT_HARNESS_DIR: /app/harness
|
||||
THT_BIN: /opt/venv/bin/tht
|
||||
SETTINGS_FILE: /tmp/settings.json
|
||||
THT_WORKSPACE_REGISTRY_ROOT: /data/workspace-registry
|
||||
THT_WORKSPACE_GIT_REMOTE: /fixtures/remote.git
|
||||
THT_WORKSPACE_GIT_BRANCH: $branch
|
||||
THT_WORKSPACE_INSTALLATION_ID: smoke
|
||||
THT_WORKSPACE_SECRET_ROOTS: /run/secrets
|
||||
volumes:
|
||||
- workspace-registry:/data/workspace-registry
|
||||
- $remote:/fixtures/remote.git:ro
|
||||
volumes:
|
||||
workspace-registry: {}
|
||||
EOF
|
||||
}
|
||||
|
||||
wait_for_core() {
|
||||
local attempt
|
||||
for attempt in $(seq 1 30); do
|
||||
if compose exec -T core curl -fsS http://127.0.0.1:8787/health >/dev/null 2>&1; then
|
||||
return 0
|
||||
fi
|
||||
sleep 1
|
||||
done
|
||||
compose logs core >&2 || true
|
||||
return 1
|
||||
}
|
||||
|
||||
if [[ -n "${WORKSPACE_GIT_REMOTE:-}" ]]; then
|
||||
echo "== Read-only Git remote preflight =="
|
||||
git ls-remote --heads "$WORKSPACE_GIT_REMOTE" >/dev/null
|
||||
fi
|
||||
|
||||
echo "== Seed isolated workspace registry =="
|
||||
git init --bare --initial-branch=main "$remote" >/dev/null
|
||||
git clone "$remote" "$seed" >/dev/null
|
||||
git -C "$seed" checkout -b "$branch" >/dev/null
|
||||
npm --prefix "$root/backend" run build >/dev/null
|
||||
node "$root/backend/dist/workspaces/migrate-legacy.js" \
|
||||
--input "$root/harness/workspaces/local.yaml" --output "$seed" >/dev/null
|
||||
git -C "$seed" add workspaces/local.yaml
|
||||
git -C "$seed" -c user.name='Workspace Registry Smoke' -c user.email='workspace-registry-smoke@example.invalid' \
|
||||
commit -m 'Seed workspace registry smoke' >/dev/null
|
||||
git -C "$seed" push origin "HEAD:$branch" >/dev/null
|
||||
|
||||
echo "== Build and start isolated Compose core =="
|
||||
compose up -d --build
|
||||
wait_for_core
|
||||
initial_status="$(compose exec -T core curl -fsS http://127.0.0.1:8787/workspace-registry/status)"
|
||||
printf '%s' "$initial_status" | grep -Eq '"head":"[0-9a-f]{40}"'
|
||||
compose exec -T core test -f /data/workspace-registry/state/active.json
|
||||
|
||||
echo "== Recreate core and prove registry volume persistence =="
|
||||
compose up -d --force-recreate
|
||||
wait_for_core
|
||||
recreated_status="$(compose exec -T core curl -fsS http://127.0.0.1:8787/workspace-registry/status)"
|
||||
initial_head="$(printf '%s' "$initial_status" | sed -n 's/.*"head":"\([0-9a-f]*\)".*/\1/p')"
|
||||
recreated_head="$(printf '%s' "$recreated_status" | sed -n 's/.*"head":"\([0-9a-f]*\)".*/\1/p')"
|
||||
test -n "$initial_head" && test "$initial_head" = "$recreated_head"
|
||||
|
||||
echo "== Pull a valid remote update =="
|
||||
sed -i.bak 's/name: Local/name: Local Updated/' "$seed/workspaces/local.yaml"
|
||||
rm "$seed/workspaces/local.yaml.bak"
|
||||
git -C "$seed" add workspaces/local.yaml
|
||||
git -C "$seed" -c user.name='Workspace Registry Smoke' -c user.email='workspace-registry-smoke@example.invalid' \
|
||||
commit -m 'Update workspace registry smoke' >/dev/null
|
||||
git -C "$seed" push origin "HEAD:$branch" >/dev/null
|
||||
compose exec -T core curl -fsS -X POST http://127.0.0.1:8787/workspace-registry/pull | grep -Eq '"head":"[0-9a-f]{40}"'
|
||||
compose exec -T core curl -fsS http://127.0.0.1:8787/workspaces | grep -Fq 'Local Updated'
|
||||
|
||||
echo "== Reject invalid remote content and retain the last valid snapshot =="
|
||||
printf '%s\n' 'workspace: invalid' >"$seed/workspaces/local.yaml"
|
||||
git -C "$seed" add workspaces/local.yaml
|
||||
git -C "$seed" -c user.name='Workspace Registry Smoke' -c user.email='workspace-registry-smoke@example.invalid' \
|
||||
commit -m 'Invalid workspace registry smoke fixture' >/dev/null
|
||||
git -C "$seed" push origin "HEAD:$branch" >/dev/null
|
||||
if compose exec -T core curl -fsS -X POST http://127.0.0.1:8787/workspace-registry/pull >/dev/null; then
|
||||
echo "registry accepted invalid remote workspace content" >&2
|
||||
exit 1
|
||||
fi
|
||||
compose exec -T core curl -fsS http://127.0.0.1:8787/workspaces | grep -Fq 'Local Updated'
|
||||
|
||||
echo "workspace registry smoke passed"
|
||||
Reference in New Issue
Block a user