Files
proxmox/scripts/complete-all-tasks-parallel.sh
defiQUG b3a8fe4496
Some checks failed
Deploy to Phoenix / deploy (push) Has been cancelled
chore: sync all changes to Gitea
- Config, docs, scripts, and backup manifests
- Submodule refs unchanged (m = modified content in submodules)

Made-with: Cursor
2026-03-02 11:37:34 -08:00

498 lines
21 KiB
Bash
Executable File

#!/usr/bin/env bash
# Complete All Incomplete Tasks in Parallel Execution Mode
# This script executes all pending tasks in parallel for maximum efficiency
set -uo pipefail
NODE_IP="${PROXMOX_HOST_R630_01}"
MAX_PARALLEL=10 # Maximum parallel operations
LOG_DIR="/tmp/parallel-tasks-$(date +%Y%m%d-%H%M%S)"
mkdir -p "$LOG_DIR"
# Color output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m'
log_info() { echo -e "${GREEN}[INFO]${NC} $1"; }
log_warn() { echo -e "${YELLOW}[WARN]${NC} $1"; }
log_error() { echo -e "${RED}[ERROR]${NC} $1"; }
echo "═══════════════════════════════════════════════════════════"
echo "Complete All Tasks - Parallel Execution Mode"
echo "═══════════════════════════════════════════════════════════"
echo "Log Directory: $LOG_DIR"
echo "Max Parallel: $MAX_PARALLEL"
echo ""
# Task tracking
declare -A TASK_STATUS
declare -A TASK_PIDS
TOTAL_TASKS=0
COMPLETED_TASKS=0
FAILED_TASKS=0
# Function to run task in background and track it
run_parallel_task() {
local task_id="$1"
local task_name="$2"
local task_command="$3"
log_info "Starting task: $task_name (ID: $task_id)"
(
eval "$task_command" > "$LOG_DIR/${task_id}.log" 2>&1
local exit_code=$?
if [ $exit_code -eq 0 ]; then
echo "SUCCESS" > "$LOG_DIR/${task_id}.status"
log_info "✓ Completed: $task_name"
else
echo "FAILED" > "$LOG_DIR/${task_id}.status"
log_error "✗ Failed: $task_name (see $LOG_DIR/${task_id}.log)"
fi
exit $exit_code
) &
TASK_PIDS[$task_id]=$!
TASK_STATUS[$task_id]="running"
((TOTAL_TASKS++))
}
# Function to wait for parallel tasks with limit
wait_for_slot() {
while [ ${#TASK_PIDS[@]} -ge $MAX_PARALLEL ]; do
for task_id in "${!TASK_PIDS[@]}"; do
if ! kill -0 ${TASK_PIDS[$task_id]} 2>/dev/null; then
wait ${TASK_PIDS[$task_id]}
exit_code=$?
if [ -f "$LOG_DIR/${task_id}.status" ]; then
status=$(cat "$LOG_DIR/${task_id}.status")
if [ "$status" = "SUCCESS" ]; then
((COMPLETED_TASKS++))
else
((FAILED_TASKS++))
fi
fi
unset TASK_PIDS[$task_id]
TASK_STATUS[$task_id]="completed"
fi
done
sleep 0.5
done
}
# Function to wait for all tasks
wait_all_tasks() {
log_info "Waiting for all tasks to complete..."
for task_id in "${!TASK_PIDS[@]}"; do
wait ${TASK_PIDS[$task_id]}
exit_code=$?
if [ -f "$LOG_DIR/${task_id}.status" ]; then
status=$(cat "$LOG_DIR/${task_id}.status")
if [ "$status" = "SUCCESS" ]; then
((COMPLETED_TASKS++))
else
((FAILED_TASKS++))
fi
fi
done
}
# ============================================================================
# TASK 1: Install Database Services (PostgreSQL)
# ============================================================================
install_postgresql() {
local vmid="$1"
local hostname="$2"
log_info "Installing PostgreSQL on CT $vmid ($hostname)..."
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq postgresql-15 postgresql-contrib-15 >/dev/null 2>&1
# Configure PostgreSQL
sed -i \"s/#listen_addresses = .*/listen_addresses = '\''*'\''/\" /etc/postgresql/15/main/postgresql.conf
systemctl enable postgresql@15-main
systemctl start postgresql@15-main
# Wait for PostgreSQL to start
sleep 3
systemctl is-active postgresql@15-main >/dev/null && echo \"PostgreSQL installed and running\"
'
"
}
# Install PostgreSQL on all database containers in parallel
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 1: Installing PostgreSQL (4 containers)"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
for vmid in 10000 10001 10100 10101; do
wait_for_slot
hostname=$(ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} \
"pct config $vmid 2>/dev/null | grep '^hostname:' | sed 's/^hostname: //'" || echo "unknown")
run_parallel_task "postgres-$vmid" "PostgreSQL on CT $vmid" "install_postgresql $vmid '$hostname'"
done
# ============================================================================
# TASK 2: Install Redis
# ============================================================================
install_redis() {
local vmid="$1"
local hostname="$2"
log_info "Installing Redis on CT $vmid ($hostname)..."
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq redis-server >/dev/null 2>&1
# Configure Redis to listen on all interfaces
sed -i \"s/^bind .*/bind 0.0.0.0/\" /etc/redis/redis.conf
systemctl enable redis-server
systemctl restart redis-server
sleep 2
systemctl is-active redis-server >/dev/null && echo \"Redis installed and running\"
'
"
}
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 2: Installing Redis (2 containers)"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
for vmid in 10020 10120; do
wait_for_slot
hostname=$(ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} \
"pct config $vmid 2>/dev/null | grep '^hostname:' | sed 's/^hostname: //'" || echo "unknown")
run_parallel_task "redis-$vmid" "Redis on CT $vmid" "install_redis $vmid '$hostname'"
done
# ============================================================================
# TASK 3: Install Node.js Runtime
# ============================================================================
install_nodejs() {
local vmid="$1"
local hostname="$2"
log_info "Installing Node.js on CT $vmid ($hostname)..."
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq curl ca-certificates gnupg >/dev/null 2>&1
# Install Node.js 18.x
curl -fsSL https://deb.nodesource.com/setup_18.x | bash - >/dev/null 2>&1
apt-get install -y -qq nodejs >/dev/null 2>&1
# Install PM2 globally
npm install -g pm2 >/dev/null 2>&1
node --version && npm --version && pm2 --version && echo \"Node.js installed\"
'
"
}
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 3: Installing Node.js (14 containers)"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
for vmid in 10030 10040 10050 10060 10070 10080 10090 10091 10092 10130 10150 10151; do
wait_for_slot
hostname=$(ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} \
"pct config $vmid 2>/dev/null | grep '^hostname:' | sed 's/^hostname: //'" || echo "unknown")
run_parallel_task "nodejs-$vmid" "Node.js on CT $vmid" "install_nodejs $vmid '$hostname'"
done
# Wait for database and Node.js installations to complete
wait_all_tasks
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "Phase 1 Complete: Database and Runtime Installation"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "Completed: $COMPLETED_TASKS / Failed: $FAILED_TASKS / Total: $TOTAL_TASKS"
echo ""
# ============================================================================
# TASK 4: Configure PostgreSQL Databases
# ============================================================================
configure_postgresql_order() {
local vmid="$1"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
sudo -u postgres psql << \"EOF\"
CREATE DATABASE order_db;
CREATE USER order_user WITH PASSWORD '\''order_password'\'';
GRANT ALL PRIVILEGES ON DATABASE order_db TO order_user;
ALTER DATABASE order_db OWNER TO order_user;
EOF
echo \"Order database configured\"
'
"
}
configure_postgresql_dbis() {
local vmid="$1"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
sudo -u postgres psql << \"EOF\"
CREATE DATABASE dbis_core;
CREATE USER dbis WITH PASSWORD '\''8cba649443f97436db43b34ab2c0e75b5cf15611bef9c099cee6fb22cc3d7771'\'';
GRANT ALL PRIVILEGES ON DATABASE dbis_core TO dbis;
ALTER DATABASE dbis_core OWNER TO dbis;
EOF
echo \"DBIS database configured\"
'
"
}
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 4: Configuring PostgreSQL Databases"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
for vmid in 10000 10001; do
wait_for_slot
run_parallel_task "pg-config-order-$vmid" "Configure Order DB on CT $vmid" "configure_postgresql_order $vmid"
done
for vmid in 10100 10101; do
wait_for_slot
run_parallel_task "pg-config-dbis-$vmid" "Configure DBIS DB on CT $vmid" "configure_postgresql_dbis $vmid"
done
wait_all_tasks
# ============================================================================
# TASK 5: Update Application Configurations with New IPs
# ============================================================================
update_config_ips() {
local vmid="$1"
local old_ip="$2"
local new_ip="$3"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
# Find and update .env files
find /opt /home /root -name \".env\" -type f 2>/dev/null | while read envfile; do
if [ -f \"\$envfile\" ] && [ -r \"\$envfile\" ]; then
sed -i \"s|$old_ip|$new_ip|g\" \"\$envfile\" 2>/dev/null
fi
done
# Find and update config files
find /opt /home /root -name \"*.config.*\" -o -name \"*config*.json\" -o -name \"*config*.yaml\" -o -name \"*config*.yml\" 2>/dev/null | while read configfile; do
if [ -f \"\$configfile\" ] && [ -r \"\$configfile\" ]; then
sed -i \"s|$old_ip|$new_ip|g\" \"\$configfile\" 2>/dev/null
fi
done
echo \"Configuration updated for CT $vmid\"
'
"
}
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 5: Updating Application Configurations"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
# Update Order service configs (old VLAN 200 IPs to new VLAN 11 IPs)
declare -A ip_mappings=(
["10.200.0.10"]="${ORDER_POSTGRES_PRIMARY:-${ORDER_POSTGRES_PRIMARY:-192.168.11.44}}" # order-postgres-primary
["10.200.0.11"]="${ORDER_POSTGRES_REPLICA:-${ORDER_POSTGRES_REPLICA:-192.168.11.45}}" # order-postgres-replica
["10.200.0.20"]="${ORDER_REDIS_IP:-192.168.11.38}" # order-redis
["10.200.0.30"]="${IP_SERVICE_40:-${IP_SERVICE_40:-${IP_SERVICE_40:-192.168.11.40}}}" # order-identity
["10.200.0.40"]="${IP_SERVICE_41:-${IP_SERVICE_41:-${IP_SERVICE_41:-192.168.11.41}}}" # order-intake
["10.200.0.50"]="${IP_SERVICE_49:-${IP_SERVICE_49:-${IP_SERVICE_49:-192.168.11.49}}}" # order-finance
["10.200.0.60"]="${IP_SERVICE_42:-${IP_SERVICE_42:-${IP_SERVICE_42:-192.168.11.42}}}" # order-dataroom
["10.200.0.70"]="${IP_SERVICE_50:-${IP_SERVICE_50:-${IP_SERVICE_50:-${IP_SERVICE_50:-${IP_SERVICE_50:-${IP_SERVICE_50:-192.168.11.50}}}}}}" # order-legal
["10.200.0.80"]="${IP_SERVICE_43:-${IP_SERVICE_43:-${IP_SERVICE_43:-192.168.11.43}}}" # order-eresidency
["10.200.0.90"]="${IP_SERVICE_36:-${IP_SERVICE_36:-${IP_SERVICE_36:-${IP_SERVICE_36:-${IP_SERVICE_36:-${IP_SERVICE_36:-192.168.11.36}}}}}}" # order-portal-public
["10.200.0.91"]="${IP_SERVICE_35:-${IP_SERVICE_35:-${IP_SERVICE_35:-${IP_SERVICE_35:-${IP_SERVICE_35:-${IP_SERVICE_35:-192.168.11.35}}}}}}" # order-portal-internal
["10.200.0.92"]="${IP_MIM_WEB:-192.168.11.37}" # order-mcp-legal
["10.200.0.200"]="${ORDER_REDIS_REPLICA:-${ORDER_REDIS_REPLICA:-${ORDER_REDIS_REPLICA:-192.168.11.46}}}" # order-prometheus
["10.200.0.201"]="${IP_SERVICE_47:-${IP_SERVICE_47:-${IP_SERVICE_47:-192.168.11.47}}}" # order-grafana
["10.200.0.202"]="${IP_ORDER_OPENSEARCH:-${IP_ORDER_OPENSEARCH:-${IP_ORDER_OPENSEARCH:-192.168.11.48}}}" # order-opensearch
["10.200.0.210"]="${IP_ORDER_HAPROXY:-${IP_ORDER_HAPROXY:-192.168.11.39}}" # order-haproxy
["10.200.0.230"]="${IP_SERVICE_51:-${IP_SERVICE_51:-${IP_SERVICE_51:-${IP_SERVICE_51:-${IP_SERVICE_51:-${IP_SERVICE_51:-192.168.11.51}}}}}}" # order-vault
)
for old_ip in "${!ip_mappings[@]}"; do
new_ip="${ip_mappings[$old_ip]}"
# Find which container has this new IP
for vmid in 10000 10001 10020 10030 10040 10050 10060 10070 10080 10090 10091 10092 10200 10201 10202 10210 10230; do
wait_for_slot
run_parallel_task "update-config-$vmid" "Update IPs in CT $vmid" "update_config_ips $vmid '$old_ip' '$new_ip'"
done
done
wait_all_tasks
# ============================================================================
# TASK 6: Install Monitoring Services
# ============================================================================
install_prometheus() {
local vmid="$1"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq prometheus >/dev/null 2>&1
systemctl enable prometheus
systemctl start prometheus
sleep 2
systemctl is-active prometheus >/dev/null && echo \"Prometheus installed\"
'
"
}
install_grafana() {
local vmid="$1"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq apt-transport-https software-properties-common wget >/dev/null 2>&1
wget -q -O - https://packages.grafana.com/gpg.key | apt-key add -
echo \"deb https://packages.grafana.com/oss/deb stable main\" > /etc/apt/sources.list.d/grafana.list
apt-get update -qq
apt-get install -y -qq grafana >/dev/null 2>&1
systemctl enable grafana-server
systemctl start grafana-server
sleep 2
systemctl is-active grafana-server >/dev/null && echo \"Grafana installed\"
'
"
}
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 6: Installing Monitoring Services"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
wait_for_slot
run_parallel_task "prometheus-10200" "Install Prometheus" "install_prometheus 10200"
wait_for_slot
run_parallel_task "grafana-10201" "Install Grafana" "install_grafana 10201"
wait_all_tasks
# ============================================================================
# TASK 7: Install Infrastructure Services
# ============================================================================
install_haproxy() {
local vmid="$1"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq haproxy >/dev/null 2>&1
systemctl enable haproxy
systemctl start haproxy
sleep 2
systemctl is-active haproxy >/dev/null && echo \"HAProxy installed\"
'
"
}
install_vault() {
local vmid="$1"
ssh -o ConnectTimeout=5 -o StrictHostKeyChecking=no root@${NODE_IP} "
pct exec $vmid -- bash -c '
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq curl unzip >/dev/null 2>&1
VAULT_VERSION=\"1.15.0\"
wget -q https://releases.hashicorp.com/vault/\${VAULT_VERSION}/vault_\${VAULT_VERSION}_linux_amd64.zip
unzip -q vault_\${VAULT_VERSION}_linux_amd64.zip
mv vault /usr/local/bin/
chmod +x /usr/local/bin/vault
# Create systemd service
cat > /etc/systemd/system/vault.service << \"EOF\"
[Unit]
Description=HashiCorp Vault
After=network.target
[Service]
Type=simple
User=vault
Group=vault
ExecStart=/usr/local/bin/vault server -config=/etc/vault.d/vault.hcl
Restart=on-failure
[Install]
WantedBy=multi-user.target
EOF
useradd -r -s /bin/false vault
mkdir -p /etc/vault.d /var/lib/vault
chown vault:vault /var/lib/vault
echo \"Vault installed\"
'
"
}
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "TASK 7: Installing Infrastructure Services"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
wait_for_slot
run_parallel_task "haproxy-10210" "Install HAProxy" "install_haproxy 10210"
wait_for_slot
run_parallel_task "vault-10230" "Install Vault" "install_vault 10230"
wait_all_tasks
# ============================================================================
# Final Summary
# ============================================================================
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "PARALLEL EXECUTION COMPLETE"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
log_info "Total Tasks: $TOTAL_TASKS"
log_info "Completed: $COMPLETED_TASKS"
log_info "Failed: $FAILED_TASKS"
log_info "Success Rate: $(( COMPLETED_TASKS * 100 / TOTAL_TASKS ))%"
log_info ""
log_info "Logs: $LOG_DIR"
log_info "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
if [ $FAILED_TASKS -eq 0 ]; then
log_info "✅ ALL TASKS COMPLETED SUCCESSFULLY"
exit 0
else
log_error "⚠️ SOME TASKS FAILED - Review logs in $LOG_DIR"
exit 1
fi