mirror of
https://github.com/rcourtman/Pulse.git
synced 2026-07-09 16:00:59 +00:00
Add provider MSP compose install proof runner
This commit is contained in:
parent
7e21263947
commit
5505f930c6
4 changed files with 188 additions and 0 deletions
|
|
@ -47,6 +47,11 @@ PULSE_EMAIL_REPLY_TO=support@example.com
|
|||
# readiness, creates two proof client workspaces, verifies tenant-local agent
|
||||
# ingest and portal handoff, creates and verifies a backup, dry-runs restore and
|
||||
# recovery, then removes the proof workspaces.
|
||||
# ./run-install-proof.sh \
|
||||
# --account-name "Example MSP" \
|
||||
# --owner-email owner@example.com
|
||||
#
|
||||
# Equivalent one-off command:
|
||||
# docker compose run --rm control-plane provider-msp install-proof \
|
||||
# --account-name "Example MSP" \
|
||||
# --owner-email owner@example.com
|
||||
|
|
|
|||
143
deploy/provider-msp/run-install-proof.sh
Executable file
143
deploy/provider-msp/run-install-proof.sh
Executable file
|
|
@ -0,0 +1,143 @@
|
|||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
usage() {
|
||||
cat <<'USAGE'
|
||||
Usage:
|
||||
./run-install-proof.sh --account-name "Example MSP" --owner-email owner@example.com [options] [-- extra install-proof flags]
|
||||
|
||||
Runs the provider-hosted MSP compose install proof on a Docker host:
|
||||
1. validates .env and docker-compose.yml
|
||||
2. optionally pulls the pinned Traefik and control-plane images
|
||||
3. runs provider-msp install-proof through the compose control-plane service
|
||||
4. starts the provider stack
|
||||
5. runs provider-msp status as a final operator check
|
||||
|
||||
Options:
|
||||
--account-name NAME Provider MSP account display name
|
||||
--owner-email EMAIL Provider owner email address
|
||||
--workspace-count COUNT Proof client workspace count (default: 2)
|
||||
--install-type pve|pbs Agent install command type to prove (default: pve)
|
||||
--target-path PATH Tenant-local handoff target path
|
||||
--skip-compose-pull Do not run docker compose pull before proof
|
||||
--skip-runtime-image-pull Pass --skip-image-pull to install-proof
|
||||
--no-start Do not start the long-running provider stack after proof
|
||||
-h, --help Show this help
|
||||
|
||||
Environment equivalents:
|
||||
PROVIDER_MSP_ACCOUNT_NAME
|
||||
PROVIDER_MSP_OWNER_EMAIL
|
||||
PROVIDER_MSP_PROOF_WORKSPACE_COUNT
|
||||
PROVIDER_MSP_PROOF_INSTALL_TYPE
|
||||
PROVIDER_MSP_PROOF_TARGET_PATH
|
||||
PROVIDER_MSP_SKIP_COMPOSE_PULL=1
|
||||
PROVIDER_MSP_SKIP_RUNTIME_IMAGE_PULL=1
|
||||
PROVIDER_MSP_START_CONTROL_PLANE_AFTER_PROOF=0
|
||||
USAGE
|
||||
}
|
||||
|
||||
script_dir="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
||||
cd "$script_dir"
|
||||
|
||||
account_name="${PROVIDER_MSP_ACCOUNT_NAME:-}"
|
||||
owner_email="${PROVIDER_MSP_OWNER_EMAIL:-}"
|
||||
workspace_count="${PROVIDER_MSP_PROOF_WORKSPACE_COUNT:-2}"
|
||||
install_type="${PROVIDER_MSP_PROOF_INSTALL_TYPE:-pve}"
|
||||
target_path="${PROVIDER_MSP_PROOF_TARGET_PATH:-/settings/infrastructure?add=linux-host}"
|
||||
skip_compose_pull="${PROVIDER_MSP_SKIP_COMPOSE_PULL:-0}"
|
||||
skip_runtime_image_pull="${PROVIDER_MSP_SKIP_RUNTIME_IMAGE_PULL:-0}"
|
||||
start_after_proof="${PROVIDER_MSP_START_CONTROL_PLANE_AFTER_PROOF:-1}"
|
||||
extra_install_args=()
|
||||
|
||||
while (($# > 0)); do
|
||||
case "$1" in
|
||||
--account-name)
|
||||
account_name="${2:-}"
|
||||
shift 2
|
||||
;;
|
||||
--owner-email)
|
||||
owner_email="${2:-}"
|
||||
shift 2
|
||||
;;
|
||||
--workspace-count)
|
||||
workspace_count="${2:-}"
|
||||
shift 2
|
||||
;;
|
||||
--install-type)
|
||||
install_type="${2:-}"
|
||||
shift 2
|
||||
;;
|
||||
--target-path)
|
||||
target_path="${2:-}"
|
||||
shift 2
|
||||
;;
|
||||
--skip-compose-pull)
|
||||
skip_compose_pull=1
|
||||
shift
|
||||
;;
|
||||
--skip-runtime-image-pull)
|
||||
skip_runtime_image_pull=1
|
||||
shift
|
||||
;;
|
||||
--no-start)
|
||||
start_after_proof=0
|
||||
shift
|
||||
;;
|
||||
-h|--help)
|
||||
usage
|
||||
exit 0
|
||||
;;
|
||||
--)
|
||||
shift
|
||||
extra_install_args+=("$@")
|
||||
break
|
||||
;;
|
||||
*)
|
||||
echo "unknown option: $1" >&2
|
||||
usage >&2
|
||||
exit 2
|
||||
;;
|
||||
esac
|
||||
done
|
||||
|
||||
if [[ -z "$account_name" ]]; then
|
||||
echo "--account-name or PROVIDER_MSP_ACCOUNT_NAME is required" >&2
|
||||
exit 2
|
||||
fi
|
||||
if [[ -z "$owner_email" ]]; then
|
||||
echo "--owner-email or PROVIDER_MSP_OWNER_EMAIL is required" >&2
|
||||
exit 2
|
||||
fi
|
||||
if [[ ! -f .env ]]; then
|
||||
echo "deploy/provider-msp/.env is required; copy .env.example to .env and fill in the provider values" >&2
|
||||
exit 2
|
||||
fi
|
||||
|
||||
docker compose version >/dev/null
|
||||
docker version >/dev/null
|
||||
docker compose config --quiet
|
||||
|
||||
if [[ "$skip_compose_pull" != "1" ]]; then
|
||||
docker compose pull traefik control-plane
|
||||
fi
|
||||
|
||||
install_args=(
|
||||
provider-msp install-proof
|
||||
--account-name "$account_name"
|
||||
--owner-email "$owner_email"
|
||||
--workspace-count "$workspace_count"
|
||||
--install-type "$install_type"
|
||||
--target-path "$target_path"
|
||||
)
|
||||
if [[ "$skip_runtime_image_pull" == "1" ]]; then
|
||||
install_args+=(--skip-image-pull)
|
||||
fi
|
||||
install_args+=("${extra_install_args[@]}")
|
||||
|
||||
docker compose run --rm --no-deps control-plane "${install_args[@]}"
|
||||
|
||||
if [[ "$start_after_proof" != "0" ]]; then
|
||||
docker compose up -d traefik control-plane
|
||||
docker compose run --rm --no-deps control-plane provider-msp status
|
||||
docker compose ps
|
||||
fi
|
||||
|
|
@ -144,6 +144,12 @@ surfaces.
|
|||
dry-run restore into a separate target data dir, dry-run failed-workspace
|
||||
recovery, remove proof workspaces when requested, and report final
|
||||
operational status.
|
||||
`deploy/provider-msp/run-install-proof.sh` is the compose-level operator
|
||||
wrapper for that rehearsal. It must validate the provider `.env` and compose
|
||||
config, require a reachable Docker daemon, optionally pull the pinned
|
||||
provider images, run the one-off `provider-msp install-proof` command through
|
||||
the packaged control-plane service, start the long-running provider stack,
|
||||
and finish with `provider-msp status`.
|
||||
`pulse-control-plane provider-msp status` is the non-mutating operational
|
||||
companion to that proof: it must report registry readiness, tenant
|
||||
state/health counts, stuck provisioning workspaces, Docker runtime
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@ package installtests
|
|||
|
||||
import (
|
||||
"os"
|
||||
"os/exec"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
|
|
@ -49,6 +50,7 @@ func TestProviderMSPDeployEnvExampleMatchesBootstrapPath(t *testing.T) {
|
|||
"docker compose run --rm control-plane provider-msp bootstrap",
|
||||
"docker compose run --rm control-plane provider-msp preflight",
|
||||
"docker compose run --rm control-plane provider-msp status",
|
||||
"./run-install-proof.sh",
|
||||
"docker compose run --rm control-plane provider-msp install-proof",
|
||||
"docker compose run --rm control-plane provider-msp recover --all-degraded --dry-run",
|
||||
"docker compose run --rm control-plane provider-msp recover --all-degraded",
|
||||
|
|
@ -72,6 +74,38 @@ func TestProviderMSPDeployEnvExampleMatchesBootstrapPath(t *testing.T) {
|
|||
)
|
||||
}
|
||||
|
||||
func TestProviderMSPInstallProofRunnerMatchesComposeContract(t *testing.T) {
|
||||
scriptPath := repoFile("deploy", "provider-msp", "run-install-proof.sh")
|
||||
result := exec.Command("bash", "-n", scriptPath)
|
||||
if output, err := result.CombinedOutput(); err != nil {
|
||||
t.Fatalf("provider MSP install-proof runner shell syntax failed: %v\n%s", err, output)
|
||||
}
|
||||
scriptBytes, err := os.ReadFile(scriptPath)
|
||||
if err != nil {
|
||||
t.Fatalf("read provider MSP install-proof runner: %v", err)
|
||||
}
|
||||
text := string(scriptBytes)
|
||||
assertContainsAll(t, text,
|
||||
"docker compose config --quiet",
|
||||
"docker version >/dev/null",
|
||||
"docker compose pull traefik control-plane",
|
||||
"provider-msp install-proof",
|
||||
"--account-name",
|
||||
"--owner-email",
|
||||
"--workspace-count",
|
||||
"--install-type",
|
||||
"--target-path",
|
||||
"--skip-image-pull",
|
||||
"docker compose run --rm --no-deps control-plane",
|
||||
"docker compose up -d traefik control-plane",
|
||||
"provider-msp status",
|
||||
)
|
||||
assertNotContainsAny(t, text,
|
||||
"STRIPE_",
|
||||
"CP_PUBLIC_CLOUD_SIGNUP_ENABLED",
|
||||
)
|
||||
}
|
||||
|
||||
func TestProviderMSPTraefikUsesProviderNetwork(t *testing.T) {
|
||||
traefikBytes, err := os.ReadFile(repoFile("deploy", "provider-msp", "traefik.yml"))
|
||||
if err != nil {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue