#!/usr/bin/env bash
set -euo pipefail

# deploy.sh — Deploy Harbor container registry to Kubernetes
# Run from gremlin-1: bash ~/sources/kube/harbor/deploy.sh

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"

echo "=== Harbor Container Registry Deploy ==="
echo ""

# -------------------------------------------------------
# 1. Create namespace
# -------------------------------------------------------
echo "--- Step 1: Creating namespace ---"
kubectl create namespace harbor-service --dry-run=client -o yaml | kubectl apply -f -
echo "  ✓ harbor-service namespace ready"
echo ""

# -------------------------------------------------------
# 2. Proxy CA cert (for Squid SSL bump)
# -------------------------------------------------------
echo "--- Step 2: Proxy CA cert ---"
CA_CERT_PATH="/tmp/harbor-home.crt"
if curl -sf http://192.168.42.1/home.crt -o "$CA_CERT_PATH" 2>/dev/null; then
  if ! kubectl get configmap proxy-ca-cert -n harbor-service > /dev/null 2>&1; then
    kubectl create configmap proxy-ca-cert --from-file=ca.crt="$CA_CERT_PATH" -n harbor-service
    echo "  ✓ proxy-ca-cert created"
  else
    echo "  ✓ proxy-ca-cert already exists"
  fi
else
  echo "  ⚠ Could not fetch CA cert (non-fatal)"
fi
echo ""

# -------------------------------------------------------
# 3. Create NFS directories (requires root for mount)
# -------------------------------------------------------
echo "--- Step 3: Ensuring NFS directories ---"
if [ "$(id -u)" -eq 0 ]; then
  mkdir -p /tmp/harbor-nfs-init
  mount -t nfs 192.168.42.8:/volume1/Kubernetes/harbor /tmp/harbor-nfs-init 2>/dev/null || true
  mkdir -p /tmp/harbor-nfs-init/data/registry
  mkdir -p /tmp/harbor-nfs-init/data/redis
  mkdir -p /tmp/harbor-nfs-init/data/jobservice
  mkdir -p /tmp/harbor-nfs-init/data/trivy
  umount /tmp/harbor-nfs-init 2>/dev/null || true
  rmdir /tmp/harbor-nfs-init 2>/dev/null || true
  echo "  ✓ NFS directories ready"
else
  echo "  ⚠ Not root — skipping NFS dir creation (dirs may already exist)"
fi
echo ""

# -------------------------------------------------------
# 4. Apply PVs and PVCs
# -------------------------------------------------------
echo "--- Step 4: Applying PVs and PVCs ---"
kubectl apply -f "$SCRIPT_DIR/../pvs/harbor-pv.yaml"
kubectl apply -f "$SCRIPT_DIR/pvcs.yaml"
echo "  ✓ PVs and PVCs applied"
echo ""

# -------------------------------------------------------
# 5. Remove old plain Docker Registry ingress
# -------------------------------------------------------
echo "--- Step 5: Checking old registry ingress ---"
if kubectl get ingress registry-ingress -n git-server > /dev/null 2>&1; then
  echo "  Removing old registry ingress from git-server namespace..."
  kubectl delete ingress registry-ingress -n git-server
  echo "  ✓ Old registry ingress removed"
else
  echo "  ✓ No old registry ingress found"
fi
echo ""

# -------------------------------------------------------
# 6. Install/upgrade Harbor via Helm
# -------------------------------------------------------
echo "--- Step 6: Installing Harbor ---"
helm repo add harbor https://helm.goharbor.io 2>/dev/null || true
helm repo update harbor 2>/dev/null || true

HARBOR_EXISTS=$(helm list -n harbor-service -q 2>/dev/null | grep -c harbor || true)
if [ "${HARBOR_EXISTS:-0}" -gt 0 ]; then
  echo "  Harbor already installed — upgrading..."
else
  echo "  Fresh Harbor install..."
fi

helm upgrade --install harbor harbor/harbor \
  --namespace harbor-service \
  --values "$SCRIPT_DIR/values.yaml" \
  --timeout 10m \
  --wait

echo ""
echo "  Waiting for Harbor core to be ready..."
kubectl wait --for=condition=ready pod -l app=harbor,component=core -n harbor-service --timeout=180s || true
echo ""

# -------------------------------------------------------
# 7. Configure Harbor via API (idempotent)
# -------------------------------------------------------
echo "--- Step 7: Configuring Harbor project and robot account ---"
HARBOR_API="https://registry.celestium.life/api/v2.0"
HARBOR_AUTH="admin:St0nks0racl3!"

# Create stonks-oracle project if it doesn't exist
if curl -sf -u "$HARBOR_AUTH" "$HARBOR_API/projects?name=stonks-oracle" | python3 -c "import sys,json; sys.exit(0 if json.load(sys.stdin) else 1)" 2>/dev/null; then
  echo "  ✓ Project stonks-oracle already exists"
else
  curl -sf -X POST -u "$HARBOR_AUTH" \
    -H "Content-Type: application/json" \
    "$HARBOR_API/projects" \
    -d '{"project_name":"stonks-oracle","public":true,"metadata":{"auto_scan":"true","severity":"high"},"storage_limit":-1}'
  echo "  ✓ Project stonks-oracle created (public, auto-scan enabled)"
fi

# Create CI robot account if it doesn't exist
EXISTING_ROBOT=$(curl -sf -u "$HARBOR_AUTH" "$HARBOR_API/robots" 2>/dev/null | python3 -c "
import sys, json
robots = json.load(sys.stdin)
for r in robots:
    if 'ci-push' in r.get('name', ''):
        print(r['name'])
        break
" 2>/dev/null || true)

if [ -n "$EXISTING_ROBOT" ]; then
  echo "  ✓ Robot account already exists: $EXISTING_ROBOT"
else
  ROBOT_RESP=$(curl -sf -X POST -u "$HARBOR_AUTH" \
    -H "Content-Type: application/json" \
    "$HARBOR_API/robots" \
    -d '{
      "name":"ci-push",
      "description":"CI/CD pipeline push account",
      "duration":-1,
      "level":"project",
      "permissions":[{
        "namespace":"stonks-oracle",
        "kind":"project",
        "access":[
          {"resource":"repository","action":"push"},
          {"resource":"repository","action":"pull"},
          {"resource":"tag","action":"create"},
          {"resource":"tag","action":"list"},
          {"resource":"artifact","action":"read"}
        ]
      }]
    }')
  ROBOT_NAME=$(echo "$ROBOT_RESP" | python3 -c "import sys,json; print(json.load(sys.stdin)['name'])")
  ROBOT_SECRET=$(echo "$ROBOT_RESP" | python3 -c "import sys,json; print(json.load(sys.stdin)['secret'])")
  echo "  ✓ Robot account created"
  echo "    Username: $ROBOT_NAME"
  echo "    Secret:   $ROBOT_SECRET"
  echo "    ⚠ Save these — add as HARBOR_USERNAME and HARBOR_PASSWORD in your CI secrets"
fi

# Set tag retention policy (idempotent — check if one exists first)
PROJECT_ID=$(curl -sf -u "$HARBOR_AUTH" "$HARBOR_API/projects?name=stonks-oracle" | python3 -c "import sys,json; print(json.load(sys.stdin)[0]['project_id'])" 2>/dev/null || true)
if [ -n "$PROJECT_ID" ]; then
  EXISTING_RETENTION=$(curl -sf -u "$HARBOR_AUTH" "$HARBOR_API/retentions" 2>/dev/null || true)
  if echo "$EXISTING_RETENTION" | python3 -c "import sys,json; d=json.load(sys.stdin); sys.exit(0 if isinstance(d,list) and len(d)>0 else 1)" 2>/dev/null; then
    echo "  ✓ Tag retention policy already exists"
  else
    curl -sf -X POST -u "$HARBOR_AUTH" \
      -H "Content-Type: application/json" \
      "$HARBOR_API/retentions" \
      -d "{
        \"algorithm\":\"or\",
        \"scope\":{\"level\":\"project\",\"ref\":$PROJECT_ID},
        \"trigger\":{\"kind\":\"Schedule\",\"settings\":{\"cron\":\"0 0 0 * * *\"}},
        \"rules\":[
          {\"disabled\":false,\"action\":\"retain\",\"scope_selectors\":{\"repository\":[{\"kind\":\"doublestar\",\"decoration\":\"repoMatches\",\"pattern\":\"**\"}]},\"tag_selectors\":[{\"kind\":\"doublestar\",\"decoration\":\"matches\",\"pattern\":\"latest\"}],\"params\":{}},
          {\"disabled\":false,\"action\":\"retain\",\"scope_selectors\":{\"repository\":[{\"kind\":\"doublestar\",\"decoration\":\"repoMatches\",\"pattern\":\"**\"}]},\"tag_selectors\":[{\"kind\":\"doublestar\",\"decoration\":\"matches\",\"pattern\":\"**\"}],\"params\":{\"latestPushedK\":10}}
        ]
      }" 2>/dev/null && echo "  ✓ Tag retention policy created (keep latest + last 10 tags, daily)" || echo "  ⚠ Could not create retention policy (non-fatal)"
  fi
fi
echo ""

echo "=== Harbor Deploy Complete ==="
echo ""
echo "  URL:   https://registry.celestium.life"
echo "  Login: admin / St0nks0racl3!"
echo ""
echo "  Pods:"
kubectl get pods -n harbor-service
