<template>
  <q-page padding class="tech-surface tech-diag-page">
    <div class="text-h6 q-mb-md">Diagnostic réseau</div>

    <!-- Speed test -->
    <q-card flat bordered class="q-mb-md">
      <q-card-section>
        <div class="text-subtitle2 q-mb-sm">Test de vitesse</div>
        <div v-if="speed !== null" class="text-center q-py-md">
          <div class="text-h3 text-primary text-weight-bold">{{ speed }}</div>
          <div class="text-caption text-grey">Mbps download</div>
          <div v-if="latency !== null" class="text-caption">Latence: {{ latency }}ms</div>
        </div>
        <q-btn unelevated color="primary" label="Lancer le test" icon="speed" class="full-width" @click="runSpeed" :loading="testing" />
      </q-card-section>
    </q-card>

    <!-- Host checks -->
    <q-card flat bordered>
      <q-card-section>
        <div class="text-subtitle2 q-mb-sm">Verification des hotes</div>
        <div v-for="h in hosts" :key="h.host" class="row items-center q-mb-xs">
          <q-icon :name="h.status === 'ok' ? 'check_circle' : h.status === 'fail' ? 'cancel' : 'radio_button_unchecked'"
            :color="h.status === 'ok' ? 'positive' : h.status === 'fail' ? 'negative' : 'grey'" class="q-mr-sm" />
          <span class="text-body2">{{ h.host }}</span>
          <q-space />
          <span v-if="h.ms" class="text-caption text-grey">{{ h.ms }}ms</span>
        </div>
        <q-btn flat color="primary" label="Verifier" icon="refresh" class="q-mt-sm" @click="checkHosts" :loading="checking" />
      </q-card-section>
    </q-card>
  </q-page>
</template>

<script setup>
import { ref } from 'vue'

const testing = ref(false)
const speed = ref(null)
const latency = ref(null)
const checking = ref(false)

// ─── Hosts to check ─────────────────────────────────────────────────────────
// We deliberately use 1.1.1.1 (not cloudflare.com) because the bare
// cloudflare.com redirects 301 → www.cloudflare.com, forcing a second DNS +
// TCP + TLS handshake on every "ping" and making the browser report
// 300–500ms on a 5ms link. 1.1.1.1/cdn-cgi/trace is a single no-redirect
// 88-byte response — the canonical "is the internet up" endpoint.
const hosts = ref([
  { host: 'google.ca', status: null, ms: null },
  { host: 'erp.gigafibre.ca', status: null, ms: null },
  { host: '1.1.1.1/cdn-cgi/trace', status: null, ms: null },
])

// ─── Speed test ─────────────────────────────────────────────────────────────
// Browser fetch() ≠ ICMP ping. A cold HTTPS request pays DNS + TCP + TLS +
// HTTP on top of the real RTT, which on mobile LTE is ~150–300ms before
// the first byte moves. We split this into two separate measurements:
//   1. Ping: warm-up + measured call against /cdn-cgi/trace (88 bytes),
//      so the second call runs on a warm connection and reports close to
//      real RTT.
//   2. Throughput: 10MB download on the SAME warm connection (same origin
//      → connection reuse, no second handshake tax).
async function runSpeed () {
  testing.value = true; speed.value = null; latency.value = null
  try {
    const pingUrl = 'https://speed.cloudflare.com/cdn-cgi/trace'
    // Warm-up — pays DNS + TCP + TLS so the next call is steady-state.
    await fetch(pingUrl, { mode: 'no-cors', cache: 'no-store' })
    // Measured ping on a warm connection.
    const p0 = performance.now()
    await fetch(pingUrl, { mode: 'no-cors', cache: 'no-store' })
    latency.value = Math.round(performance.now() - p0)

    // Throughput — 10MB download, same origin so TLS session is reused.
    const dlUrl = 'https://speed.cloudflare.com/__down?bytes=10000000'
    const t0 = performance.now()
    await fetch(dlUrl, { mode: 'no-cors' })
    const dlMs = performance.now() - t0
    speed.value = Math.round((10 * 8) / (dlMs / 1000))
  } catch {
    speed.value = 0
  } finally { testing.value = false }
}

// Warm-up + measure pattern so "cloudflare.com a répondu en 300ms" stops
// showing up for what is actually a 5ms link. First call absorbs the
// cold-connection penalty (DNS + TCP + TLS + LTE RRC wake); second call
// reports real RTT + HTTP round trip.
async function checkHosts () {
  checking.value = true
  for (const h of hosts.value) {
    try {
      // Warm-up — result discarded.
      await fetch('https://' + h.host, { mode: 'no-cors', signal: AbortSignal.timeout(5000) })
      // Measurement.
      const t0 = performance.now()
      await fetch('https://' + h.host, { mode: 'no-cors', signal: AbortSignal.timeout(5000) })
      h.ms = Math.round(performance.now() - t0)
      h.status = 'ok'
    } catch { h.status = 'fail'; h.ms = null }
  }
  checking.value = false
}
</script>
