"use client";

import { useEffect, useState } from "react";

type LogLine = { time: string; body: React.ReactNode };

type Beat = {
    at: number;
    line: LogLine;
    effect?: "incident" | "runDone" | "revoked";
};

const BEATS: Beat[] = [
    { at: 600, line: { time: "14:22:02", body: "running · step 1/3 · pull image" } },
    { at: 1500, line: { time: "14:22:04", body: "running · step 2/3 · migrate database" } },
    {
        at: 2600,
        line: {
            time: "14:22:07",
            body: (
                <>
                    <span className="ok">ok</span> · migrate database · exit 0
                </>
            ),
        },
    },
    {
        at: 3400,
        line: { time: "14:22:08", body: "running · step 3/3 · restart service" },
        effect: "incident",
    },
    {
        at: 4300,
        line: {
            time: "14:22:10",
            body: (
                <>
                    <span className="er">monitor</span> · edge-gw-02 tls · connection refused
                </>
            ),
        },
    },
    {
        at: 5200,
        line: {
            time: "14:22:11",
            body: (
                <>
                    <span className="ok">ok</span> · restart service · exit 0
                </>
            ),
        },
        effect: "runDone",
    },
    {
        at: 6000,
        line: {
            time: "14:22:12",
            body: (
                <>
                    run finished · <span className="ok">success</span> · 3 steps · 1 server
                </>
            ),
        },
        effect: "revoked",
    },
];

const FIRST_LINE: LogLine = { time: "14:22:01", body: "queued · deploy-app · 1 server" };
const MAX_LINES = 7;

export function InstrumentPanel() {
    const [lines, setLines] = useState<LogLine[]>([FIRST_LINE]);
    const [incident, setIncident] = useState(false);
    const [runActive, setRunActive] = useState(true);
    const [revoked, setRevoked] = useState(false);
    const [resting, setResting] = useState(false);

    useEffect(() => {
        const reduced = window.matchMedia("(prefers-reduced-motion: reduce)").matches;

        const apply = (effect: Beat["effect"]) => {
            if (effect === "incident") setIncident(true);
            if (effect === "runDone") setRunActive(false);
            if (effect === "revoked") setRevoked(true);
        };

        if (reduced) {
            setLines([FIRST_LINE, ...BEATS.map((b) => b.line)].slice(-MAX_LINES));
            BEATS.forEach((b) => apply(b.effect));
            setResting(true);
            return;
        }

        const timers = BEATS.map((beat) =>
            window.setTimeout(() => {
                setLines((prev) => [...prev, beat.line].slice(-MAX_LINES));
                apply(beat.effect);
            }, beat.at),
        );
        timers.push(window.setTimeout(() => setResting(true), 6600));

        return () => timers.forEach(window.clearTimeout);
    }, []);

    return (
        <div className="instrument">
            <div className="rail">
                <div className="instrument__bar">
                    <span>
                        <b>northgate</b> · fleet
                    </span>
                    <span>12 servers</span>
                    <span>{incident ? "10 up" : "11 up"}</span>
                    <span>{incident ? "2 down" : "1 down"}</span>
                    <span>3 monitors</span>
                    <span>{runActive ? "1 run active" : "no runs active"}</span>
                    <span className="instrument__clock">14:22:12 UTC</span>
                </div>

                <div className="panes">
                    <section className="pane" aria-label="Fleet status">
                        <h2 className="pane__h">
                            Fleet <span>{revoked ? "key revoked · 1 server updated" : "agents polling"}</span>
                        </h2>

                        <Row host="proxmox-node-1" sub="4 keys · 12% cpu" state="up" label="Active" />
                        <Row host="db-primary" sub="3 keys · 61% cpu" state="up" label="Active" />
                        <Row host="edge-gw-02" sub={incident ? "2 keys · tls refused" : "2 keys · tls 41d"} state={incident ? "down" : "up"} label={incident ? "Incident" : "Active"} />
                        <Row host="win-build-01" sub="agent 1.4.1 · update ready" state="pend" label="Pending" />
                        <Row host="app-worker-03" sub={revoked ? "4 keys · 1 revoked" : "5 keys · idle"} state="up" label="Active" />
                    </section>

                    <section className="pane" aria-label="Workflow run">
                        <h2 className="pane__h">
                            Run <span>run_8f31c2</span>
                        </h2>
                        <div className="stream" aria-live="polite">
                            {lines.map((line, i) => (
                                <div key={`${line.time}-${i}`}>
                                    <span className="t">{line.time}</span> {line.body}
                                </div>
                            ))}
                            {resting && (
                                <div>
                                    <span className="caret">_</span>
                                </div>
                            )}
                        </div>
                    </section>
                </div>
            </div>
        </div>
    );
}

function Row({ host, sub, state, label }: { host: string; sub: string; state: "up" | "down" | "pend"; label: string }) {
    return (
        <div className="frow">
            <span className={state === "up" ? "dot" : `dot dot--${state}`} />
            <span className="frow__host">{host}</span>
            <span className="frow__sub">{sub}</span>
            <span className={`chip chip--${state}`}>{label}</span>
        </div>
    );
}
