groups:
  - name: claudes_palace
    interval: 30s
    rules:
      # Battery cycling automation manages 15-80% range via HA + Tapo switch.
      # This alert is a safety net if the automation fails to turn on the charger.
      - alert: PalaceBatteryCritical
        expr: >
          node_power_supply_capacity{job="claudes-palace",power_supply="BAT0"} < 10
        for: 2m
        labels:
          severity: critical
        annotations:
          summary: "claudes-palace battery below 10% — charge automation may have failed"
          description: "Battery at {{ $value }}%. The HA charge cycling automation should have turned on the charger at 15%. Check switch.p110_claude and sensor.claudes_palace_battery_level in HA."

      - alert: PalaceGPUTempHigh
        expr: >
          nvidia_gpu_temp_celsius{job="claudes-palace"} > 85
        for: 5m
        labels:
          severity: high
        annotations:
          summary: "claudes-palace GPU temperature > 85°C"
          description: "GPU at {{ $value }}°C for 5+ minutes. Check thermal paste, airflow, or reduce GPU workload."

      - alert: PalaceHighCPU
        expr: >
          (1 - avg(rate(node_cpu_seconds_total{job="claudes-palace",mode="idle"}[5m]))) > 0.90
        for: 10m
        labels:
          severity: high
        annotations:
          summary: "claudes-palace CPU usage > 90% for 10+ minutes"
          description: "Sustained high CPU may indicate runaway process or thermal throttling."

      - alert: PalaceHighMemory
        expr: >
          (1 - node_memory_MemAvailable_bytes{job="claudes-palace"} / node_memory_MemTotal_bytes{job="claudes-palace"}) > 0.90
        for: 5m
        labels:
          severity: high
        annotations:
          summary: "claudes-palace memory usage > 90%"
          description: "Memory at {{ $value | humanizePercentage }}. May trigger OOM kills. Check Docker containers and Claude Code processes."

      - alert: PalaceDiskHigh
        expr: >
          (1 - node_filesystem_avail_bytes{job="claudes-palace",mountpoint="/"} / node_filesystem_size_bytes{job="claudes-palace",mountpoint="/"}) > 0.85
        for: 5m
        labels:
          severity: high
        annotations:
          summary: "claudes-palace root disk usage > 85%"
          description: "Disk at {{ $value | humanizePercentage }}. Clean up Docker images, logs, or /tmp."

      - alert: PalaceNodeExporterDown
        expr: up{job="claudes-palace"} == 0
        for: 5m
        labels:
          severity: critical
        annotations:
          summary: "claudes-palace node_exporter unreachable"
          description: "Cannot scrape metrics from claudes-palace (###_IP:9100) for 5+ minutes. Host may be down or network issue."

      - alert: PalaceBackupStale
        expr: >
          (time() - backup_last_success{job="claudes-palace"}) > 93600
          and backup_last_success{job="claudes-palace"} > 0
        for: 5m
        labels:
          severity: high
        annotations:
          summary: "claudes-palace backup older than 26 hours"
          description: "Last successful restic backup was more than 26 hours ago. Check NFS mount and backup cron."
