"use client";

import { useState } from "react";
import type { ReactElement } from "react";
import { Card, SectionHeader, Badge, Dot } from "@mosaic/ui";
import type { ActiveJob } from "@/lib/api/dashboard";

/* ------------------------------------------------------------------ */
/*  Internal display types                                             */
/* ------------------------------------------------------------------ */

type DotVariant = "teal" | "blue" | "amber" | "red" | "muted";

type BadgeVariant =
  | "badge-teal"
  | "badge-amber"
  | "badge-red"
  | "badge-blue"
  | "badge-muted"
  | "badge-purple"
  | "badge-pulse";

interface AgentNode {
  id: string;
  initials: string;
  avatarColor: string;
  name: string;
  task: string;
  status: DotVariant;
  statusLabel: string;
}

interface OrchestratorSession {
  id: string;
  orchId: string;
  name: string;
  badge: string;
  badgeVariant: BadgeVariant;
  duration: string;
  progress: number;
  agents: AgentNode[];
}

export interface OrchestratorSessionsProps {
  jobs?: ActiveJob[] | undefined;
}

/* ------------------------------------------------------------------ */
/*  Mapping helpers                                                    */
/* ------------------------------------------------------------------ */

const STEP_COLORS: string[] = [
  "rgba(47,128,255,0.15)",
  "rgba(20,184,166,0.15)",
  "rgba(245,158,11,0.15)",
  "rgba(139,92,246,0.15)",
  "rgba(229,72,77,0.15)",
];

function statusToDotVariant(status: string): DotVariant {
  const lower = status.toLowerCase();
  if (lower === "running" || lower === "active" || lower === "completed") return "teal";
  if (lower === "pending" || lower === "queued") return "blue";
  if (lower === "waiting" || lower === "paused") return "amber";
  if (lower === "failed" || lower === "error") return "red";
  return "muted";
}

function statusToBadgeVariant(status: string): BadgeVariant {
  const lower = status.toLowerCase();
  if (lower === "running" || lower === "active") return "badge-teal";
  if (lower === "pending" || lower === "queued") return "badge-blue";
  if (lower === "waiting" || lower === "paused") return "badge-amber";
  if (lower === "failed" || lower === "error") return "badge-red";
  if (lower === "completed") return "badge-purple";
  return "badge-muted";
}

function formatDuration(isoDate: string): string {
  const now = Date.now();
  const start = new Date(isoDate).getTime();
  const diffMs = now - start;

  if (Number.isNaN(diffMs) || diffMs < 0) return "0m";

  const totalMinutes = Math.floor(diffMs / 60_000);
  if (totalMinutes < 60) return `${String(totalMinutes)}m`;

  const hours = Math.floor(totalMinutes / 60);
  const minutes = totalMinutes % 60;
  return `${String(hours)}h ${String(minutes)}m`;
}

function initials(name: string): string {
  return name
    .split(/[\s\-_]+/)
    .slice(0, 2)
    .map((w) => w.charAt(0).toUpperCase())
    .join("");
}

function mapJobToSession(job: ActiveJob): OrchestratorSession {
  const agents: AgentNode[] = job.steps.map((step, idx) => ({
    id: step.id,
    initials: initials(step.name),
    avatarColor: STEP_COLORS[idx % STEP_COLORS.length] ?? "rgba(100,116,139,0.15)",
    name: step.name,
    task: `Phase: ${step.phase}`,
    status: statusToDotVariant(step.status),
    statusLabel: step.status.toLowerCase(),
  }));

  return {
    id: job.id,
    orchId: job.id.length > 10 ? job.id.slice(0, 10).toUpperCase() : job.id.toUpperCase(),
    name: job.type,
    badge: job.status,
    badgeVariant: statusToBadgeVariant(job.status),
    duration: formatDuration(job.createdAt),
    progress: job.progressPercent,
    agents,
  };
}

/* ------------------------------------------------------------------ */
/*  Sub-components                                                     */
/* ------------------------------------------------------------------ */

interface AgentNodeItemProps {
  agent: AgentNode;
}

function AgentNodeItem({ agent }: AgentNodeItemProps): ReactElement {
  const [hovered, setHovered] = useState(false);

  return (
    <div
      onMouseEnter={(): void => {
        setHovered(true);
      }}
      onMouseLeave={(): void => {
        setHovered(false);
      }}
      style={{
        display: "flex",
        alignItems: "center",
        gap: 10,
        padding: "7px 10px",
        borderRadius: "var(--r-sm)",
        border: `1px solid ${hovered ? "var(--ms-border-700)" : "var(--border)"}`,
        background: hovered ? "var(--surface)" : "var(--bg-mid)",
        transition: "border-color 0.15s, background 0.15s",
      }}
    >
      <div
        style={{
          width: 30,
          height: 30,
          borderRadius: 6,
          flexShrink: 0,
          display: "flex",
          alignItems: "center",
          justifyContent: "center",
          fontWeight: 700,
          fontFamily: "var(--mono)",
          fontSize: "0.7rem",
          background: agent.avatarColor,
          color: "var(--text)",
        }}
      >
        {agent.initials}
      </div>
      <div style={{ flex: 1, minWidth: 0 }}>
        <div
          style={{
            fontSize: "0.8rem",
            fontWeight: 600,
            color: "var(--text)",
            whiteSpace: "nowrap",
            overflow: "hidden",
            textOverflow: "ellipsis",
          }}
        >
          {agent.name}
        </div>
        <div
          style={{
            fontSize: "0.72rem",
            color: "var(--muted)",
            whiteSpace: "nowrap",
            overflow: "hidden",
            textOverflow: "ellipsis",
          }}
        >
          {agent.task}
        </div>
      </div>
      <Dot variant={agent.status} />
      <span
        style={{
          fontSize: "0.65rem",
          fontFamily: "var(--mono)",
          color: "var(--muted)",
          textTransform: "uppercase",
        }}
      >
        {agent.statusLabel}
      </span>
    </div>
  );
}

interface OrchCardProps {
  session: OrchestratorSession;
}

function OrchCard({ session }: OrchCardProps): ReactElement {
  return (
    <div
      style={{
        background: "var(--bg-mid)",
        border: "1px solid var(--border)",
        borderRadius: "var(--r)",
        padding: "12px 14px",
        marginBottom: 10,
      }}
    >
      <div
        style={{
          display: "flex",
          alignItems: "center",
          gap: 8,
          marginBottom: 10,
        }}
      >
        <Dot variant={statusToDotVariant(session.badge)} />
        <span
          style={{
            fontFamily: "var(--mono)",
            fontSize: "0.75rem",
            color: "var(--ms-purple-400)",
            fontWeight: 700,
          }}
        >
          {session.orchId}
        </span>
        <span
          style={{
            fontSize: "0.8rem",
            fontWeight: 600,
            color: "var(--text)",
          }}
        >
          {session.name}
        </span>
        <Badge variant={session.badgeVariant}>{session.badge}</Badge>
        <span
          style={{
            marginLeft: "auto",
            fontSize: "0.72rem",
            fontFamily: "var(--mono)",
            color: "var(--muted)",
          }}
        >
          {session.duration}
        </span>
      </div>
      {session.progress > 0 && (
        <div
          style={{
            height: 4,
            borderRadius: 2,
            background: "var(--border)",
            marginBottom: 10,
            overflow: "hidden",
          }}
        >
          <div
            style={{
              height: "100%",
              width: `${String(session.progress)}%`,
              background: "var(--primary)",
              borderRadius: 2,
              transition: "width 0.3s ease",
            }}
          />
        </div>
      )}
      <div style={{ display: "flex", flexDirection: "column", gap: 6 }}>
        {session.agents.map((agent) => (
          <AgentNodeItem key={agent.id} agent={agent} />
        ))}
      </div>
    </div>
  );
}

/* ------------------------------------------------------------------ */
/*  Main export                                                        */
/* ------------------------------------------------------------------ */

export function OrchestratorSessions({ jobs }: OrchestratorSessionsProps): ReactElement {
  const sessions = jobs ? jobs.map(mapJobToSession) : [];
  const activeCount = jobs
    ? jobs.filter(
        (j) => j.status.toLowerCase() === "running" || j.status.toLowerCase() === "active"
      ).length
    : 0;

  return (
    <Card>
      <SectionHeader
        title="Active Orchestrator Sessions"
        subtitle={
          sessions.length > 0
            ? `${String(activeCount)} of ${String(sessions.length)} jobs running`
            : "No active sessions"
        }
        actions={
          sessions.length > 0 ? (
            <Badge variant="badge-teal">{String(activeCount)} active</Badge>
          ) : undefined
        }
      />
      <div>
        {sessions.length > 0 ? (
          sessions.map((session) => <OrchCard key={session.id} session={session} />)
        ) : (
          <div
            style={{
              padding: "24px 0",
              textAlign: "center",
              fontSize: "0.8rem",
              color: "var(--muted)",
            }}
          >
            No active sessions
          </div>
        )}
      </div>
    </Card>
  );
}
