import * as stylex from "@stylexjs/stylex";
import { useClientNames } from "@/features/clients/clientNames";
import { QueryCells, QueryTableHead } from "@/features/queries/QueryLogPage";
import { RING_CAPACITY } from "./ringBuffer";
import { useLiveQueries, type EventSourceFactory, type StreamStatus } from "./useLiveQueries";
import { styles as shared } from "@/ui/styles";
import { colors } from "@/ui/tokens.stylex";

const DARK = "@media (prefers-color-scheme: dark)";

const styles = stylex.create({
	toolbar: {
		display: "flex",
		flexWrap: "wrap",
		alignItems: "center",
		gap: "0.75rem",
	},
	heading: {
		fontSize: "1.5rem",
		lineHeight: "2rem",
		fontWeight: 600,
	},
	toolbarButton: {
		fontWeight: 500,
	},
	pill: {
		borderRadius: "9999px",
		paddingInline: "0.625rem",
		paddingBlock: "0.125rem",
		fontSize: "0.75rem",
		lineHeight: "1rem",
		fontWeight: 500,
	},
	/** Four stream states need four tints; only two of them map onto a token role. */
	pillConnecting: {
		backgroundColor: { default: "oklch(96.7% 0.001 286.375)", [DARK]: "oklch(27.4% 0.006 286.033)" },
		color: { default: "oklch(37% 0.013 285.805)", [DARK]: "oklch(87.1% 0.006 286.286)" },
	},
	pillOpen: {
		backgroundColor: { default: "oklch(96.2% 0.044 156.743)", [DARK]: "oklch(39.3% 0.095 152.535)" },
		color: { default: "oklch(44.8% 0.119 151.328)", [DARK]: "oklch(92.5% 0.084 155.995)" },
	},
	pillRetrying: {
		backgroundColor: { default: "oklch(96.2% 0.059 95.617)", [DARK]: "oklch(41.4% 0.112 45.904)" },
		color: { default: "oklch(47.3% 0.137 46.201)", [DARK]: "oklch(92.4% 0.12 95.746)" },
	},
	pillCapped: {
		backgroundColor: { default: "oklch(93.6% 0.032 17.717)", [DARK]: "oklch(39.6% 0.141 25.723)" },
		color: { default: "oklch(44.4% 0.177 26.899)", [DARK]: "oklch(88.5% 0.062 18.334)" },
	},
	note: {
		marginTop: "0.5rem",
		fontSize: "0.875rem",
		lineHeight: "1.25rem",
		color: colors.textMuted,
	},
	/** Informational, neither a warning nor a failure, so the blue ramp stands alone. */
	resumed: {
		marginTop: "0.75rem",
		display: "flex",
		alignItems: "center",
		gap: "0.75rem",
		borderRadius: "0.25rem",
		borderWidth: 1,
		borderStyle: "solid",
		borderColor: { default: "oklch(80.9% 0.105 251.813)", [DARK]: "oklch(37.9% 0.146 265.522)" },
		backgroundColor: { default: "oklch(97% 0.014 254.604)", [DARK]: "oklch(28.2% 0.091 267.935)" },
		color: { default: "oklch(42.4% 0.199 265.638)", [DARK]: "oklch(88.2% 0.059 254.128)" },
		paddingInline: "0.75rem",
		paddingBlock: "0.5rem",
		fontSize: "0.875rem",
		lineHeight: "1.25rem",
	},
	dismiss: {
		borderStyle: "none",
		backgroundColor: "transparent",
		padding: 0,
		color: "inherit",
		fontSize: "inherit",
		fontWeight: 500,
		textDecorationLine: "underline",
	},
	failureNote: {
		marginTop: "0.75rem",
		fontSize: "0.875rem",
		lineHeight: "1.25rem",
		color: colors.dangerText,
	},
	cappedBox: {
		marginTop: "1rem",
		borderRadius: "0.25rem",
		borderWidth: 1,
		borderStyle: "solid",
		borderColor: colors.dangerBorder,
		backgroundColor: colors.dangerSurface,
		padding: "1rem",
	},
	cappedHeading: {
		fontWeight: 600,
		color: colors.dangerText,
	},
	cappedDetail: {
		marginTop: "0.25rem",
		fontSize: "0.875rem",
		lineHeight: "1.25rem",
		color: colors.dangerText,
	},
	empty: {
		marginTop: "1.5rem",
		color: colors.textMuted,
	},
	tableWrap: {
		marginTop: "1rem",
		overflowX: "auto",
		borderRadius: "0.25rem",
		borderWidth: 1,
		borderStyle: "solid",
		borderColor: colors.border,
	},
	table: {
		width: "100%",
		fontSize: "0.875rem",
		lineHeight: "1.25rem",
	},
	/** `divide-y`: a hairline between rows, so the first row carries none. */
	row: {
		borderTopWidth: { default: 1, ":first-child": 0 },
		borderTopStyle: "solid",
		borderTopColor: colors.border,
	},
	rowBlocked: {
		backgroundColor: {
			default: "oklch(97.1% 0.013 17.38)",
			[DARK]: "oklch(25.8% 0.092 26.042 / 0.4)",
		},
	},
	footnote: {
		marginTop: "0.75rem",
		fontSize: "0.875rem",
		lineHeight: "1.25rem",
		color: colors.textMuted,
	},
});

const PILL_LABELS: Record<StreamStatus, string> = {
	connecting: "Connecting…",
	open: "Live",
	retrying: "Reconnecting…",
	capped: "Disconnected",
};

function pillStyle(status: StreamStatus) {
	if (status === "open") return styles.pillOpen;
	if (status === "retrying") return styles.pillRetrying;
	if (status === "capped") return styles.pillCapped;
	return styles.pillConnecting;
}

function StatusPill({ status }: { status: StreamStatus }) {
	const label = PILL_LABELS[status];
	return (
		<span role="status" aria-label={label} {...stylex.props(styles.pill, pillStyle(status))}>
			{label}
		</span>
	);
}

/** Freeze is display-only: the stream stays open and the 500-row ring buffer keeps
 * filling; Resume shows the current buffer (anything pushed out meanwhile is gone). */
export default function LiveLogPage({ createEventSource }: { createEventSource?: EventSourceFactory } = {}) {
	const live = useLiveQueries({ createEventSource });
	const clientNames = useClientNames();

	return (
		<section>
			<div {...stylex.props(styles.toolbar)}>
				<h1 {...stylex.props(styles.heading)}>Live</h1>
				<StatusPill status={live.status} />
				<button
					type="button"
					onClick={live.toggleFreeze}
					aria-pressed={live.frozen}
					{...stylex.props(shared.button, styles.toolbarButton, shared.focusRing)}
				>
					{live.frozen ? "Resume" : "Freeze"}
				</button>
			</div>

			{live.frozen && (
				<p {...stylex.props(styles.note)} role="status">
					Display frozen — new queries keep buffering ({live.liveCount} in buffer, newest {RING_CAPACITY}{" "}
					kept).
				</p>
			)}

			{live.missed !== null && (
				<div role="status" {...stylex.props(styles.resumed)}>
					<span>
						Stream resumed —{" "}
						{live.missed === 0 ? "no queries missed" : `${live.missed} missed queries recovered`}.
					</span>
					<button
						type="button"
						onClick={live.dismissMissed}
						{...stylex.props(styles.dismiss, shared.focusRing)}
					>
						Dismiss
					</button>
				</div>
			)}

			{live.resyncFailed && (
				<p role="alert" {...stylex.props(styles.failureNote)}>
					Stream resumed, but re-syncing the gap failed — some queries may be missing here.
				</p>
			)}

			{live.status === "capped" && (
				<div role="alert" {...stylex.props(styles.cappedBox)}>
					<h2 {...stylex.props(styles.cappedHeading)}>Live stream unavailable</h2>
					<p {...stylex.props(styles.cappedDetail)}>
						The connection failed repeatedly — possibly too many live viewers (the server caps streams per
						address), or the server is unreachable.
					</p>
					<button type="button" onClick={live.retry} {...stylex.props(shared.retryButton, shared.focusRing)}>
						Retry
					</button>
				</div>
			)}

			{live.rows.length === 0 ? (
				live.status !== "capped" && (
					<p {...stylex.props(styles.empty)}>
						{live.status === "open" ? "Waiting for queries…" : "No queries received yet."}
					</p>
				)
			) : (
				<>
					<div {...stylex.props(styles.tableWrap)}>
						<table {...stylex.props(styles.table)}>
							<QueryTableHead />
							<tbody>
								{live.rows.map((row) => (
									<tr key={row.key} {...stylex.props(styles.row, row.blocked && styles.rowBlocked)}>
										<QueryCells row={row} clientNames={clientNames} />
									</tr>
								))}
							</tbody>
						</table>
					</div>
					<p {...stylex.props(styles.footnote)}>
						Showing {live.rows.length} {live.rows.length === 1 ? "query" : "queries"} (newest first, last{" "}
						{RING_CAPACITY} kept).
					</p>
				</>
			)}
		</section>
	);
}
