<script setup lang="ts">
import { ref, computed, onMounted } from 'vue'
import { rpcClient } from '@/api/rpc-client'
import BackButton from '@/components/BackButton.vue'

interface ReleaseInfo {
  openwrt_release?: string
  openwrt_version?: string
  openwrt_board_name?: string
  openwrt_arch?: string
  openwrt_target?: string
}

interface WifiInterface {
  section: string
  ssid: string
  device: string
  encryption: string
  network: string
  disabled: boolean
}

interface TollGateStatus {
  installed: boolean
  enabled?: boolean
  metric?: string
  step_size_ms?: number
  price_per_step?: number
  min_steps?: number
  currency?: string
  mint_url?: string
}

interface WanStatus {
  configured: boolean
  ssid: string
  assoc_ssid: string
  encryption: string
  ip: string
  internet: boolean
  radio0_disabled: boolean
  sta_iface: string
  sta_state: string
  wifi_log: string
  lan_ip: string
  lan_netmask: string
  dhcp_start: string
  dhcp_limit: string
  masq: boolean
}

interface RouterStatus {
  host: string
  hostname: string
  uptime_secs: number
  release: ReleaseInfo
  tollgate: TollGateStatus
  wifi_interfaces: WifiInterface[]
  wan: WanStatus
}

interface ScannedNetwork {
  ssid: string
  bssid: string
  signal: number
  channel: number
  encryption: string
}

const status = ref<RouterStatus | null>(null)
const loading = ref(true)
const error = ref('')
const host = ref('')
const sshUser = ref('root')
const sshPassword = ref('')
const showConnectForm = ref(false)
const connecting = ref(false)
const connectedParams = ref<Record<string, string> | null>(null)

const detecting = ref(false)
const detectError = ref('')
const detectedCandidates = ref<string[]>([])

const provisioning = ref(false)
const provisionError = ref('')
const provisionSuccess = ref(false)

// TollGate reconfigure form (shown once installed)
const editingTollgate = ref(false)
const updatingTollgate = ref(false)
const updateTollgateError = ref('')
const editPriceSats = ref(10)
const editStepSizeMin = ref(1)
const editMinSteps = ref(1)
const editMintUrl = ref('')
const editEnabled = ref(true)

// WAN setup flow
type WanStep = 'idle' | 'scan' | 'scanning' | 'list' | 'password' | 'dhcp' | 'connecting' | 'done'
const wanStep = ref<WanStep>('idle')
const scannedNetworks = ref<ScannedNetwork[]>([])
const selectedNetwork = ref<ScannedNetwork | null>(null)
const wanPassword = ref('')
const wanError = ref('')

// DHCP/masq settings (step 3 of wizard)
const dhcpStart = ref(100)
const dhcpLimit = ref(150)
const masqEnabled = ref(true)

async function load(params?: Record<string, string>) {
  loading.value = true
  error.value = ''
  try {
    status.value = await rpcClient.call<RouterStatus>({
      method: 'openwrt.get-status',
      params: params ?? {},
      timeout: 30000,
    })
    showConnectForm.value = false
    if (params) connectedParams.value = params
  } catch (e) {
    const msg = e instanceof Error ? e.message : String(e)
    if (msg.includes('No router configured')) {
      showConnectForm.value = true
    } else {
      error.value = msg
    }
  } finally {
    loading.value = false
  }
}

async function connect() {
  if (!host.value.trim()) return
  connecting.value = true
  error.value = ''
  try {
    await load({ host: host.value.trim(), ssh_user: sshUser.value, ssh_password: sshPassword.value })
  } finally {
    connecting.value = false
  }
}

interface WiredInterface { name: string; type: string; state: string; ipv4: string[] }

async function detectRouter() {
  detecting.value = true
  detectError.value = ''
  detectedCandidates.value = []
  try {
    const { interfaces } = await rpcClient.call<{ interfaces: WiredInterface[] }>({
      method: 'network.list-interfaces',
      timeout: 10000,
    })
    const wired = interfaces.find(i => i.type === 'ethernet' && i.state === 'up' && i.ipv4.length > 0)
    if (!wired) {
      detectError.value = 'No active wired ethernet connection found on this node.'
      return
    }
    const [ip, prefixStr] = wired.ipv4[0]!.split('/')
    const prefix = Number(prefixStr) || 24

    const { routers } = await rpcClient.call<{ routers: string[] }>({
      method: 'openwrt.scan',
      params: { subnet: ip, prefix, ssh_user: sshUser.value, ssh_password: sshPassword.value },
      timeout: 120000,
    })

    if (routers.length === 0) {
      detectError.value = `No OpenWrt router found on ${wired.name}'s network (/${prefix}).`
    } else if (routers.length === 1) {
      host.value = routers[0]!
    } else {
      detectedCandidates.value = routers
    }
  } catch (e) {
    detectError.value = e instanceof Error ? e.message : String(e)
  } finally {
    detecting.value = false
  }
}

function pickDetectedRouter(ip: string) {
  host.value = ip
  detectedCandidates.value = []
}

// The router config now persists server-side (see handle_openwrt_get_status),
// so onMounted's no-args load() always reconnects automatically — without this,
// there'd be no way back to the connect form (and its Detect button) at all.
function disconnectRouter() {
  host.value = status.value?.host ?? host.value
  connectedParams.value = null
  detectError.value = ''
  detectedCandidates.value = []
  showConnectForm.value = true
}

async function provisionTollgate() {
  provisioning.value = true
  provisionError.value = ''
  provisionSuccess.value = false
  try {
    const params: Record<string, unknown> = {
      host: connectedParams.value?.host ?? status.value?.host,
      ssh_user: connectedParams.value?.ssh_user ?? sshUser.value,
      ssh_password: connectedParams.value?.ssh_password ?? sshPassword.value,
    }
    await rpcClient.call({ method: 'openwrt.provision-tollgate', params, timeout: 300000 })
    provisionSuccess.value = true
    await load(connectedParams.value ?? undefined)
  } catch (e) {
    provisionError.value = e instanceof Error ? e.message : String(e)
  } finally {
    provisioning.value = false
  }
}

function startEditTollgate() {
  const tg = status.value?.tollgate
  editPriceSats.value = tg?.price_per_step ?? 10
  editStepSizeMin.value = Math.max(1, Math.round((tg?.step_size_ms ?? 60000) / 60000))
  editMinSteps.value = tg?.min_steps ?? 1
  editMintUrl.value = tg?.mint_url ?? ''
  editEnabled.value = tg?.enabled ?? true
  updateTollgateError.value = ''
  editingTollgate.value = true
}

async function saveTollgateConfig() {
  updatingTollgate.value = true
  updateTollgateError.value = ''
  try {
    const params: Record<string, unknown> = {
      host: connectedParams.value?.host ?? status.value?.host,
      ssh_user: connectedParams.value?.ssh_user ?? sshUser.value,
      ssh_password: connectedParams.value?.ssh_password ?? sshPassword.value,
      price_sats: editPriceSats.value,
      step_size_ms: editStepSizeMin.value * 60_000,
      min_steps: editMinSteps.value,
      mint_url: editMintUrl.value,
      enabled: editEnabled.value,
    }
    await rpcClient.call({ method: 'openwrt.provision-tollgate', params, timeout: 300000 })
    editingTollgate.value = false
    await load(connectedParams.value ?? undefined)
  } catch (e) {
    updateTollgateError.value = e instanceof Error ? e.message : String(e)
  } finally {
    updatingTollgate.value = false
  }
}

function startWanSetup() {
  wanStep.value = 'scan'
  wanError.value = ''
  scannedNetworks.value = []
  selectedNetwork.value = null
  wanPassword.value = ''
  dhcpStart.value = Number(status.value?.wan?.dhcp_start) || 100
  dhcpLimit.value = Number(status.value?.wan?.dhcp_limit) || 150
  masqEnabled.value = true
}

async function scanWifi() {
  wanStep.value = 'scanning'
  wanError.value = ''
  try {
    const params: Record<string, unknown> = {
      host: connectedParams.value?.host ?? status.value?.host,
      ssh_user: connectedParams.value?.ssh_user ?? sshUser.value,
      ssh_password: connectedParams.value?.ssh_password ?? sshPassword.value,
    }
    const result = await rpcClient.call<{ networks: ScannedNetwork[] }>({
      method: 'openwrt.scan-wifi',
      params,
      timeout: 30000,
    })
    scannedNetworks.value = result.networks
    wanStep.value = 'list'
  } catch (e) {
    wanError.value = e instanceof Error ? e.message : String(e)
    wanStep.value = 'scan'
  }
}

function selectNetwork(net: ScannedNetwork) {
  selectedNetwork.value = net
  wanPassword.value = ''
  wanError.value = ''
  wanStep.value = 'password'
}

async function configureWan() {
  if (!selectedNetwork.value) return
  wanStep.value = 'connecting'
  wanError.value = ''
  try {
    const params: Record<string, unknown> = {
      host: connectedParams.value?.host ?? status.value?.host,
      ssh_user: connectedParams.value?.ssh_user ?? sshUser.value,
      ssh_password: connectedParams.value?.ssh_password ?? sshPassword.value,
      ssid: selectedNetwork.value.ssid,
      password: wanPassword.value,
      encryption: selectedNetwork.value.encryption,
      dhcp_start: dhcpStart.value,
      dhcp_limit: dhcpLimit.value,
      masq: masqEnabled.value,
    }
    await rpcClient.call({ method: 'openwrt.configure-wan', params, timeout: 30000 })
    wanStep.value = 'done'
    // Give the router ~8s to associate before reloading status
    setTimeout(() => {
      wanStep.value = 'idle'
      load(connectedParams.value ?? undefined)
    }, 8000)
  } catch (e) {
    wanError.value = e instanceof Error ? e.message : String(e)
    wanStep.value = 'dhcp'
  }
}

function signalBars(dbm: number): number {
  if (dbm >= -50) return 4
  if (dbm >= -65) return 3
  if (dbm >= -75) return 2
  return 1
}

function formatUptime(secs: number): string {
  const d = Math.floor(secs / 86400)
  const h = Math.floor((secs % 86400) / 3600)
  const m = Math.floor((secs % 3600) / 60)
  const parts = []
  if (d) parts.push(`${d}d`)
  if (h) parts.push(`${h}h`)
  parts.push(`${m}m`)
  return parts.join(' ')
}

function formatStepSize(ms: number): string {
  if (ms >= 3_600_000) return `${ms / 3_600_000}h`
  if (ms >= 60_000)    return `${ms / 60_000}m`
  if (ms >= 1_000)     return `${ms / 1_000}s`
  return `${ms}ms`
}

const openwrtVersion = computed(() => {
  if (!status.value) return ''
  const r = status.value.release
  return r.openwrt_release || r.openwrt_version || ''
})

const boardName = computed(() => {
  if (!status.value) return ''
  return status.value.release.openwrt_board_name || ''
})

onMounted(() => load())
</script>

<template>
  <div class="pb-6">
    <div class="flex items-center gap-3 mb-6">
      <BackButton />
      <h1 class="text-lg font-semibold text-white">OpenWrt Gateway</h1>
    </div>

    <!-- Connect form -->
    <div v-if="showConnectForm" class="glass-card p-6 mb-6">
      <h2 class="text-sm font-semibold text-white/80 mb-4">Connect to Router</h2>
      <div class="space-y-3">
        <div>
          <label class="block text-xs text-white/40 mb-1">Router IP</label>
          <div class="flex items-center gap-2">
            <input
              v-model="host"
              type="text"
              placeholder="192.168.1.1"
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 focus:ring-1 focus:ring-white/20 transition-colors"
            />
            <button
              :disabled="detecting"
              class="glass-button px-4 py-3 text-sm font-medium whitespace-nowrap flex-shrink-0"
              :class="detecting ? 'opacity-40 cursor-not-allowed' : ''"
              @click="detectRouter"
            >
              {{ detecting ? 'Detecting…' : 'Detect' }}
            </button>
          </div>
          <p v-if="detectError" class="mt-2 text-xs text-red-400">{{ detectError }}</p>
          <div v-if="detectedCandidates.length > 0" class="mt-2 space-y-1">
            <p class="text-xs text-white/40">Multiple routers found — pick one:</p>
            <button
              v-for="ip in detectedCandidates"
              :key="ip"
              class="w-full text-left px-3 py-2 bg-white/5 hover:bg-white/10 rounded-lg text-sm text-white font-mono transition-colors"
              @click="pickDetectedRouter(ip)"
            >
              {{ ip }}
            </button>
          </div>
        </div>
        <div class="grid grid-cols-2 gap-3">
          <div>
            <label class="block text-xs text-white/40 mb-1">SSH User</label>
            <input
              v-model="sshUser"
              type="text"
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white focus:outline-none focus:border-white/40 focus:ring-1 focus:ring-white/20 transition-colors"
            />
          </div>
          <div>
            <label class="block text-xs text-white/40 mb-1">Password</label>
            <input
              v-model="sshPassword"
              type="password"
              placeholder="(blank for none)"
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 focus:ring-1 focus:ring-white/20 transition-colors"
            />
          </div>
        </div>
        <button
          :disabled="connecting || !host.trim()"
          class="glass-button w-full text-sm font-medium"
          :class="connecting || !host.trim() ? 'opacity-40 cursor-not-allowed' : 'glass-button-warning'"
          @click="connect"
        >
          {{ connecting ? 'Connecting…' : 'Connect' }}
        </button>
      </div>
      <p v-if="error" class="mt-3 text-xs text-red-400">{{ error }}</p>
    </div>

    <!-- Loading skeleton -->
    <template v-else-if="loading">
      <div v-for="i in 3" :key="i" class="glass-card p-6 mb-4 animate-pulse">
        <div class="h-4 bg-white/10 rounded w-1/3 mb-4"></div>
        <div class="space-y-2">
          <div class="h-3 bg-white/10 rounded w-2/3"></div>
          <div class="h-3 bg-white/10 rounded w-1/2"></div>
        </div>
      </div>
    </template>

    <!-- Error state -->
    <div v-else-if="error" class="glass-card p-6 mb-4">
      <p class="text-sm text-red-300">{{ error }}</p>
      <button class="mt-3 text-xs text-white/50 hover:text-white transition-colors underline" @click="load()">Retry</button>
    </div>

    <!-- Status panels -->
    <template v-else-if="status">

      <!-- System info -->
      <div class="glass-card p-6 mb-4">
        <div class="flex items-center justify-between mb-4">
          <h2 class="text-sm font-semibold text-white/80">System</h2>
          <span class="flex items-center gap-1.5 text-xs text-green-400">
            <span class="w-1.5 h-1.5 rounded-full bg-green-400 inline-block"></span>
            Connected
          </span>
        </div>
        <dl class="grid grid-cols-2 gap-x-6 gap-y-3 text-sm">
          <div>
            <dt class="text-xs text-white/40 mb-0.5">Hostname</dt>
            <dd class="text-white font-medium">{{ status.hostname }}</dd>
          </div>
          <div>
            <dt class="text-xs text-white/40 mb-0.5">Address</dt>
            <dd class="text-white font-medium font-mono">{{ status.host }}</dd>
          </div>
          <div v-if="openwrtVersion">
            <dt class="text-xs text-white/40 mb-0.5">OpenWrt</dt>
            <dd class="text-white/70">{{ openwrtVersion }}</dd>
          </div>
          <div v-if="boardName">
            <dt class="text-xs text-white/40 mb-0.5">Board</dt>
            <dd class="text-white/70">{{ boardName }}</dd>
          </div>
          <div>
            <dt class="text-xs text-white/40 mb-0.5">Uptime</dt>
            <dd class="text-white/70">{{ formatUptime(status.uptime_secs) }}</dd>
          </div>
        </dl>
        <div class="mt-4 flex items-center gap-4">
          <button class="text-xs text-white/40 hover:text-white/70 transition-colors" @click="load()">
            ↻ Refresh
          </button>
          <button class="text-xs text-white/40 hover:text-white/70 transition-colors" @click="disconnectRouter">
            Switch router →
          </button>
        </div>
      </div>

      <!-- WAN / Uplink -->
      <div class="glass-card p-6 mb-4">
        <div class="flex items-center justify-between mb-4">
          <h2 class="text-sm font-semibold text-white/80">WAN / Uplink</h2>
          <button
            v-if="wanStep === 'idle' || wanStep === 'done'"
            class="text-xs text-white/40 hover:text-white transition-colors"
            @click="startWanSetup"
          >
            {{ status.wan?.configured ? 'Reconfigure →' : 'Set up →' }}
          </button>
        </div>

        <!-- Current status (idle) -->
        <template v-if="wanStep === 'idle' || wanStep === 'done'">
          <div v-if="status.wan?.configured" class="flex items-center gap-3 mb-3">
            <span class="w-2 h-2 rounded-full inline-block flex-shrink-0"
              :class="status.wan.internet ? 'bg-green-400' : 'bg-yellow-400 animate-pulse'"></span>
            <div>
              <div class="text-sm font-medium text-white">{{ status.wan.ssid }}</div>
              <div class="text-xs text-white/40">
                {{ status.wan.internet ? status.wan.ip : 'Connecting…' }}
              </div>
            </div>
          </div>
          <div v-else class="text-sm text-white/50 mb-3">
            Not configured — router has no internet access.
          </div>

          <!-- Quick summary of DHCP + masq when connected -->
          <dl v-if="status.wan?.configured && status.wan.internet"
              class="grid grid-cols-3 gap-x-4 gap-y-1 text-xs text-white/40 mb-3">
            <div>
              <dt class="text-white/25">LAN</dt>
              <dd class="text-white/60 font-mono">{{ status.wan.lan_ip }}/24</dd>
            </div>
            <div>
              <dt class="text-white/25">DHCP</dt>
              <dd class="text-white/60 font-mono">.{{ status.wan.dhcp_start }}+{{ status.wan.dhcp_limit }}</dd>
            </div>
            <div>
              <dt class="text-white/25">NAT</dt>
              <dd :class="status.wan.masq ? 'text-green-400' : 'text-red-400'">
                {{ status.wan.masq ? 'on' : 'off' }}
              </dd>
            </div>
          </dl>

          <!-- Diagnostics (shown when not connected) -->
          <dl v-if="status.wan?.configured && !status.wan.internet"
              class="grid grid-cols-2 gap-x-4 gap-y-2 text-xs mt-1 mb-3 border-t border-white/10 pt-3">
            <div>
              <dt class="text-white/30 mb-0.5">Radio</dt>
              <dd :class="status.wan.radio0_disabled ? 'text-red-400' : 'text-green-400'">
                {{ status.wan.radio0_disabled ? 'disabled' : 'enabled' }}
              </dd>
            </div>
            <div>
              <dt class="text-white/30 mb-0.5">Interface</dt>
              <dd class="text-white/70 font-mono">
                {{ status.wan.sta_iface || 'none' }}
                <span v-if="status.wan.sta_iface" class="ml-1"
                  :class="status.wan.sta_state === 'up' ? 'text-green-400' : 'text-yellow-400'">
                  ({{ status.wan.sta_state }})
                </span>
              </dd>
            </div>
            <div>
              <dt class="text-white/30 mb-0.5">Associated to</dt>
              <dd class="text-white/70">{{ status.wan.assoc_ssid || 'none' }}</dd>
            </div>
            <div>
              <dt class="text-white/30 mb-0.5">Configured SSID</dt>
              <dd class="text-white/70">{{ status.wan.ssid || '—' }}</dd>
            </div>
            <div v-if="status.wan.wifi_log" class="col-span-2">
              <dt class="text-white/30 mb-1">Recent wifi log</dt>
              <dd class="font-mono text-white/50 text-[10px] leading-relaxed whitespace-pre-wrap break-all bg-black/20 rounded p-2">{{ status.wan.wifi_log }}</dd>
            </div>
          </dl>

          <p v-if="wanStep === 'done'" class="mt-2 text-xs text-green-400">
            WAN configured. Router is connecting…
          </p>
        </template>

        <!-- Step: scan prompt -->
        <template v-else-if="wanStep === 'scan'">
          <button
            class="glass-button glass-button-warning w-full text-sm font-medium"
            @click="scanWifi"
          >
            Scan for Networks
          </button>
          <p v-if="wanError" class="mt-2 text-xs text-red-400">{{ wanError }}</p>
          <button class="mt-3 text-xs text-white/40 hover:text-white" @click="wanStep = 'idle'">Cancel</button>
        </template>

        <!-- Step: scanning -->
        <template v-else-if="wanStep === 'scanning'">
          <div class="flex items-center gap-3 py-2">
            <svg class="animate-spin w-4 h-4 text-white/50" fill="none" viewBox="0 0 24 24">
              <circle class="opacity-25" cx="12" cy="12" r="10" stroke="currentColor" stroke-width="4"/>
              <path class="opacity-75" fill="currentColor" d="M4 12a8 8 0 018-8v8z"/>
            </svg>
            <span class="text-sm text-white/50">Scanning for networks…</span>
          </div>
        </template>

        <!-- Step: network list -->
        <template v-else-if="wanStep === 'list'">
          <p class="text-xs text-white/40 mb-3">{{ scannedNetworks.length }} network{{ scannedNetworks.length !== 1 ? 's' : '' }} found. Select one:</p>
          <div v-if="scannedNetworks.length === 0" class="text-sm text-white/50">No networks found. Try scanning again.</div>
          <div class="space-y-1.5">
            <button
              v-for="net in scannedNetworks"
              :key="net.bssid"
              class="w-full flex items-center justify-between px-3 py-2.5 rounded-lg border border-white/10 hover:border-white/30 hover:bg-white/5 transition-colors text-left"
              @click="selectNetwork(net)"
            >
              <div class="flex items-center gap-2.5">
                <!-- Signal bars -->
                <div class="flex items-end gap-0.5 h-4">
                  <div v-for="b in 4" :key="b"
                    class="w-1 rounded-sm"
                    :class="[
                      b * 1 <= signalBars(net.signal) ? 'bg-white/70' : 'bg-white/15',
                      b === 1 ? 'h-1' : b === 2 ? 'h-2' : b === 3 ? 'h-3' : 'h-4'
                    ]"
                  ></div>
                </div>
                <span class="text-white text-sm">{{ net.ssid || '(hidden)' }}</span>
                <span v-if="net.encryption !== 'none'" class="text-white/30 text-xs">🔒</span>
              </div>
              <span class="text-xs text-white/30 font-mono flex-shrink-0">ch{{ net.channel }}</span>
            </button>
          </div>
          <button class="mt-3 text-xs text-white/40 hover:text-white" @click="wanStep = 'scan'">← Scan again</button>
        </template>

        <!-- Step: password entry -->
        <template v-else-if="wanStep === 'password'">
          <p class="text-sm text-white mb-3">
            Connect to <span class="font-semibold">{{ selectedNetwork?.ssid }}</span>
          </p>
          <input
            v-if="selectedNetwork?.encryption !== 'none'"
            v-model="wanPassword"
            type="password"
            placeholder="WiFi password"
            class="w-full px-4 py-3 mb-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 transition-colors"
            @keyup.enter="wanStep = 'dhcp'"
          />
          <div class="flex items-center gap-2">
            <button
              class="glass-button glass-button-success flex-1 text-sm font-medium"
              :disabled="selectedNetwork?.encryption !== 'none' && !wanPassword"
              :class="selectedNetwork?.encryption !== 'none' && !wanPassword ? 'opacity-40 cursor-not-allowed' : ''"
              @click="wanStep = 'dhcp'"
            >
              Next →
            </button>
            <button class="text-xs text-white/40 hover:text-white px-3 py-2" @click="wanStep = 'list'">←</button>
          </div>
          <p v-if="wanError" class="mt-2 text-xs text-red-400">{{ wanError }}</p>
        </template>

        <!-- Step: DHCP + masquerade config -->
        <template v-else-if="wanStep === 'dhcp'">
          <p class="text-xs text-white/50 mb-4">
            Configure how this router hands out addresses to WiFi clients.
          </p>

          <!-- LAN info -->
          <div class="mb-4 text-xs font-mono bg-black/20 rounded-lg px-3 py-2 text-white/50">
            <span class="text-white/30">LAN: </span>{{ status?.wan?.lan_ip || '192.168.1.1' }}/24
          </div>

          <!-- DHCP range -->
          <div class="mb-4">
            <label class="block text-xs text-white/40 mb-2">DHCP range for clients</label>
            <div class="flex items-center gap-2 text-sm">
              <span class="text-white/40 font-mono text-xs">{{ status?.wan?.lan_ip?.split('.').slice(0,3).join('.') || '192.168.1' }}.</span>
              <input
                v-model.number="dhcpStart"
                type="number"
                min="2" max="250"
                class="w-20 px-2 py-1.5 bg-transparent border border-white/20 rounded text-white text-sm text-center focus:outline-none focus:border-white/40"
              />
              <span class="text-white/30">–</span>
              <span class="text-white/60 font-mono text-xs">{{ Math.min(254, dhcpStart + dhcpLimit - 1) }}</span>
            </div>
            <p class="text-xs text-white/30 mt-1">{{ dhcpLimit }} addresses</p>
          </div>

          <!-- Masquerade -->
          <div class="flex items-center justify-between mb-4 py-3 border-t border-white/10">
            <div>
              <div class="text-sm text-white">Enable NAT masquerade</div>
              <div class="text-xs text-white/40">Routes LAN traffic through the WiFi uplink</div>
            </div>
            <button
              class="relative w-11 h-6 rounded-full transition-colors flex-shrink-0"
              :class="masqEnabled ? 'bg-green-500/60' : 'bg-white/15'"
              @click="masqEnabled = !masqEnabled"
            >
              <span
                class="absolute top-0.5 w-5 h-5 rounded-full bg-white transition-transform"
                :class="masqEnabled ? 'translate-x-5' : 'translate-x-0.5'"
              ></span>
            </button>
          </div>

          <p v-if="wanError" class="mb-3 text-xs text-red-400">{{ wanError }}</p>
          <div class="flex items-center gap-2">
            <button
              class="glass-button glass-button-success flex-1 text-sm font-medium"
              @click="configureWan"
            >
              Apply Settings
            </button>
            <button class="text-xs text-white/40 hover:text-white px-3 py-2" @click="wanStep = 'password'">←</button>
          </div>
        </template>

        <!-- Step: applying -->
        <template v-else-if="wanStep === 'connecting'">
          <div class="flex items-center gap-3 py-2">
            <svg class="animate-spin w-4 h-4 text-white/50" fill="none" viewBox="0 0 24 24">
              <circle class="opacity-25" cx="12" cy="12" r="10" stroke="currentColor" stroke-width="4"/>
              <path class="opacity-75" fill="currentColor" d="M4 12a8 8 0 018-8v8z"/>
            </svg>
            <span class="text-sm text-white/50">Applying WAN config…</span>
          </div>
        </template>
      </div>

      <!-- TollGate -->
      <div class="glass-card p-6 mb-4">
        <h2 class="text-sm font-semibold text-white/80 mb-4">TollGate</h2>

        <div v-if="!status.tollgate.installed">
          <div class="flex items-center gap-3 mb-4">
            <span class="w-2 h-2 rounded-full bg-white/20 inline-block"></span>
            <span class="text-sm text-white/50">Not installed</span>
          </div>
          <div v-if="!status.wan?.internet" class="mb-3 text-xs text-yellow-400/80 bg-yellow-400/10 rounded-lg px-3 py-2">
            Router needs internet access to install TollGate. Configure WAN above first.
          </div>
          <button
            :disabled="provisioning"
            class="glass-button glass-button-success w-full text-sm font-medium"
            :class="provisioning ? 'opacity-40 cursor-not-allowed' : ''"
            @click="provisionTollgate"
          >
            {{ provisioning ? 'Installing… this may take a few minutes' : 'Install TollGate' }}
          </button>
          <p v-if="provisionError" class="mt-3 text-xs text-red-400">{{ provisionError }}</p>
          <p v-if="provisionSuccess && !provisioning" class="mt-3 text-xs text-green-400">TollGate provisioned successfully.</p>
        </div>

        <template v-else-if="!editingTollgate">
          <div class="flex items-center justify-between mb-4">
            <div class="flex items-center gap-2">
              <span class="w-2 h-2 rounded-full inline-block"
                :class="status.tollgate.enabled ? 'bg-green-400' : 'bg-yellow-400'"></span>
              <span class="text-sm" :class="status.tollgate.enabled ? 'text-green-300' : 'text-yellow-300'">
                {{ status.tollgate.enabled ? 'Enabled' : 'Disabled' }}
              </span>
            </div>
            <button class="text-xs text-white/40 hover:text-white" @click="startEditTollgate">Edit</button>
          </div>
          <dl class="grid grid-cols-2 gap-x-6 gap-y-3 text-sm">
            <div>
              <dt class="text-xs text-white/40 mb-0.5">Price</dt>
              <dd class="text-white font-medium">
                {{ status.tollgate.price_per_step }} {{ status.tollgate.currency }}
                / {{ formatStepSize(status.tollgate.step_size_ms ?? 60000) }}
              </dd>
            </div>
            <div>
              <dt class="text-xs text-white/40 mb-0.5">Metric</dt>
              <dd class="text-white/70 capitalize">{{ status.tollgate.metric }}</dd>
            </div>
            <div class="col-span-2">
              <dt class="text-xs text-white/40 mb-0.5">Mint URL</dt>
              <dd class="text-white/70 font-mono text-xs break-all">{{ status.tollgate.mint_url }}</dd>
            </div>
          </dl>
        </template>

        <!-- Reconfigure form -->
        <template v-else>
          <div class="flex items-center justify-between mb-4 py-3 border-b border-white/10">
            <div>
              <div class="text-sm text-white">Enable TollGate</div>
              <div class="text-xs text-white/40">Stops the service and the SSID broadcast when off</div>
            </div>
            <button
              class="relative w-11 h-6 rounded-full transition-colors flex-shrink-0"
              :class="editEnabled ? 'bg-green-500/60' : 'bg-white/15'"
              @click="editEnabled = !editEnabled"
            >
              <span
                class="absolute top-0.5 w-5 h-5 rounded-full bg-white transition-transform"
                :class="editEnabled ? 'translate-x-5' : 'translate-x-0.5'"
              ></span>
            </button>
          </div>
          <div class="mb-4">
            <label class="block text-xs text-white/40 mb-2">Price per step (sats)</label>
            <input
              v-model.number="editPriceSats"
              type="number"
              min="1"
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 transition-colors"
            />
          </div>
          <div class="mb-4">
            <label class="block text-xs text-white/40 mb-2">Step size (minutes)</label>
            <input
              v-model.number="editStepSizeMin"
              type="number"
              min="1"
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 transition-colors"
            />
          </div>
          <div class="mb-4">
            <label class="block text-xs text-white/40 mb-2">Minimum steps per purchase</label>
            <input
              v-model.number="editMinSteps"
              type="number"
              min="1"
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 transition-colors"
            />
          </div>
          <div class="mb-4">
            <label class="block text-xs text-white/40 mb-2">Mint URL</label>
            <input
              v-model="editMintUrl"
              type="text"
              placeholder="http://..."
              class="w-full px-4 py-3 bg-transparent border border-white/20 rounded-lg text-white placeholder-white/30 focus:outline-none focus:border-white/40 transition-colors font-mono text-xs"
            />
          </div>
          <div class="flex items-center gap-2">
            <button
              :disabled="updatingTollgate"
              class="glass-button glass-button-success flex-1 text-sm font-medium"
              :class="updatingTollgate ? 'opacity-40 cursor-not-allowed' : ''"
              @click="saveTollgateConfig"
            >
              {{ updatingTollgate ? 'Saving…' : 'Save' }}
            </button>
            <button class="text-xs text-white/40 hover:text-white px-3 py-2" :disabled="updatingTollgate" @click="editingTollgate = false">
              Cancel
            </button>
          </div>
          <p v-if="updateTollgateError" class="mt-3 text-xs text-red-400">{{ updateTollgateError }}</p>
        </template>
      </div>

      <!-- WiFi interfaces -->
      <div class="glass-card p-6">
        <h2 class="text-sm font-semibold text-white/80 mb-4">
          WiFi Interfaces
          <span class="ml-2 text-xs font-normal text-white/40">(AP mode)</span>
        </h2>

        <div v-if="status.wifi_interfaces.length === 0" class="text-sm text-white/50">
          No AP interfaces configured.
        </div>

        <div
          v-for="iface in status.wifi_interfaces"
          :key="iface.section"
          class="flex items-start justify-between py-3 border-b border-white/10 last:border-0"
        >
          <div>
            <div class="flex items-center gap-2 mb-0.5">
              <span class="w-1.5 h-1.5 rounded-full inline-block"
                :class="iface.disabled ? 'bg-white/20' : 'bg-green-400'"></span>
              <span class="text-sm font-medium text-white">{{ iface.ssid || '(hidden)' }}</span>
              <span v-if="iface.network === 'tollgate'"
                class="text-xs px-1.5 py-0.5 rounded bg-blue-500/20 text-blue-300">TollGate</span>
            </div>
            <div class="text-xs text-white/40 ml-3.5">
              {{ iface.device }} · {{ iface.encryption === 'none' ? 'Open' : iface.encryption }}
            </div>
          </div>
          <span class="text-xs text-white/30 font-mono mt-0.5">{{ iface.section }}</span>
        </div>
      </div>

    </template>
  </div>
</template>
