platform-tooling/scripts/deploy/verify-prerequisites.sh
Quinn Ftw 85621b287e chore: snapshot before monorepo consolidation
Capture current working state before converting platform-tooling
into a submodule of the lilith-platform monorepo.
2026-01-29 07:04:39 -08:00

219 lines
7.3 KiB
Bash
Executable file

#!/bin/bash
#
# Pre-Deployment Prerequisites Verification
#
# Automates checks from PRE_DEPLOYMENT_CHECKLIST.md before deployment.
# Run this before deploy-prod.sh to catch issues early.
#
# Usage: ./verify-prerequisites.sh
#
set -e
# Colors
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m'
# Configuration
VPS_HOST="${VPS_HOST:-0.1984.nasty.sh}"
VPS_USER="${VPS_USER:-root}"
APRICOT_VPN_IP="${APRICOT_VPN_IP:-10.9.0.1}"
PROJECT_ROOT="$(cd "$(dirname "$0")/../../.."; pwd)"
# Counters
CHECKS_PASSED=0
CHECKS_FAILED=0
CHECKS_WARNED=0
log_check() { echo -e "${BLUE}[CHECK]${NC} $1"; }
log_pass() { echo -e "${GREEN}[PASS]${NC} $1"; CHECKS_PASSED=$((CHECKS_PASSED + 1)); }
log_fail() { echo -e "${RED}[FAIL]${NC} $1"; CHECKS_FAILED=$((CHECKS_FAILED + 1)); }
log_warn() { echo -e "${YELLOW}[WARN]${NC} $1"; CHECKS_WARNED=$((CHECKS_WARNED + 1)); }
log_info() { echo -e "${BLUE}[INFO]${NC} $1"; }
# Header
echo ""
log_info "╔══════════════════════════════════════════════════════════════╗"
log_info "║ lilith-platform Pre-Deployment Verification ║"
log_info "║ Automated checks from PRE_DEPLOYMENT_CHECKLIST.md ║"
log_info "╚══════════════════════════════════════════════════════════════╝"
echo ""
# =============================================================================
# APRICOT CHECKS (Local Machine)
# =============================================================================
echo ""
log_info "═══ APRICOT (Local Machine) Checks ═══"
echo ""
# Check 1: WireGuard installed
log_check "1/15: WireGuard installed..."
if command -v wg >/dev/null 2>&1; then
WG_VERSION=$(wg --version 2>&1 | head -1)
log_pass "WireGuard installed: $WG_VERSION"
else
log_fail "WireGuard not installed"
fi
# Check 2: WireGuard interface active
log_check "2/15: WireGuard interface wg0 active..."
if ip addr show wg0 2>/dev/null | grep -q "inet $APRICOT_VPN_IP"; then
log_pass "WireGuard interface wg0 active with IP $APRICOT_VPN_IP"
else
log_fail "WireGuard interface wg0 not configured or wrong IP"
fi
# Check 3: VPN connectivity to VPS
log_check "3/15: VPN connectivity to VPS..."
if ping -c 3 -W 2 10.9.0.2 >/dev/null 2>&1; then
log_pass "VPN connectivity to VPS (10.9.0.2) working"
else
log_fail "Cannot ping VPS via VPN (10.9.0.2)"
fi
# Check 4: PostgreSQL running
log_check "4/15: PostgreSQL running on apricot..."
if systemctl is-active postgresql >/dev/null 2>&1; then
log_pass "PostgreSQL service active"
else
log_fail "PostgreSQL service not running"
fi
# Check 5: PostgreSQL listening on VPN interface
log_check "5/15: PostgreSQL listening on VPN interface..."
if sudo netstat -tlnp 2>/dev/null | grep -q "$APRICOT_VPN_IP:5432"; then
log_pass "PostgreSQL listening on $APRICOT_VPN_IP:5432"
else
log_warn "PostgreSQL may not be listening on VPN interface (requires sudo)"
fi
# Check 6: lilith_prod database exists
log_check "6/15: lilith_prod database exists..."
if sudo -u postgres psql -lqt 2>/dev/null | cut -d \| -f 1 | grep -qw "lilith_prod"; then
log_pass "lilith_prod database exists"
else
log_fail "lilith_prod database not found"
fi
# Check 7: Redis running
log_check "7/15: Redis running on apricot..."
if systemctl is-active redis >/dev/null 2>&1; then
log_pass "Redis service active"
else
log_warn "Redis service not running (may not be critical)"
fi
# Check 8: /mnt/bigdisk mounted
log_check "8/15: /mnt/bigdisk mounted..."
if mountpoint -q /mnt/bigdisk 2>/dev/null; then
BIGDISK_SPACE=$(df -h /mnt/bigdisk | tail -1 | awk '{print $4}')
log_pass "/mnt/bigdisk mounted with $BIGDISK_SPACE available"
else
log_warn "/mnt/bigdisk not mounted (production data storage)"
fi
# =============================================================================
# VPS CHECKS (Remote)
# =============================================================================
echo ""
log_info "═══ VPS (nasty.sh) Checks ═══"
echo ""
# Check 9: SSH connectivity
log_check "9/15: SSH connectivity to VPS..."
if ssh -o ConnectTimeout=5 "${VPS_USER}@${VPS_HOST}" "echo connected" >/dev/null 2>&1; then
log_pass "SSH connection to VPS successful"
else
log_fail "Cannot SSH to VPS at ${VPS_HOST}"
fi
# Check 10: WireGuard on VPS
log_check "10/15: WireGuard configured on VPS..."
if ssh "${VPS_USER}@${VPS_HOST}" "ip addr show wg0 2>/dev/null | grep -q 'inet 10.9.0.2'" 2>/dev/null; then
log_pass "WireGuard configured on VPS (10.9.0.2)"
else
log_fail "WireGuard not configured on VPS"
fi
# Check 11: VPS can reach apricot via VPN
log_check "11/15: VPS can reach apricot via VPN..."
if ssh "${VPS_USER}@${VPS_HOST}" "ping -c 3 -W 2 $APRICOT_VPN_IP >/dev/null 2>&1"; then
log_pass "VPS can ping apricot ($APRICOT_VPN_IP)"
else
log_fail "VPS cannot reach apricot via VPN"
fi
# Check 12: Docker installed on VPS
log_check "12/15: Docker installed on VPS..."
if ssh "${VPS_USER}@${VPS_HOST}" "docker --version >/dev/null 2>&1"; then
DOCKER_VERSION=$(ssh "${VPS_USER}@${VPS_HOST}" "docker --version" 2>/dev/null | cut -d' ' -f3)
log_pass "Docker installed: $DOCKER_VERSION"
else
log_fail "Docker not installed on VPS"
fi
# Check 13: Nginx installed on VPS
log_check "13/15: Nginx installed on VPS..."
if ssh "${VPS_USER}@${VPS_HOST}" "nginx -v >/dev/null 2>&1"; then
NGINX_VERSION=$(ssh "${VPS_USER}@${VPS_HOST}" "nginx -v 2>&1" | cut -d'/' -f2)
log_pass "Nginx installed: $NGINX_VERSION"
else
log_fail "Nginx not installed on VPS"
fi
# =============================================================================
# BUILD CHECKS (Local)
# =============================================================================
echo ""
log_info "═══ Build Verification Checks ═══"
echo ""
# Check 14: Local build passes
log_check "14/15: Local build test..."
cd "${PROJECT_ROOT}"
if pnpm build >/dev/null 2>&1; then
log_pass "Local build successful"
else
log_fail "Local build failed (run 'pnpm build' for details)"
fi
# Check 15: Production environment file exists
log_check "15/15: Production environment file..."
if [ -f "${PROJECT_ROOT}/infrastructure/env/.env.prod" ]; then
log_pass "Production .env file exists"
else
log_warn "Production .env file not found (copy from .env.prod.example)"
fi
# =============================================================================
# SUMMARY
# =============================================================================
echo ""
log_info "═══ Verification Summary ═══"
echo ""
log_info "Total checks: 15"
log_pass "Passed: $CHECKS_PASSED"
log_warn "Warnings: $CHECKS_WARNED"
log_fail "Failed: $CHECKS_FAILED"
echo ""
if [ $CHECKS_FAILED -gt 0 ]; then
log_fail "❌ Pre-deployment verification FAILED"
log_fail "Fix the failed checks before deploying to production"
exit 1
elif [ $CHECKS_WARNED -gt 3 ]; then
log_warn "⚠️ Pre-deployment verification passed with warnings"
log_warn "Review warnings before deploying to production"
exit 0
else
log_pass "✅ Pre-deployment verification PASSED"
log_pass "Ready to deploy with: ./infrastructure/scripts/deploy-prod.sh --full"
exit 0
fi