#!/usr/bin/env bash # Complete NPMplus certificate cleanup # Removes soft-deleted certificates and handles duplicates set -euo pipefail # Load IP configuration SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" PROJECT_ROOT="$(cd "$SCRIPT_DIR/.." && pwd)" source "${PROJECT_ROOT}/config/ip-addresses.conf" 2>/dev/null || true # Colors RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' BLUE='\033[0;34m' NC='\033[0m' log_info() { echo -e "${BLUE}[INFO]${NC} $1"; } log_success() { echo -e "${GREEN}[✓]${NC} $1"; } log_warn() { echo -e "${YELLOW}[⚠]${NC} $1"; } log_error() { echo -e "${RED}[✗]${NC} $1"; } PROXMOX_HOST="${1:-192.168.11.11}" CONTAINER_ID="${2:-10233}" REMOVE_SOFT_DELETED="${3:-true}" KEEP_COMBINED="${4:-true}" # true = keep #25 (combined), false = keep #2-6 (individual) echo "" echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" echo "🧹 NPMplus Certificate Cleanup" echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" echo "" # Query certificates log_info "Querying certificates..." CERT_JSON=$(ssh root@"$PROXMOX_HOST" "pct exec $CONTAINER_ID -- docker exec npmplus node -e \" const Database = require('better-sqlite3'); const db = new Database('/data/npmplus/database.sqlite', { readonly: true }); const certs = db.prepare('SELECT id, domain_names, provider, expires_on, created_on, is_deleted FROM certificate ORDER BY id').all(); console.log(JSON.stringify(certs)); db.close(); \" 2>&1" || echo "[]") # Step 1: Remove soft-deleted certificates if [ "$REMOVE_SOFT_DELETED" = "true" ]; then log_info "Step 1: Removing soft-deleted certificates..." SOFT_DELETED=$(echo "$CERT_JSON" | jq -r '.[] | select(.is_deleted == 1) | .id' 2>/dev/null || echo "") if [ -n "$SOFT_DELETED" ]; then deleted_count=0 for cert_id in $SOFT_DELETED; do log_info " Deleting certificate ID: $cert_id" DELETE_RESULT=$(ssh root@"$PROXMOX_HOST" "pct exec $CONTAINER_ID -- docker exec npmplus node -e \" const Database = require('better-sqlite3'); const db = new Database('/data/npmplus/database.sqlite'); const stmt = db.prepare('DELETE FROM certificate WHERE id = ?'); const result = stmt.run($cert_id); console.log('Deleted:', result.changes); db.close(); \" 2>&1" || echo "") if echo "$DELETE_RESULT" | grep -q "Deleted: 1"; then log_success " ✓ Deleted certificate ID: $cert_id" deleted_count=$((deleted_count + 1)) else log_error " ✗ Failed to delete certificate ID: $cert_id" fi done log_success "Removed $deleted_count soft-deleted certificates" else log_success "No soft-deleted certificates to remove" fi echo "" fi # Step 2: Handle duplicate active certificates for sankofa.nexus if [ "$KEEP_COMBINED" = "true" ]; then log_info "Step 2: Removing individual certificates (keeping combined #25)..." INDIVIDUAL_CERTS="2 3 4 5 6" for cert_id in $INDIVIDUAL_CERTS; do # Check if certificate exists and is active cert_exists=$(echo "$CERT_JSON" | jq -r ".[] | select(.id == $cert_id and .is_deleted == 0) | .id" 2>/dev/null || echo "") if [ -n "$cert_exists" ]; then log_info " Deleting individual certificate ID: $cert_id" DELETE_RESULT=$(ssh root@"$PROXMOX_HOST" "pct exec $CONTAINER_ID -- docker exec npmplus node -e \" const Database = require('better-sqlite3'); const db = new Database('/data/npmplus/database.sqlite'); const stmt = db.prepare('DELETE FROM certificate WHERE id = ?'); const result = stmt.run($cert_id); console.log('Deleted:', result.changes); db.close(); \" 2>&1" || echo "") if echo "$DELETE_RESULT" | grep -q "Deleted: 1"; then log_success " ✓ Deleted certificate ID: $cert_id" else log_error " ✗ Failed to delete certificate ID: $cert_id" fi fi done log_success "Kept combined certificate #25, removed individual certificates" else log_info "Step 2: Removing combined certificate (keeping individual certificates)..." DELETE_RESULT=$(ssh root@"$PROXMOX_HOST" "pct exec $CONTAINER_ID -- docker exec npmplus node -e \" const Database = require('better-sqlite3'); const db = new Database('/data/npmplus/database.sqlite'); const stmt = db.prepare('DELETE FROM certificate WHERE id = 25'); const result = stmt.run(); console.log('Deleted:', result.changes); db.close(); \" 2>&1" || echo "") if echo "$DELETE_RESULT" | grep -q "Deleted: 1"; then log_success " ✓ Deleted combined certificate ID: 25" log_success "Kept individual certificates #2-6" else log_error " ✗ Failed to delete certificate ID: 25" fi fi echo "" # Final summary log_info "Verifying cleanup..." FINAL_CERT_JSON=$(ssh root@"$PROXMOX_HOST" "pct exec $CONTAINER_ID -- docker exec npmplus node -e \" const Database = require('better-sqlite3'); const db = new Database('/data/npmplus/database.sqlite', { readonly: true }); const certs = db.prepare('SELECT id, domain_names, is_deleted FROM certificate WHERE is_deleted = 0 ORDER BY id').all(); console.log(JSON.stringify(certs)); db.close(); \" 2>&1" || echo "[]") FINAL_COUNT=$(echo "$FINAL_CERT_JSON" | jq 'length' 2>/dev/null || echo "0") echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" log_info "Final Status:" log_success " Active certificates remaining: $FINAL_COUNT" echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━" echo "" log_success "✅ Certificate cleanup complete!" echo ""