From f13fd3faf07da47d1c047112f1e2336419e7b8e6 Mon Sep 17 00:00:00 2001 From: hsiegeln <37154749+hsiegeln@users.noreply.github.com> Date: Mon, 13 Apr 2026 16:30:53 +0200 Subject: [PATCH] feat(installer): add docker operations and health verification --- installer/install.sh | 78 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 78 insertions(+) diff --git a/installer/install.sh b/installer/install.sh index ecc3e7e..e0f17e9 100644 --- a/installer/install.sh +++ b/installer/install.sh @@ -877,3 +877,81 @@ EOF log_info "Generated docker-compose.yml" } + +# --- Docker operations --- + +docker_compose_pull() { + log_info "Pulling Docker images..." + (cd "$INSTALL_DIR" && docker compose -p "$COMPOSE_PROJECT" pull) + log_success "All images pulled." +} + +docker_compose_up() { + log_info "Starting Cameleer SaaS platform..." + (cd "$INSTALL_DIR" && docker compose -p "$COMPOSE_PROJECT" up -d) + log_info "Containers started." +} + +docker_compose_down() { + log_info "Stopping Cameleer SaaS platform..." + (cd "$INSTALL_DIR" && docker compose -p "$COMPOSE_PROJECT" down) +} + +# --- Health verification --- + +check_service_health() { + local name="$1" check_cmd="$2" timeout_secs="${3:-120}" + local elapsed=0 + local start_time=$(date +%s) + + while [ $elapsed -lt $timeout_secs ]; do + if eval "$check_cmd" >/dev/null 2>&1; then + local duration=$(($(date +%s) - start_time)) + printf " ${GREEN}[ok]${NC} %-20s ready (%ds)\n" "$name" "$duration" + return 0 + fi + sleep 5 + elapsed=$(( $(date +%s) - start_time )) + done + + printf " ${RED}[FAIL]${NC} %-20s not ready after %ds\n" "$name" "$timeout_secs" + echo " Check: docker compose -p $COMPOSE_PROJECT logs ${name,,}" + return 1 +} + +verify_health() { + echo "" + log_info "Verifying installation..." + local failed=0 + + check_service_health "PostgreSQL" \ + "cd '$INSTALL_DIR' && docker compose -p '$COMPOSE_PROJECT' exec -T postgres pg_isready -U cameleer" \ + 120 || failed=1 + + [ $failed -eq 0 ] && check_service_health "ClickHouse" \ + "cd '$INSTALL_DIR' && docker compose -p '$COMPOSE_PROJECT' exec -T clickhouse clickhouse-client --password \"\$(grep CLICKHOUSE_PASSWORD '$INSTALL_DIR/.env' | cut -d= -f2)\" --query 'SELECT 1'" \ + 120 || failed=1 + + [ $failed -eq 0 ] && check_service_health "Logto" \ + "cd '$INSTALL_DIR' && docker compose -p '$COMPOSE_PROJECT' exec -T logto node -e \"require('http').get('http://localhost:3001/oidc/.well-known/openid-configuration', r => process.exit(r.statusCode === 200 ? 0 : 1)).on('error', () => process.exit(1))\"" \ + 120 || failed=1 + + [ $failed -eq 0 ] && check_service_health "Bootstrap" \ + "cd '$INSTALL_DIR' && docker compose -p '$COMPOSE_PROJECT' exec -T logto test -f /data/logto-bootstrap.json" \ + 120 || failed=1 + + [ $failed -eq 0 ] && check_service_health "Cameleer SaaS" \ + "curl -sfk https://localhost:${HTTPS_PORT}/platform/api/config" \ + 120 || failed=1 + + [ $failed -eq 0 ] && check_service_health "Traefik routing" \ + "curl -sfk -o /dev/null https://localhost:${HTTPS_PORT}/" \ + 120 || failed=1 + + echo "" + if [ $failed -ne 0 ]; then + log_error "Installation verification failed. Stack is running — check logs." + exit 1 + fi + log_success "All services healthy." +}