PRD 0001: Per-agent egress proxy via pipelock (#1)
This commit was merged in pull request #1.
This commit is contained in:
+87
@@ -0,0 +1,87 @@
|
||||
#!/usr/bin/env bash
|
||||
# Integration: full sidecar smoke test. Boots a pipelock container the
|
||||
# same way cli.sh does (docker create + docker cp YAML + docker start),
|
||||
# then probes /health. Catches regressions in:
|
||||
# - the YAML-cp path (the /etc/pipelock.yaml vs /etc/pipelock/ bug)
|
||||
# - argv shape (the `run --listen 0.0.0.0:N` invocation)
|
||||
# - YAML structural validity (pipelock would refuse to start on a bad config)
|
||||
TEST_NAME="pipelock_sidecar_smoke"
|
||||
|
||||
. "$(dirname "$0")/../lib/common.sh"
|
||||
# shellcheck source=../../lib/log.sh
|
||||
. "${REPO_ROOT}/lib/log.sh"
|
||||
# shellcheck source=../../lib/pipelock.sh
|
||||
. "${REPO_ROOT}/lib/pipelock.sh"
|
||||
|
||||
skip_test_if_no_docker
|
||||
|
||||
# Use a distinct name so concurrent runs don't collide.
|
||||
name="cb-test-pipelock-smoke-$$"
|
||||
work_dir="$(mktemp -d)"
|
||||
yaml="${work_dir}/pipelock.yaml"
|
||||
|
||||
cleanup() {
|
||||
docker rm -f "$name" >/dev/null 2>&1 || true
|
||||
rm -rf "$work_dir"
|
||||
}
|
||||
trap cleanup EXIT
|
||||
|
||||
# Generate a real config from a fixture manifest.
|
||||
m="$(write_fixture fixture_minimal)"
|
||||
pipelock_write_yaml "$m" dev "$yaml"
|
||||
rm -f "$m"
|
||||
|
||||
# Same lifecycle as lib/pipelock.sh's pipelock_start, minus the
|
||||
# network-attach steps (we just need a port we can curl).
|
||||
docker create --name "$name" -p 0:8888 \
|
||||
"$CLAUDE_BOTTLE_PIPELOCK_IMAGE" \
|
||||
run --config /etc/pipelock.yaml --listen "0.0.0.0:8888" \
|
||||
>/dev/null 2>&1 \
|
||||
|| { _fail "docker create failed"; test_summary; }
|
||||
|
||||
# This is the exact cp path that broke before — guard against
|
||||
# regressing to a /etc/pipelock/ subdirectory destination.
|
||||
if ! docker cp "$yaml" "${name}:/etc/pipelock.yaml" >/dev/null 2>&1; then
|
||||
_fail "docker cp to /etc/pipelock.yaml failed (parent dir must already exist in image)"
|
||||
test_summary
|
||||
fi
|
||||
|
||||
if ! docker start "$name" >/dev/null 2>&1; then
|
||||
_fail "docker start failed; check that argv 'run --listen 0.0.0.0:8888' still matches image"
|
||||
test_summary
|
||||
fi
|
||||
|
||||
# Find the host-side port docker mapped 8888 to.
|
||||
hostport="$(docker port "$name" 8888 2>/dev/null | head -1 | awk -F: '{print $NF}')"
|
||||
if [ -z "$hostport" ]; then
|
||||
_fail "could not determine published port" "docker port output: $(docker port "$name" 2>&1)"
|
||||
test_summary
|
||||
fi
|
||||
|
||||
# Wait up to 15 seconds for /health to come up.
|
||||
healthy=0
|
||||
for _ in $(seq 1 15); do
|
||||
if curl -fsS "http://127.0.0.1:${hostport}/health" >/dev/null 2>&1; then
|
||||
healthy=1
|
||||
break
|
||||
fi
|
||||
sleep 1
|
||||
done
|
||||
|
||||
if [ "$healthy" -eq 1 ]; then
|
||||
_pass "sidecar /health responded"
|
||||
else
|
||||
_fail "sidecar /health did not respond within 15s" "logs:" "$(docker logs "$name" 2>&1 | tail -20)"
|
||||
test_summary
|
||||
fi
|
||||
|
||||
# Body should mention the version we pinned. We don't pin the exact
|
||||
# version string here because the digest we test against is one
|
||||
# release; the next release will change the version field but should
|
||||
# keep the schema. Keep the assertion at "field is present and has
|
||||
# a numeric-dotted shape".
|
||||
body="$(curl -fsS "http://127.0.0.1:${hostport}/health" 2>&1)"
|
||||
assert_contains "$body" '"status":"healthy"' "/health body status:healthy"
|
||||
assert_match "$body" '"version":"[0-9]+\.[0-9]+\.[0-9]+"' "/health body has version field"
|
||||
|
||||
test_summary
|
||||
Reference in New Issue
Block a user