import { useEffect, useMemo, useRef, useState } from "react";
import { writeClipboardText } from "../browser/clipboard";
import {
  AVAILABLE_REGEX_FLAVOURS,
  defaultRegexOptions,
} from "../regex/flavours/flavour-registry";
import { ComparisonOrchestrator } from "../regex/comparison/ComparisonOrchestrator";
import type {
  ComparisonFlavour,
  ComparisonPatternModel,
  RegexComparisonResult,
} from "../regex/comparison/comparison.types";
import {
  generatePcre2C,
  type GeneratedPcre2CProgram,
} from "../regex/codegen/pcre2-c";
import {
  DEFAULT_REGEX_LIMITS,
  utf8ByteLength,
} from "../regex/execution/request-limits";
import type {
  RegexEngineOptions,
  RegexFlavourId,
} from "../regex/model/flavour";
import "./ComparisonCodePanel.css";

const ECMASCRIPT = AVAILABLE_REGEX_FLAVOURS.require("ecmascript");
const PCRE2 = AVAILABLE_REGEX_FLAVOURS.require("pcre2");
const MAXIMUM_RENDERED_DIFFERENCES = 250;
const MAXIMUM_RENDERED_ALIGNMENTS = 100;

type PanelTab = "compare" | "code";
type PanelStatus =
  | { readonly kind: "idle"; readonly message: string }
  | { readonly kind: "running"; readonly message: string }
  | { readonly kind: "ready"; readonly message: string }
  | { readonly kind: "error"; readonly message: string };

export interface ComparisonCodePanelProps {
  readonly activeFlavour: RegexFlavourId;
  readonly activeFlags: readonly string[];
  readonly activeOptions: RegexEngineOptions;
  readonly pattern: string;
  readonly subject: string;
  readonly replacement: string;
  readonly scanAll: boolean;
  readonly timeoutMs: number;
  readonly onClose: () => void;
}

function initialFlags(
  activeFlavour: RegexFlavourId,
  activeFlags: readonly string[],
  flavour: ComparisonFlavour,
): readonly string[] {
  const definition = flavour === "ecmascript" ? ECMASCRIPT : PCRE2;
  return activeFlavour === flavour
    ? definition.flags
        .map((flag) => flag.value)
        .filter((flag) => activeFlags.includes(flag))
    : definition.defaultFlags;
}

function initialOptions(
  activeFlavour: RegexFlavourId,
  activeOptions: RegexEngineOptions,
): RegexEngineOptions {
  return activeFlavour === "pcre2" ? activeOptions : defaultRegexOptions(PCRE2);
}

function toggleFlag(
  current: readonly string[],
  flag: string,
  enabled: boolean,
  flavour: ComparisonFlavour,
): readonly string[] {
  const definition = flavour === "ecmascript" ? ECMASCRIPT : PCRE2;
  const selected = new Set(current);
  if (enabled) {
    selected.add(flag);
    for (const group of definition.mutuallyExclusiveFlags ?? []) {
      if (!group.includes(flag)) continue;
      for (const incompatible of group) {
        if (incompatible !== flag) selected.delete(incompatible);
      }
    }
  } else {
    selected.delete(flag);
  }
  return definition.flags
    .map((candidate) => candidate.value)
    .filter((candidate) => selected.has(candidate));
}

function preview(value: string | undefined, maximum = 240): string {
  if (value === undefined) return "—";
  return value.length <= maximum
    ? value
    : `${value.slice(0, maximum)}… (${value.length.toLocaleString()} UTF-16 units)`;
}

function downloadSource(program: GeneratedPcre2CProgram): void {
  const url = URL.createObjectURL(
    new Blob([program.source], { type: "text/x-c;charset=utf-8" }),
  );
  const anchor = document.createElement("a");
  anchor.href = url;
  anchor.download = program.fileName;
  anchor.click();
  window.setTimeout(() => URL.revokeObjectURL(url), 1_000);
}

function engineExecution(result: RegexComparisonResult["sides"][number]) {
  return result.runtime.replacement?.execution ?? result.runtime.execution;
}

function SideResult({
  side,
}: {
  readonly side: RegexComparisonResult["sides"][number];
}) {
  const execution = engineExecution(side);
  const diagnostics = [
    ...(side.syntax.pattern?.diagnostics ?? []),
    ...(side.syntax.replacement?.diagnostics ?? []),
    ...(execution?.diagnostics ?? []),
  ];
  return (
    <article className="comparison-side-card">
      <header>
        <div>
          <p className="eyebrow">Exact request {side.requestIdentity}</p>
          <h4>
            {side.input.flavour === "ecmascript" ? "ECMAScript" : "PCRE2"}
          </h4>
        </div>
        <span className={`status status-${side.runtime.status}`}>
          {side.runtime.status}
        </span>
      </header>
      <dl>
        <div>
          <dt>Pattern syntax</dt>
          <dd>
            {side.syntax.pattern
              ? side.syntax.pattern.accepted
                ? "Accepted"
                : "Rejected"
              : side.syntax.status}
          </dd>
        </div>
        <div>
          <dt>Provider</dt>
          <dd>
            {side.syntax.pattern
              ? `${side.syntax.pattern.provider.id} ${side.syntax.pattern.provider.version}`
              : "Unavailable"}
          </dd>
        </div>
        <div>
          <dt>Engine compile</dt>
          <dd>
            {execution
              ? execution.accepted
                ? "Accepted"
                : "Rejected"
              : side.runtime.status}
          </dd>
        </div>
        <div>
          <dt>Engine identity</dt>
          <dd>
            {execution
              ? `${execution.engine.engineName} · ${execution.engine.engineVersion}`
              : "Unavailable"}
          </dd>
        </div>
        <div>
          <dt>Exact flags</dt>
          <dd>
            user {side.input.flags.join("") || "none"} · effective{" "}
            {execution?.flags.effectiveFlags || "unavailable"}
          </dd>
        </div>
        <div>
          <dt>Options</dt>
          <dd>
            <code>{JSON.stringify(side.input.options)}</code>
          </dd>
        </div>
        <div>
          <dt>Matches</dt>
          <dd>{execution?.matches.length.toLocaleString() ?? "Unavailable"}</dd>
        </div>
        <div>
          <dt>Offsets</dt>
          <dd>
            native {execution?.engine.offsetUnit ?? "unavailable"} · comparison
            UTF-16
          </dd>
        </div>
        {side.runtime.replacement ? (
          <div>
            <dt>Replacement</dt>
            <dd>
              {side.runtime.replacement.outputBytes.toLocaleString()} bytes
              {side.runtime.replacement.truncated ? " · incomplete" : ""}
            </dd>
          </div>
        ) : null}
      </dl>
      {side.syntax.pattern?.coverage.unsupportedConstructs.length ? (
        <details>
          <summary>Provider coverage gaps</summary>
          <ul>
            {side.syntax.pattern.coverage.unsupportedConstructs.map((gap) => (
              <li key={gap}>{gap}</li>
            ))}
          </ul>
        </details>
      ) : null}
      {diagnostics.length > 0 ? (
        <details>
          <summary>{diagnostics.length.toLocaleString()} diagnostic(s)</summary>
          <ul>
            {diagnostics.slice(0, 100).map((diagnostic) => (
              <li key={`${diagnostic.source}-${diagnostic.id}`}>
                <strong>{diagnostic.severity}:</strong> {diagnostic.message}
              </li>
            ))}
          </ul>
        </details>
      ) : null}
      {side.syntax.error || side.runtime.error ? (
        <p className="comparison-error">
          {side.syntax.error ?? side.runtime.error}
        </p>
      ) : null}
    </article>
  );
}

function ComparisonResultView({
  result,
}: {
  readonly result: RegexComparisonResult;
}) {
  const visibleDifferences = result.differences.slice(
    0,
    MAXIMUM_RENDERED_DIFFERENCES,
  );
  const visibleAlignments = result.matchAlignments.slice(
    0,
    MAXIMUM_RENDERED_ALIGNMENTS,
  );
  return (
    <div className="comparison-result" aria-live="polite">
      <section className={`comparison-verdict verdict-${result.status}`}>
        <p className="eyebrow">Bounded comparison verdict</p>
        <h3>{result.status.replaceAll("-", " ")}</h3>
        <p>{result.notices[0]?.message}</p>
        <small>
          {result.elapsedMs.toFixed(1)} ms wall time ·{" "}
          {result.totalDifferences.toLocaleString()} recorded difference(s)
        </small>
      </section>
      {result.notComparable.length > 0 ? (
        <section className="comparison-reasons">
          <h4>Why this run is not comparable</h4>
          <ul>
            {result.notComparable.map((reason, index) => (
              <li key={`${reason.code}-${reason.flavour ?? "both"}-${index}`}>
                <strong>{reason.code.replaceAll("-", " ")}:</strong>{" "}
                {reason.message}
              </li>
            ))}
          </ul>
        </section>
      ) : null}
      <div className="comparison-side-grid">
        <SideResult side={result.sides[0]} />
        <SideResult side={result.sides[1]} />
      </div>
      <section className="comparison-differences">
        <h4>Syntax, execution and replacement differences</h4>
        {visibleDifferences.length === 0 ? (
          <p>
            No retained semantic differences for this subject. Engine metadata
            can still differ.
          </p>
        ) : (
          <table>
            <thead>
              <tr>
                <th>Kind</th>
                <th>Finding</th>
                <th>ECMAScript</th>
                <th>PCRE2</th>
              </tr>
            </thead>
            <tbody>
              {visibleDifferences.map((difference, index) => (
                <tr key={`${difference.kind}-${index}`}>
                  <td>{difference.kind.replaceAll("-", " ")}</td>
                  <td>{difference.summary}</td>
                  <td>
                    <code>{preview(difference.left)}</code>
                  </td>
                  <td>
                    <code>{preview(difference.right)}</code>
                  </td>
                </tr>
              ))}
            </tbody>
          </table>
        )}
        {visibleDifferences.length < result.totalDifferences ? (
          <p className="comparison-limit-note">
            Rendering the first {visibleDifferences.length.toLocaleString()} of{" "}
            {result.totalDifferences.toLocaleString()} differences.
          </p>
        ) : null}
      </section>
      {visibleAlignments.length > 0 ? (
        <section className="comparison-alignments">
          <h4>Match alignment by normalized editor range</h4>
          <table>
            <thead>
              <tr>
                <th>Alignment</th>
                <th>ECMAScript UTF-16</th>
                <th>PCRE2 UTF-16</th>
                <th>Equal</th>
              </tr>
            </thead>
            <tbody>
              {visibleAlignments.map((alignment, index) => (
                <tr key={`${alignment.alignment}-${index}`}>
                  <td>{alignment.alignment.replaceAll("-", " ")}</td>
                  <td>
                    {alignment.left
                      ? `${alignment.left.range.startUtf16}–${alignment.left.range.endUtf16}`
                      : "—"}
                  </td>
                  <td>
                    {alignment.right
                      ? `${alignment.right.range.startUtf16}–${alignment.right.range.endUtf16}`
                      : "—"}
                  </td>
                  <td>{alignment.equal ? "yes" : "no"}</td>
                </tr>
              ))}
            </tbody>
          </table>
          {visibleAlignments.length < result.totalMatchAlignments ? (
            <p className="comparison-limit-note">
              Rendering the first {visibleAlignments.length.toLocaleString()} of{" "}
              {result.totalMatchAlignments.toLocaleString()} alignments.
            </p>
          ) : null}
        </section>
      ) : null}
    </div>
  );
}

export function ComparisonCodePanel({
  activeFlavour,
  activeFlags,
  activeOptions,
  pattern: initialPattern,
  subject: initialSubject,
  replacement: initialReplacement,
  scanAll: initialScanAll,
  timeoutMs: initialTimeoutMs,
  onClose,
}: ComparisonCodePanelProps) {
  const [tab, setTab] = useState<PanelTab>("compare");
  const [patternModel, setPatternModel] =
    useState<ComparisonPatternModel>("shared");
  const [sharedPattern, setSharedPattern] = useState(initialPattern);
  const [ecmaPattern, setEcmaPattern] = useState(initialPattern);
  const [pcrePattern, setPcrePattern] = useState(initialPattern);
  const [subject, setSubject] = useState(initialSubject);
  const [operation, setOperation] = useState<"match" | "replace">("match");
  const [ecmaReplacement, setEcmaReplacement] = useState(initialReplacement);
  const [pcreReplacement, setPcreReplacement] = useState(initialReplacement);
  const [ecmaFlags, setEcmaFlags] = useState(() =>
    initialFlags(activeFlavour, activeFlags, "ecmascript"),
  );
  const [pcreFlags, setPcreFlags] = useState(() =>
    initialFlags(activeFlavour, activeFlags, "pcre2"),
  );
  const [pcreOptions, setPcreOptions] = useState(() =>
    initialOptions(activeFlavour, activeOptions),
  );
  const [scanAll, setScanAll] = useState(initialScanAll);
  const [timeoutMs, setTimeoutMs] = useState(initialTimeoutMs);
  const [maximumMatches, setMaximumMatches] = useState(1_000);
  const [maximumCaptureRows, setMaximumCaptureRows] = useState(10_000);
  const [maximumOutputBytes, setMaximumOutputBytes] = useState(1024 * 1024);
  const [status, setStatus] = useState<PanelStatus>({
    kind: "idle",
    message: "Configure two exact engine requests.",
  });
  const [result, setResult] = useState<RegexComparisonResult>();
  const [generated, setGenerated] = useState<GeneratedPcre2CProgram>();
  const [generatedStatus, setGeneratedStatus] = useState("");
  const orchestrator = useRef<ComparisonOrchestrator | undefined>(undefined);
  const comparisonRevision = useRef(0);

  useEffect(
    () => () => {
      comparisonRevision.current += 1;
      orchestrator.current?.dispose();
      orchestrator.current = undefined;
    },
    [],
  );

  const pcreOptionValues = useMemo(
    () => ({
      matchLimit: Number(pcreOptions.matchLimit),
      depthLimit: Number(pcreOptions.depthLimit),
      heapLimitKib: Number(pcreOptions.heapLimitKib),
    }),
    [pcreOptions],
  );

  const compare = async () => {
    const revision = ++comparisonRevision.current;
    setResult(undefined);
    setStatus({
      kind: "running",
      message: "Running independently killable ECMAScript and PCRE2 workers…",
    });
    try {
      orchestrator.current ??= new ComparisonOrchestrator();
      const comparison = await orchestrator.current.compare({
        schemaVersion: 1,
        patternModel,
        operation,
        subject,
        scanAll,
        maximumMatches,
        maximumCaptureRows,
        maximumOutputBytes,
        timeoutMs,
        sides: [
          {
            flavour: "ecmascript",
            flavourVersion: ECMASCRIPT.defaultVersion,
            pattern: patternModel === "shared" ? sharedPattern : ecmaPattern,
            flags: ecmaFlags,
            options: {},
            ...(operation === "replace"
              ? { replacement: ecmaReplacement }
              : {}),
          },
          {
            flavour: "pcre2",
            flavourVersion: PCRE2.defaultVersion,
            pattern: patternModel === "shared" ? sharedPattern : pcrePattern,
            flags: pcreFlags,
            options: pcreOptionValues,
            ...(operation === "replace"
              ? { replacement: pcreReplacement }
              : {}),
          },
        ],
      });
      if (revision !== comparisonRevision.current) return;
      setResult(comparison);
      setStatus({
        kind: "ready",
        message:
          comparison.status === "not-comparable"
            ? "Both side outcomes are retained; equivalence is not claimed."
            : "Both exact requests completed.",
      });
    } catch (error) {
      if (revision !== comparisonRevision.current) return;
      setStatus({
        kind: "error",
        message: error instanceof Error ? error.message : String(error),
      });
    }
  };

  const cancel = () => {
    comparisonRevision.current += 1;
    orchestrator.current?.cancel();
    setStatus({
      kind: "idle",
      message: "Comparison cancelled; both active workers were terminated.",
    });
  };

  const generate = () => {
    setGenerated(undefined);
    setGeneratedStatus("");
    try {
      const program = generatePcre2C({
        flavour: "pcre2",
        flavourVersion: PCRE2.defaultVersion,
        operation,
        pattern: patternModel === "shared" ? sharedPattern : pcrePattern,
        flags: pcreFlags,
        options: pcreOptionValues,
        subject,
        scanAll,
        ...(operation === "replace" ? { replacement: pcreReplacement } : {}),
        maximumMatches,
        maximumCaptureRows,
        maximumOutputBytes,
      });
      setGenerated(program);
      setGeneratedStatus(
        "Generated locally from the exact PCRE2 snapshot shown above.",
      );
    } catch (error) {
      setGeneratedStatus(
        error instanceof Error ? error.message : String(error),
      );
    }
  };

  const setPcreOption = (name: string, value: number) => {
    setPcreOptions((current) => ({ ...current, [name]: value }));
  };

  return (
    <section
      className="panel comparison-code-panel"
      aria-labelledby="comparison-code-heading"
    >
      <header className="panel-heading">
        <div>
          <p className="eyebrow">Evidence, not automatic translation</p>
          <h2 id="comparison-code-heading">Compare &amp; generate</h2>
        </div>
        <button
          type="button"
          className="icon-button"
          aria-label="Close compare and generate"
          data-dialog-initial-focus
          onClick={onClose}
        >
          ×
        </button>
      </header>
      <div className="comparison-tabs" role="tablist" aria-label="Tool">
        <button
          type="button"
          role="tab"
          aria-selected={tab === "compare"}
          onClick={() => setTab("compare")}
        >
          Compare engines
        </button>
        <button
          type="button"
          role="tab"
          aria-selected={tab === "code"}
          onClick={() => setTab("code")}
        >
          PCRE2 C code
        </button>
      </div>
      <div className="comparison-config">
        <div className="comparison-config-row">
          <label>
            <span>Pattern model</span>
            <select
              value={patternModel}
              onChange={(event) =>
                setPatternModel(event.target.value as ComparisonPatternModel)
              }
            >
              <option value="shared">Shared pattern · unchanged</option>
              <option value="variants">Explicit per-flavour variants</option>
            </select>
          </label>
          <label>
            <span>Operation</span>
            <select
              value={operation}
              onChange={(event) =>
                setOperation(event.target.value as "match" | "replace")
              }
            >
              <option value="match">Match</option>
              <option value="replace">Replace</option>
            </select>
          </label>
          <label className="check-control comparison-scan-control">
            <input
              type="checkbox"
              checked={scanAll}
              onChange={(event) => setScanAll(event.target.checked)}
            />
            Scan all explicitly
          </label>
        </div>
        {patternModel === "shared" ? (
          <label className="comparison-text-field">
            <span>Shared pattern sent unchanged to both engines</span>
            <textarea
              aria-label="Shared comparison pattern"
              value={sharedPattern}
              maxLength={DEFAULT_REGEX_LIMITS.patternHardLengthUtf16}
              onChange={(event) => setSharedPattern(event.target.value)}
            />
          </label>
        ) : (
          <div className="comparison-variant-grid">
            <label className="comparison-text-field">
              <span>ECMAScript pattern variant</span>
              <textarea
                value={ecmaPattern}
                maxLength={DEFAULT_REGEX_LIMITS.patternHardLengthUtf16}
                onChange={(event) => setEcmaPattern(event.target.value)}
              />
            </label>
            <label className="comparison-text-field">
              <span>PCRE2 pattern variant</span>
              <textarea
                value={pcrePattern}
                maxLength={DEFAULT_REGEX_LIMITS.patternHardLengthUtf16}
                onChange={(event) => setPcrePattern(event.target.value)}
              />
            </label>
          </div>
        )}
        <div className="comparison-variant-grid">
          {(
            [
              ["ecmascript", ECMASCRIPT, ecmaFlags, setEcmaFlags],
              ["pcre2", PCRE2, pcreFlags, setPcreFlags],
            ] as const
          ).map(([flavour, definition, selected, setSelected]) => (
            <fieldset className="comparison-flag-selector" key={flavour}>
              <legend>{definition.label} flags · exact</legend>
              {definition.flags.map((flag) => (
                <label key={flag.value} title={flag.label}>
                  <input
                    type="checkbox"
                    checked={selected.includes(flag.value)}
                    onChange={(event) =>
                      setSelected(
                        toggleFlag(
                          selected,
                          flag.value,
                          event.target.checked,
                          flavour,
                        ),
                      )
                    }
                  />
                  <code>{flag.value}</code>
                  <span>{flag.label}</span>
                </label>
              ))}
            </fieldset>
          ))}
        </div>
        <fieldset className="comparison-limit-grid">
          <legend>PCRE2 native and host bounds</legend>
          <label>
            <span>Match steps</span>
            <input
              type="number"
              value={pcreOptionValues.matchLimit}
              min={1}
              max={100_000_000}
              onChange={(event) =>
                setPcreOption("matchLimit", Number(event.target.value))
              }
            />
          </label>
          <label>
            <span>Depth</span>
            <input
              type="number"
              value={pcreOptionValues.depthLimit}
              min={1}
              max={100_000}
              onChange={(event) =>
                setPcreOption("depthLimit", Number(event.target.value))
              }
            />
          </label>
          <label>
            <span>Heap KiB</span>
            <input
              type="number"
              value={pcreOptionValues.heapLimitKib}
              min={1}
              max={131_072}
              onChange={(event) =>
                setPcreOption("heapLimitKib", Number(event.target.value))
              }
            />
          </label>
          <label>
            <span>Matches</span>
            <input
              type="number"
              value={maximumMatches}
              min={1}
              max={DEFAULT_REGEX_LIMITS.maximumMatches}
              onChange={(event) =>
                setMaximumMatches(Number(event.target.value))
              }
            />
          </label>
          <label>
            <span>Capture rows</span>
            <input
              type="number"
              value={maximumCaptureRows}
              min={1}
              max={DEFAULT_REGEX_LIMITS.maximumCaptureRows}
              onChange={(event) =>
                setMaximumCaptureRows(Number(event.target.value))
              }
            />
          </label>
          <label>
            <span>Worker ms</span>
            <input
              type="number"
              value={timeoutMs}
              min={1}
              max={DEFAULT_REGEX_LIMITS.advancedMaximumTimeoutMs}
              onChange={(event) => setTimeoutMs(Number(event.target.value))}
            />
          </label>
        </fieldset>
        {operation === "replace" ? (
          <div className="comparison-variant-grid">
            <label className="comparison-text-field">
              <span>ECMAScript replacement · exact syntax</span>
              <textarea
                value={ecmaReplacement}
                maxLength={DEFAULT_REGEX_LIMITS.maximumReplacementTemplateUtf16}
                onChange={(event) => setEcmaReplacement(event.target.value)}
              />
            </label>
            <label className="comparison-text-field">
              <span>PCRE2 replacement · exact syntax</span>
              <textarea
                value={pcreReplacement}
                maxLength={DEFAULT_REGEX_LIMITS.maximumReplacementTemplateUtf16}
                onChange={(event) => setPcreReplacement(event.target.value)}
              />
            </label>
            <label>
              <span>Output byte cap</span>
              <input
                type="number"
                value={maximumOutputBytes}
                min={1}
                max={DEFAULT_REGEX_LIMITS.maximumReplacementOutputBytes}
                onChange={(event) =>
                  setMaximumOutputBytes(Number(event.target.value))
                }
              />
            </label>
          </div>
        ) : null}
        <label className="comparison-text-field comparison-subject">
          <span>
            Shared subject · {utf8ByteLength(subject).toLocaleString()} UTF-8
            bytes
          </span>
          <textarea
            aria-label="Comparison subject"
            value={subject}
            onChange={(event) => setSubject(event.target.value)}
          />
        </label>
      </div>
      {tab === "compare" ? (
        <div role="tabpanel" className="comparison-tab-panel">
          <div className="comparison-actions">
            <button
              type="button"
              className="primary-button"
              disabled={status.kind === "running"}
              onClick={() => void compare()}
            >
              {status.kind === "running" ? "Comparing…" : "Run comparison"}
            </button>
            {status.kind === "running" ? (
              <button
                type="button"
                className="secondary-button"
                onClick={cancel}
              >
                Cancel both workers
              </button>
            ) : null}
            <p className={`comparison-panel-status status-${status.kind}`}>
              {status.message}
            </p>
          </div>
          {result ? <ComparisonResultView result={result} /> : null}
        </div>
      ) : (
        <div role="tabpanel" className="comparison-tab-panel codegen-panel">
          <div className="comparison-actions">
            <button type="button" className="primary-button" onClick={generate}>
              Generate reviewed C17
            </button>
            {generated ? (
              <>
                <button
                  type="button"
                  className="secondary-button"
                  onClick={() => {
                    void writeClipboardText(generated.source)
                      .then(() =>
                        setGeneratedStatus("Complete generated source copied."),
                      )
                      .catch((error: unknown) =>
                        setGeneratedStatus(
                          error instanceof Error
                            ? error.message
                            : String(error),
                        ),
                      );
                  }}
                >
                  Copy complete source
                </button>
                <button
                  type="button"
                  className="secondary-button"
                  onClick={() => downloadSource(generated)}
                >
                  Download .c
                </button>
              </>
            ) : null}
            <p role="status">{generatedStatus}</p>
          </div>
          {generated ? (
            <section className="generated-code-result">
              <header>
                <div>
                  <p className="eyebrow">
                    {generated.engineIdentity} · {generated.represents}
                  </p>
                  <h3>{generated.fileName}</h3>
                </div>
                <span className="provenance-badge">
                  Exact UTF-8 byte arrays
                </span>
              </header>
              <p>
                Compile: <code>{generated.compileCommand}</code>
              </p>
              <ul>
                {generated.caveats.map((caveat) => (
                  <li key={caveat}>{caveat}</li>
                ))}
              </ul>
              <pre tabIndex={0}>
                <code>{generated.source}</code>
              </pre>
            </section>
          ) : (
            <p className="comparison-empty-state">
              Generation consumes the exact PCRE2 pattern, flags, native limits,
              subject and optional replacement above. It never powers the
              browser runtime.
            </p>
          )}
        </div>
      )}
    </section>
  );
}
