<!doctype html>

<html lang="en">

<head>

  <meta charset="utf-8" />

  <title>CyberPatriot Leaderboard</title>

  <meta name="viewport" content="width=device-width,initial-scale=1" />

  <style>

    body { font-family: Inter, system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial; background: #0f172a; color: #e6eef8; margin: 0; padding: 24px; }

    .container { max-width: 960px; margin: 0 auto; }

    header { display:flex; align-items:center; justify-content:space-between; gap:12px; margin-bottom:16px; }

    h1 { font-size:1.4rem; margin:0; }

    .meta { color:#9fb3d8; font-size:0.9rem; }

    table { width:100%; border-collapse:collapse; background: linear-gradient(180deg, rgba(255,255,255,0.02), rgba(255,255,255,0.01)); border-radius:8px; overflow:hidden; }

    th, td { padding:10px 12px; text-align:left; font-size:0.95rem; }

    th { background: rgba(255,255,255,0.03); color:#cfe5ff; position:sticky; top:0; z-index:2; }

    tr { border-bottom:1px solid rgba(255,255,255,0.03); }

    tr:hover { background: rgba(255,255,255,0.02); }

    .rank { width:64px; font-weight:700; color:#ffd166; }

    .score { width:120px; text-align:right; font-weight:700; color:#9ae6b4; }

    .small { font-size:0.8rem; color:#9fb3d8; }

    .error { color:#ffb4b4; margin-top:12px; }

    .refresh { display:inline-flex; gap:8px; align-items:center; cursor:pointer; padding:6px 10px; border-radius:6px; background: rgba(255,255,255,0.02); border:1px solid rgba(255,255,255,0.02); color:#dff1ff; }

  </style>

</head>

<body>

  <div class="container">

    <header>

      <div>

        <h1>CyberPatriot Live Leaderboard</h1>

        <div class="meta">Auto-updates every minute • Source: scoreboard.uscyberpatriot.org</div>

      </div>

      <div>

        <button id="manualRefresh" class="refresh">Refresh now</button>

        <div id="lastUpdated" class="small" style="margin-top:6px; text-align:right;"></div>

      </div>

    </header>


    <main>

      <table id="leaderboard">

        <thead>

          <tr><th class="rank">#</th><th>Team</th><th>Team Number</th><th class="score">Score</th></tr>

        </thead>

        <tbody>

          <tr><td colspan="4" class="small">Loading…</td></tr>

        </tbody>

      </table>


      <div id="error" class="error" role="alert" style="display:none;"></div>

    </main>

  </div>


  <script>

    const API = '/api/teams'; // adjust if needed

    const tbody = document.querySelector('#leaderboard tbody');

    const lastUpdatedEl = document.getElementById('lastUpdated');

    const errorEl = document.getElementById('error');

    const manualRefresh = document.getElementById('manualRefresh');


    async function load() {

      errorEl.style.display = 'none';

      try {

        const resp = await fetch(API);

        if (!resp.ok) throw new Error('Network error: ' + resp.status);

        const json = await resp.json();

        render(json);

      } catch (e) {

        errorEl.style.display = 'block';

        errorEl.textContent = 'Failed to fetch leaderboard: ' + e.message;

        console.error(e);

      }

    }


    function render(data) {

      tbody.innerHTML = '';

      const teams = data.teams || [];

      if (!teams.length) {

        tbody.innerHTML = '<tr><td colspan="4" class="small">No teams found.</td></tr>';

      } else {

        teams.forEach((t, idx) => {

          const tr = document.createElement('tr');

          const rankTd = document.createElement('td'); rankTd.className='rank'; rankTd.textContent = idx + 1;

          const nameTd = document.createElement('td'); nameTd.textContent = t.name || (t.raw && t.raw.join(' | ')) || '-';

          const numTd = document.createElement('td'); numTd.textContent = t.teamNumber || '-';

          const scoreTd = document.createElement('td'); scoreTd.className='score'; scoreTd.textContent = (t.score !== null && t.score !== undefined) ? t.score : '-';


          tr.appendChild(rankTd);

          tr.appendChild(nameTd);

          tr.appendChild(numTd);

          tr.appendChild(scoreTd);

          tbody.appendChild(tr);

        });

      }


      lastUpdatedEl.textContent = 'Updated: ' + (data.updated ? new Date(data.updated).toLocaleString() : new Date().toLocaleString()) + ' • Teams: ' + (data.count || teams.length);

    }


    // initial load

    load();


    // update every minute (60,000 ms)

    const INTERVAL = 60 * 1000;

    setInterval(load, INTERVAL);


    manualRefresh.addEventListener('click', () => {

      load();

    });

  </script>

</body>

</html>