import { Badge } from "@/components/ui/badge";
import {
	Table,
	TableBody,
	TableCell,
	TableHead,
	TableHeader,
	TableRow,
} from "@/components/ui/table";
import {
	MobileCardRow,
	type MobileCardField,
} from "@/components/ui/mobile-card";
import { useIsMobile } from "../hooks/useIsMobile";
import type { BackupJob, BackupRun } from "../types/backups";

interface Props {
	jobs: BackupJob[];
	latestRuns: Map<string, BackupRun>;
}

function formatInterval(seconds: number | null): string {
	if (!seconds) return "N/A";
	if (seconds < 60) return `${seconds}s`;
	if (seconds < 3600) return `${Math.floor(seconds / 60)}m`;
	if (seconds < 86400) return `${Math.floor(seconds / 3600)}h`;
	return `${Math.floor(seconds / 86400)}d`;
}

function formatTimestamp(ts: number | null): string {
	if (!ts) return "Never";
	return new Date(ts * 1000).toLocaleString();
}

type StatusVariant = "success" | "destructive" | "warning" | "secondary";

/**
 * Map a job/run status onto a Badge variant per design §2.3:
 * `success` → success (chart-2); `failure` → destructive (chart-4);
 * `in_progress` → warning (chart-3); unknown → secondary (neutral accent).
 */
function statusVariant(status: string): StatusVariant {
	if (status === "success") return "success";
	if (status === "failure") return "destructive";
	if (status === "in_progress") return "warning";
	return "secondary";
}

// Mobile card fields (spec R3.2): job name is primary; source/schedule/status
// give at-a-glance context. See OpenSpec change `mobile-responsive-parity`.
interface JobCardRow {
	job: BackupJob;
	status: string;
	run_started: number | null;
}

const jobCardFields: MobileCardField<JobCardRow>[] = [
	{ key: "name", label: "Name", render: (r) => r.job.name, primary: true },
	{
		key: "source",
		label: "Source",
		render: (r) => r.job.source ?? "—",
	},
	{
		key: "schedule",
		label: "Schedule",
		render: (r) => formatInterval(r.job.schedule_interval_seconds),
	},
	{
		key: "status",
		label: "Last status",
		render: (r) => <Badge variant={statusVariant(r.status)}>{r.status}</Badge>,
	},
];

export default function BackupJobsTable({ jobs, latestRuns }: Props) {
	const isMobile = useIsMobile();

	if (isMobile) {
		const cardRows: JobCardRow[] = jobs.map((job) => {
			const run = latestRuns.get(job.id);
			return {
				job,
				status: run?.status ?? "unknown",
				run_started: run?.started_at ?? null,
			};
		});
		return (
			<MobileCardRow
				rows={cardRows}
				fields={jobCardFields}
				getRowId={(r) => r.job.id}
			/>
		);
	}

	return (
		<div className="overflow-hidden rounded-lg border border-border">
			<Table aria-label="Backup jobs">
				<TableHeader>
					<TableRow className="bg-card hover:bg-card">
						<TableHead>Name</TableHead>
						<TableHead>Source</TableHead>
						<TableHead>Target</TableHead>
						<TableHead>Schedule</TableHead>
						<TableHead>Last Status</TableHead>
						<TableHead>Last Run</TableHead>
						<TableHead>Next Expected</TableHead>
					</TableRow>
				</TableHeader>
				<TableBody>
					{jobs.map((job) => {
						const run = latestRuns.get(job.id);
						const status = run?.status ?? "unknown";
						const nextExpected =
							run && job.schedule_interval_seconds
								? run.started_at + job.schedule_interval_seconds
								: null;

						return (
							<TableRow key={job.id}>
								<TableCell>{job.name}</TableCell>
								<TableCell>{job.source ?? "—"}</TableCell>
								<TableCell>{job.target ?? "—"}</TableCell>
								<TableCell>
									{formatInterval(job.schedule_interval_seconds)}
								</TableCell>
								<TableCell>
									<Badge variant={statusVariant(status)}>{status}</Badge>
								</TableCell>
								<TableCell>
									{formatTimestamp(run?.started_at ?? null)}
								</TableCell>
								<TableCell>{formatTimestamp(nextExpected)}</TableCell>
							</TableRow>
						);
					})}
				</TableBody>
			</Table>
		</div>
	);
}
