#!/bin/bash # Helper script to manually clean all service databases in Kubernetes # This ensures databases are in a clean state before running migration generation set -euo pipefail # Colors for output RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' NC='\033[0m' # No Color # Configuration NAMESPACE="${KUBE_NAMESPACE:-bakery-ia}" # Parse command line arguments CONFIRM=false SPECIFIC_SERVICE="" while [[ $# -gt 0 ]]; do case $1 in --namespace) NAMESPACE="$2"; shift 2 ;; --service) SPECIFIC_SERVICE="$2"; shift 2 ;; --yes) CONFIRM=true; shift ;; -h|--help) echo "Usage: $0 [OPTIONS]" echo "" echo "Options:" echo " --namespace NAME Use specific Kubernetes namespace (default: bakery-ia)" echo " --service NAME Clean only specific service database" echo " --yes Skip confirmation prompt" echo "" echo "Examples:" echo " $0 # Clean all databases (with confirmation)" echo " $0 --service auth --yes # Clean only auth database without confirmation" exit 0 ;; *) echo "Unknown option: $1"; echo "Use --help for usage information"; exit 1 ;; esac done # List of all services SERVICES=( "pos" "sales" "recipes" "training" "auth" "orders" "inventory" "suppliers" "tenant" "notification" "alert-processor" "forecasting" "external" "production" ) # If specific service is provided, use only that if [ -n "$SPECIFIC_SERVICE" ]; then SERVICES=("$SPECIFIC_SERVICE") fi echo -e "${BLUE}========================================${NC}" echo -e "${BLUE}Database Cleanup Script (K8s)${NC}" echo -e "${BLUE}========================================${NC}" echo "" echo -e "${RED}⚠ WARNING: This will DROP ALL TABLES in the following databases:${NC}" for service in "${SERVICES[@]}"; do echo -e " - ${service}" done echo "" if [ "$CONFIRM" = false ]; then read -p "Are you sure you want to continue? (yes/no) " -r echo if [[ ! $REPLY =~ ^yes$ ]]; then echo -e "${YELLOW}Aborted.${NC}" exit 0 fi fi SUCCESS_COUNT=0 FAILED_COUNT=0 FAILED_SERVICES=() # Function to get a running pod for a service get_running_pod() { local service=$1 local pod_name="" local selectors=( "app.kubernetes.io/name=${service}-service,app.kubernetes.io/component=microservice" "app.kubernetes.io/name=${service}-service,app.kubernetes.io/component=worker" "app.kubernetes.io/name=${service}-service" ) for selector in "${selectors[@]}"; do pod_name=$(kubectl get pods -n "$NAMESPACE" -l "$selector" --field-selector=status.phase=Running -o jsonpath='{.items[0].metadata.name}' 2>/dev/null) if [ -n "$pod_name" ]; then echo "$pod_name" return 0 fi done echo "" return 1 } echo "" echo -e "${BLUE}Starting database cleanup...${NC}" echo "" for service in "${SERVICES[@]}"; do echo -e "${BLUE}----------------------------------------${NC}" echo -e "${BLUE}Cleaning: $service${NC}" echo -e "${BLUE}----------------------------------------${NC}" # Find pod POD_NAME=$(get_running_pod "$service") if [ -z "$POD_NAME" ]; then echo -e "${RED}✗ No running pod found, skipping...${NC}" FAILED_COUNT=$((FAILED_COUNT + 1)) FAILED_SERVICES+=("$service (pod not found)") continue fi echo -e "${GREEN}✓ Found pod: $POD_NAME${NC}" # Get database URL environment variable name db_env_var=$(echo "$service" | tr '[:lower:]-' '[:upper:]_')_DATABASE_URL CONTAINER="${service}-service" # Drop all tables CLEANUP_RESULT=$(kubectl exec -n "$NAMESPACE" "$POD_NAME" -c "$CONTAINER" -- sh -c "cd /app && PYTHONPATH=/app:/app/shared:\$PYTHONPATH python3 << 'EOFPYTHON' import asyncio import os from sqlalchemy.ext.asyncio import create_async_engine from sqlalchemy import text async def cleanup_database(): try: engine = create_async_engine(os.getenv('$db_env_var')) # Get list of tables before cleanup async with engine.connect() as conn: result = await conn.execute(text(\"\"\" SELECT COUNT(*) FROM pg_tables WHERE schemaname = 'public' \"\"\")) table_count_before = result.scalar() # Drop and recreate public schema async with engine.begin() as conn: await conn.execute(text('DROP SCHEMA IF EXISTS public CASCADE')) await conn.execute(text('CREATE SCHEMA public')) await conn.execute(text('GRANT ALL ON SCHEMA public TO PUBLIC')) # Verify cleanup async with engine.connect() as conn: result = await conn.execute(text(\"\"\" SELECT COUNT(*) FROM pg_tables WHERE schemaname = 'public' \"\"\")) table_count_after = result.scalar() await engine.dispose() print(f'SUCCESS: Dropped {table_count_before} tables, {table_count_after} remaining') return 0 except Exception as e: print(f'ERROR: {str(e)}') return 1 exit(asyncio.run(cleanup_database())) EOFPYTHON " 2>&1) if echo "$CLEANUP_RESULT" | grep -q "SUCCESS"; then echo -e "${GREEN}✓ Database cleaned successfully${NC}" echo -e "${BLUE} $CLEANUP_RESULT${NC}" SUCCESS_COUNT=$((SUCCESS_COUNT + 1)) else echo -e "${RED}✗ Database cleanup failed${NC}" echo -e "${YELLOW}Error details: $CLEANUP_RESULT${NC}" FAILED_COUNT=$((FAILED_COUNT + 1)) FAILED_SERVICES+=("$service (cleanup failed)") fi echo "" done # Summary echo -e "${BLUE}========================================${NC}" echo -e "${BLUE}Summary${NC}" echo -e "${BLUE}========================================${NC}" echo -e "${GREEN}✓ Successfully cleaned: $SUCCESS_COUNT databases${NC}" echo -e "${RED}✗ Failed: $FAILED_COUNT databases${NC}" if [ "$FAILED_COUNT" -gt 0 ]; then echo "" echo -e "${RED}Failed services:${NC}" for failed_service in "${FAILED_SERVICES[@]}"; do echo -e "${RED} - $failed_service${NC}" done fi echo "" if [ "$SUCCESS_COUNT" -gt 0 ]; then echo -e "${GREEN}Databases are now clean and ready for migration generation!${NC}" echo -e "${YELLOW}Next step: Run ./regenerate_migrations_k8s.sh${NC}" fi