import React, { memo, useMemo, useState } from "react";

function prettyJson(text) {
  if (!text) return "—";
  try {
    return JSON.stringify(JSON.parse(text), null, 2);
  } catch {
    return text;
  }
}

function ApiTraceTab({
  hasSelectedTask,
  selectedTaskName,
  apiTraceLogs,
  formatTimestamp,
  clearApiTrace,
  exportApiTraceJson,
  exportApiTraceCsv
}) {
  const [search, setSearch] = useState("");
  const query = String(search || "").trim().toLowerCase();
  const allRows = Array.isArray(apiTraceLogs) ? apiTraceLogs : [];

  const rows = useMemo(() => {
    if (!query) return allRows;
    return allRows.filter((item) => {
      const hay = [
        item.method,
        item.phone,
        item.errorText,
        item.requestJson,
        item.responseJson
      ].map((part) => String(part || "").toLowerCase()).join(" ");
      return hay.includes(query);
    });
  }, [allRows, query]);

  const okCount = rows.filter((item) => item.ok).length;
  const failCount = rows.length - okCount;
  const inviteRows = allRows.filter((item) => item.method === "channels.InviteToChannel");
  const inviteTotal = inviteRows.length;
  const inviteMissing = inviteRows.filter((item) => {
    const response = String(item.responseJson || "");
    return response.includes("missingInvitees") || response.includes("missing_invitees");
  }).length;
  const inviteRpcError = inviteRows.filter((item) => !item.ok || String(item.errorText || "").trim()).length;
  const inviteOkNoMissing = Math.max(0, inviteTotal - inviteMissing - inviteRpcError);

  return (
    <section className="card">
      <div className="row-header">
        <h3>API трассировка</h3>
        <div className="actions">
          <button
            type="button"
            className="secondary"
            onClick={() => exportApiTraceJson()}
          >
            Экспорт JSON
          </button>
          <button
            type="button"
            className="secondary"
            onClick={() => exportApiTraceCsv()}
          >
            Экспорт CSV
          </button>
          <button
            type="button"
            className="secondary"
            onClick={() => clearApiTrace()}
          >
            Очистить трассировку
          </button>
        </div>
      </div>
      <div className="hint">
        Задача: {hasSelectedTask ? selectedTaskName : "—"}.
        Для Telegram MTProto HTTP‑headers отсутствуют, поэтому в лог пишется транспортный контекст.
      </div>
      <div className="inline-controls">
        <input
          className="text-input"
          value={search}
          onChange={(event) => setSearch(event.target.value)}
          placeholder="Поиск по методу / ошибке / JSON"
        />
        <span className="status-caption">Всего: {rows.length}</span>
        <span className="status-caption ok">OK: {okCount}</span>
        <span className="status-caption warn">Ошибок: {failCount}</span>
      </div>
      <div className="inline-controls">
        <span className="status-caption">InviteToChannel: {inviteTotal}</span>
        <span className="status-caption warn">missing_invitees: {inviteMissing}</span>
        <span className="status-caption ok">без missing: {inviteOkNoMissing}</span>
        <span className="status-caption">RPC errors: {inviteRpcError}</span>
      </div>
      <div className="api-trace-list">
        {!rows.length && <div className="empty">Трассировка пуста.</div>}
        {rows.map((item) => (
          <details key={item.id} className={`api-trace-item ${item.ok ? "success" : "error"}`} open={false}>
            <summary>
              <div className="api-trace-head">
                <strong>{item.method || "unknown"}</strong>
                <span className="status-caption">{formatTimestamp(item.createdAt)}</span>
              </div>
              <div className="api-trace-body">
                <div>Аккаунт: {item.phone || item.accountId || "—"}</div>
                <div>Задача: {item.taskId || "—"} · {item.ok ? "OK" : "Ошибка"} · {item.durationMs || 0} ms</div>
                {!item.ok && <div>Ошибка: {item.errorText || "—"}</div>}
              </div>
            </summary>
            <div className="api-trace-details">
              <div>
                <strong>Запрос (JSON)</strong>
                <pre>{prettyJson(item.requestJson)}</pre>
              </div>
              <div>
                <strong>Заголовки / контекст</strong>
                <pre>{prettyJson(item.headersJson)}</pre>
              </div>
              <div>
                <strong>Ответ (JSON)</strong>
                <pre>{prettyJson(item.responseJson)}</pre>
              </div>
            </div>
          </details>
        ))}
      </div>
    </section>
  );
}

export default memo(ApiTraceTab);
