// RiftUptime.jsx — живий статус інфраструктури з UptimeRobot (read-only ключ).
// Група RIVNE. Якщо API недоступний (CORS/офлайн) — показуємо знімок-фолбек.

const UPTIME_API_KEY = 'ur822371-c49c8751cf8351f844ebffc6';

function useUptime() {
  const [state, setState] = React.useState({ loading: true, monitors: null, error: false });
  React.useEffect(() => {
    let alive = true;
    // "simple" request (form-urlencoded, no custom headers) → no CORS preflight
    const body = 'api_key=' + encodeURIComponent(UPTIME_API_KEY) +
      '&format=json&logs=0&custom_uptime_ratios=1-7-30-90';
    fetch('https://api.uptimerobot.com/v2/getMonitors', {
      method: 'POST',
      headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
      body,
    })
      .then(r => r.json())
      .then(d => {
        if (!alive) return;
        if (d && d.stat === 'ok' && Array.isArray(d.monitors)) {
          setState({ loading: false, monitors: d.monitors, error: false });
        } else {
          setState({ loading: false, monitors: null, error: true });
        }
      })
      .catch(() => { if (alive) setState({ loading: false, monitors: null, error: true }); });
    return () => { alive = false; };
  }, []);
  return state;
}
window.useUptime = useUptime;

const ratio90 = (m) => {
  const parts = String(m.custom_uptime_ratio || '').split('-');
  const v = parseFloat(parts[3] != null ? parts[3] : parts[0]);
  return isNaN(v) ? null : v;
};

// UptimeRobot status: 0 paused · 1 not checked yet · 2 up · 8 seems down · 9 down
const classify = (m) => {
  if (m.status === 8 || m.status === 9) return 'down';
  if (m.status === 2) return 'up';
  if (m.status === 1) { const r = ratio90(m); return (r != null && r >= 99) ? 'up' : 'pending'; }
  return 'pending';
};

// fb = { live, uptime, cap, cells } — статичний фолбек кожної сторінки
const LiveStatus = ({ lang, fb }) => {
  const { loading, monitors, error } = useUptime();
  const L = (uk, en) => (lang === 'uk' ? uk : en);

  // Сфера віджета — інфраструктура реєстру/DNS (без панелі білінгу, винесеної за межі сайту)
  const active = (monitors || []).filter(m =>
    m.status !== 0 && !/bill/i.test((m.friendly_name || '') + ' ' + (m.url || '')));
  const haveLive = !loading && !error && active.length > 0;
  const anyDown = active.some(m => classify(m) === 'down');
  const upAll = haveLive && !anyDown;
  const ratios = active.map(ratio90).filter(n => n != null);
  const avg90 = ratios.length ? ratios.reduce((a, b) => a + b, 0) / ratios.length : null;

  const big = haveLive && avg90 != null ? avg90.toFixed(2) + '%' : fb.uptime;
  const liveLabel = haveLive
    ? (upAll ? L('Усі системи в нормі', 'All systems operational') : L('Виявлено інцидент', 'Incident detected'))
    : fb.live;
  const cap = haveLive ? L('середня доступність DNS за 90 днів', 'average DNS availability over 90 days') : fb.cap;

  const isDown = (m) => classify(m) === 'down';
  const avgOf = (arr) => { const rs = arr.map(ratio90).filter(n => n != null); return rs.length ? rs.reduce((a, b) => a + b, 0) / rs.length : null; };

  // Агрегуємо у загальні категорії — без переліку конкретних серверів,
  // щоб зміна неймсерверів не вимагала правок сайту.
  const dns = active.filter(m => /^DNS\b/i.test(m.friendly_name || '') || m.type === 6);
  const soa = active.filter(m => /SOA/i.test(m.friendly_name || '') || m.type === 5);
  const dnsUp = dns.filter(m => !isDown(m)).length;
  const dnsAvg = avgOf(dns);
  const soaOk = soa.length > 0 && soa.every(m => !isDown(m));

  let liveCells = [];
  if (dns.length) liveCells.push({
    n: String(dns.length), dot: dns.some(isDown) ? 'down' : 'up',
    l: L('глобальних сервісів DNS', 'global DNS services'),
    sub: (dnsAvg != null ? dnsAvg.toFixed(2) + '%' : '') + L(' · 90 днів', ' · 90 days'),
  });
  if (soa.length) liveCells.push({
    n: soaOk ? L('Норма', 'OK') : '!', dot: soa.some(isDown) ? 'down' : 'up',
    l: L('цілісність зон (SOA)', 'zone integrity (SOA)'), sub: 'rivne.ua · rv.ua',
  });
  const staticFacts = [
    { n: 'DNSSEC', l: L('підпис усіх зон', 'all zones signed'), sub: L('з 2012', 'since 2012') },
    { n: 'IPv4 / IPv6', l: L('подвійний стек', 'dual stack'), sub: 'dual-stack' },
    { n: '24/7', l: L('моніторинг', 'monitoring'), sub: 'UptimeRobot' },
  ];
  while (liveCells.length < 4 && staticFacts.length) liveCells.push(staticFacts.shift());
  liveCells = liveCells.slice(0, 4);

  return (
    <React.Fragment>
      <div className="rift-status">
        <div className="rift-status__live">
          <span className="rift-status__pulse" data-down={haveLive && !upAll ? '1' : undefined}>
            <span className="dot" />{liveLabel}
          </span>
          <div className="rift-status__big">{big}</div>
          <div className="rift-status__cap">{cap}</div>
          <a className="rift-status__attr" href="https://uptimerobot.com" target="_blank" rel="noopener noreferrer">
            {L('дані згідно uptimerobot.com', 'data via uptimerobot.com')}
          </a>
        </div>
        <div className="rift-status__grid">
          {(haveLive ? liveCells : fb.cells).map((c, i) => (
            <div className="rift-statc" key={i}>
              <div className={`rift-statc__n ${c.dot ? 'rift-mon__n' : ''}`}>
                {c.dot ? <span className={`rift-mon__dot is-${c.dot}`}></span> : null}
                {c.n}
              </div>
              <div className="rift-statc__l">{c.l}</div>
              <div className="rift-statc__sub">{c.sub}</div>
            </div>
          ))}
        </div>
      </div>
      <p className="rift-status__src">
        {loading
          ? L('● Підключення до моніторингу UptimeRobot…', '● Connecting to UptimeRobot monitoring…')
          : haveLive
            ? L('● Моніторинг у реальному часі · UptimeRobot · група RIVNE', '● Live monitoring · UptimeRobot · RIVNE group')
            : L('○ Показники зі знімка (моніторинг тимчасово недоступний)', '○ Snapshot metrics (monitoring temporarily unavailable)')}
      </p>
    </React.Fragment>
  );
};
window.LiveStatus = LiveStatus;
