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

# ── SpendOS Setup ──────────────────────────────────────
# One command to provision your autonomous agent economy.
# Usage: ./setup.sh [--deploy --provider railway]

GREEN='\033[0;32m'
YELLOW='\033[1;33m'
RED='\033[0;31m'
CYAN='\033[0;36m'
NC='\033[0m'
BOLD='\033[1m'

log()  { echo -e "${GREEN}[SpendOS]${NC} $1"; }
warn() { echo -e "${YELLOW}[SpendOS]${NC} $1"; }
err()  { echo -e "${RED}[SpendOS]${NC} $1"; }
info() { echo -e "${CYAN}[SpendOS]${NC} $1"; }

echo ""
echo -e "${BOLD}  ╔═══════════════════════════════════════════════╗${NC}"
echo -e "${BOLD}  ║   SpendOS — Autonomous Agent Economy          ║${NC}"
echo -e "${BOLD}  ║   The first agent that governs its own spend  ║${NC}"
echo -e "${BOLD}  ╚═══════════════════════════════════════════════╝${NC}"
echo ""

# ── Check prerequisites ───────────────────────────────

command -v node >/dev/null 2>&1 || { err "Node.js required (22+). Install: https://nodejs.org"; exit 1; }
NODE_V=$(node -v | sed 's/v//' | cut -d. -f1)
if [ "$NODE_V" -lt 22 ]; then
  err "Node.js 22+ required (found v$NODE_V)"
  exit 1
fi
log "Node.js $(node -v)"

# ── Install dependencies ──────────────────────────────

log "Installing dependencies..."
npm install --legacy-peer-deps 2>&1 | tail -3

# ── Auto-provision everything ─────────────────────────

if [ ! -f .env ]; then
  log "Provisioning your SpendOS instance..."
  cp .env.example .env

  # ── 1. Admin token (auto) ──
  ADMIN_TOKEN=$(openssl rand -hex 32)
  sed -i.bak "s/generate-with-openssl-rand-hex-32/$ADMIN_TOKEN/" .env && rm -f .env.bak
  log "Admin token: ${CYAN}$ADMIN_TOKEN${NC}"

  # ── 2. OWS passphrase (auto) ──
  OWS_PASS=$(openssl rand -base64 32)
  sed -i.bak "s|your-vault-passphrase|$OWS_PASS|" .env && rm -f .env.bak
  log "OWS vault passphrase: generated"

  # ── 3. OWS wallet mnemonic (auto-generate via viem) ──
  log "Generating OWS wallet..."
  MNEMONIC=$(node --input-type=module -e "
    import { generateMnemonic, english } from 'viem/accounts';
    console.log(generateMnemonic(english));
  " 2>/dev/null || echo "")

  if [ -n "$MNEMONIC" ]; then
    ESCAPED=$(echo "$MNEMONIC" | sed 's/[&/\]/\\&/g')
    sed -i.bak "s/your twelve word mnemonic phrase here/$ESCAPED/" .env && rm -f .env.bak
    # Derive the wallet address
    WALLET_ADDR=$(node --input-type=module -e "
      import { mnemonicToAccount } from 'viem/accounts';
      const a = mnemonicToAccount('$MNEMONIC');
      console.log(a.address);
    " 2>/dev/null || echo "unknown")
    log "OWS wallet created: ${CYAN}$WALLET_ADDR${NC}"
    echo ""
    echo -e "  ${YELLOW}IMPORTANT: Save this mnemonic somewhere safe!${NC}"
    echo -e "  ${BOLD}$MNEMONIC${NC}"
    echo ""
  else
    warn "Could not auto-generate wallet. Add mnemonic manually to .env"
  fi

  # ── 4. Deployer key (auto-generate for audit contract) ──
  DEPLOYER_KEY=$(node --input-type=module -e "
    import { generatePrivateKey, privateKeyToAccount } from 'viem/accounts';
    const key = generatePrivateKey();
    const acc = privateKeyToAccount(key);
    console.log(key + ' ' + acc.address);
  " 2>/dev/null || echo "")

  if [ -n "$DEPLOYER_KEY" ]; then
    DKEY=$(echo "$DEPLOYER_KEY" | cut -d' ' -f1)
    DADDR=$(echo "$DEPLOYER_KEY" | cut -d' ' -f2)
    sed -i.bak "s|0x...your-deployer-private-key|$DKEY|" .env && rm -f .env.bak
    log "Deployer wallet: ${CYAN}$DADDR${NC}"
    info "Fund this with a tiny amount of ETH on Base for audit gas"
  fi

  # ── 5. Optional: CDP keys (user provides) ──
  echo ""
  echo -e "${BOLD}Optional — x402 payments (skip with Enter):${NC}"
  echo -e "  Get keys at: https://docs.cdp.coinbase.com"
  echo ""

  if [ -t 0 ]; then
    read -p "  CDP API Key ID: " CDP_ID
    if [ -n "$CDP_ID" ]; then
      sed -i.bak "s/your-cdp-key-id/$CDP_ID/" .env && rm -f .env.bak
      read -p "  CDP API Key Secret: " CDP_SECRET
      if [ -n "$CDP_SECRET" ]; then
        sed -i.bak "s/your-cdp-key-secret/$CDP_SECRET/" .env && rm -f .env.bak
        log "CDP x402 payments configured"
      fi
    else
      info "Skipped — endpoints will run without payment gate (free mode)"
    fi

    echo ""
    echo -e "${BOLD}Optional — Twitter/X (agent can post and interact):${NC}"
    echo -e "  The agent uses a visual browser to log into X."
    echo -e "  Credentials are stored securely (never in git, env var only)."
    echo ""
    read -p "  Twitter/X username (or Enter to skip): " TWITTER_USER
    if [ -n "$TWITTER_USER" ]; then
      read -sp "  Twitter/X password: " TWITTER_PASS
      echo ""
      echo "TWITTER_USERNAME=$TWITTER_USER" >> .env
      echo "TWITTER_PASSWORD=$TWITTER_PASS" >> .env
      log "Twitter configured — agent will log in via browser on first boot"
      info "Credentials stored in .env only (never committed to git)"
    else
      info "Skipped — agent runs without Twitter access"
    fi

    echo ""
    echo -e "${BOLD}Optional — MoonPay (agent gets market data, quotes, balances):${NC}"
    echo -e "  Get key at: https://dashboard.moonpay.com"
    echo ""
    read -p "  MoonPay API Key (or Enter to skip): " MOONPAY_KEY
    if [ -n "$MOONPAY_KEY" ]; then
      echo "MOONPAY_API_KEY=$MOONPAY_KEY" >> .env
      log "MoonPay connected — agent can view quotes, balances, token data"
      info "Signing/sending tools are blocked — transactions require delegation approval"
    else
      info "Skipped — agent runs without MoonPay market data"
    fi
  fi

else
  log ".env already exists, skipping provisioning"
fi

# ── Create local data directories ─────────────────────

DATA_DIR="${SPENDOS_DATA_DIR:-./data}"
mkdir -p "$DATA_DIR" 2>/dev/null || mkdir -p /tmp/spendos-data

# ── Summary ───────────────────────────────────────────

# ── ACP Agent Commerce setup ──────────────────────

if [ -d "acp-seller" ] && [ -t 0 ]; then
  echo ""
  echo -e "${BOLD}ACP — Agent Commerce Protocol (earn from other agents):${NC}"
  echo ""

  if [ -f "acp-seller/config.json" ] && node -e "const c=JSON.parse(require('fs').readFileSync('acp-seller/config.json'));process.exit(c.LITE_AGENT_API_KEY?0:1)" 2>/dev/null; then
    log "ACP already configured"
    ACP_AGENT=$(node -e "const c=JSON.parse(require('fs').readFileSync('acp-seller/config.json'));console.log(c.agents?.find(a=>a.active)?.name||'unknown')" 2>/dev/null)
    info "Active agent: ${ACP_AGENT}"
  else
    read -p "  Connect to ACP marketplace? (Y/n): " ACP_CONNECT
    if [ "${ACP_CONNECT,,}" != "n" ]; then
      log "Opening browser for ACP login..."
      cd acp-seller
      npx tsx bin/acp.ts setup 2>&1
      if [ $? -eq 0 ]; then
        log "ACP connected! Registering SpendOS offerings..."
        # Create agent named spendos
        npx tsx bin/acp.ts agent create spendos 2>&1 || true
        npx tsx bin/acp.ts profile update description "Autonomous AI agent — URL summarization, tweet generation, translation. Pay-per-call via USDC." 2>&1 || true
        # Register offerings
        for offering in src/seller/offerings/spendos/spendos_*/; do
          name=$(basename "$offering")
          npx tsx bin/acp.ts sell create "$name" 2>&1 || true
        done
        log "ACP offerings registered"
      fi
      cd ..
    else
      info "Skipped — run 'cd acp-seller && npx tsx bin/acp.ts setup' later"
    fi
  fi
fi

echo ""
echo -e "${GREEN}══════════════════════════════════════════════════${NC}"
echo -e "${GREEN}  Setup complete!${NC}"
echo -e "${GREEN}══════════════════════════════════════════════════${NC}"
echo ""
echo -e "  ${BOLD}Run locally:${NC}"
echo -e "    npx tsx src/server.ts"
echo ""
ENVTOKEN=$(grep SPENDOS_ADMIN_TOKEN .env 2>/dev/null | cut -d= -f2 || echo "YOUR_TOKEN")
echo -e "  ${BOLD}Dashboard:${NC}"
echo -e "    http://localhost:3030/?token=${ENVTOKEN}"
echo ""
echo -e "  ${BOLD}Deploy to Railway:${NC}"
echo -e "    ./setup.sh --deploy --provider railway"
echo ""

# ── Deploy to Railway ─────────────────────────────────

DEPLOY=false
PROVIDER=""

for arg in "$@"; do
  case $arg in
    --deploy) DEPLOY=true ;;
    railway)  PROVIDER="railway" ;;
  esac
done

if [ "$DEPLOY" = true ] && [ "$PROVIDER" = "railway" ]; then
  echo ""
  log "Deploying to Railway..."

  command -v railway >/dev/null 2>&1 || {
    log "Installing Railway CLI..."
    npm install -g @railway/cli
  }

  # Login check
  railway whoami >/dev/null 2>&1 || {
    warn "Not logged in to Railway"
    railway login
  }

  # Init project if needed
  if ! railway status >/dev/null 2>&1; then
    log "Creating Railway project..."
    railway init
  fi

  # Push all env vars
  log "Setting environment variables on Railway..."
  while IFS= read -r line; do
    [[ "$line" =~ ^[[:space:]]*# ]] && continue
    [[ -z "${line// }" ]] && continue
    key="${line%%=*}"
    value="${line#*=}"
    key=$(echo "$key" | xargs)
    [ -z "$key" ] && continue
    railway variables --set "$key=$value" 2>/dev/null || true
  done < .env

  # Inject ACP config (base64 encoded — no secrets in plain text)
  if [ -f "acp-seller/config.json" ]; then
    ACP_CONFIG_B64=$(base64 < acp-seller/config.json | tr -d '\n')
    railway variables --set "ACP_CONFIG_B64=$ACP_CONFIG_B64" 2>/dev/null || true
    log "ACP config injected (base64)"
  fi

  # Deploy
  log "Building and deploying..."
  railway up --detach

  echo ""
  echo -e "${GREEN}══════════════════════════════════════════════════${NC}"
  echo -e "${GREEN}  Deployed to Railway!${NC}"
  echo -e "${GREEN}══════════════════════════════════════════════════${NC}"
  echo ""
  echo -e "  ${BOLD}Next steps:${NC}"
  echo -e "  1. Add a persistent volume mounted at ${CYAN}/data${NC} in Railway dashboard"
  echo -e "  2. Your URL will appear in Railway once the build completes"
  echo -e "  3. Append ${CYAN}?token=$ENVTOKEN${NC} to access the dashboard"
  echo ""
fi
