import { useEffect, useMemo } from "react";
import { trpc } from "@/lib/trpc";
import { PhaseAccordion } from "@/components/PhaseAccordion";
import type { SerializedTask } from "@/components/TaskRow";
import type { TaskCounts, FlatTaskEntry } from "./ExecutionContext";
import { sortByPriorityAndQueueTime } from "@codewalk-district/shared";

interface PhaseWithTasksProps {
  phase: {
    id: string;
    initiativeId: string;
    name: string;
    content: string | null;
    status: string;
    createdAt: string;
    updatedAt: string;
  };
  defaultExpanded: boolean;
  onTaskClick: (taskId: string) => void;
  onTaskCounts: (phaseId: string, counts: TaskCounts) => void;
  registerTasks: (phaseId: string, entries: FlatTaskEntry[]) => void;
}

export function PhaseWithTasks({
  phase,
  defaultExpanded,
  onTaskClick,
  onTaskCounts,
  registerTasks,
}: PhaseWithTasksProps) {
  const tasksQuery = trpc.listPhaseTasks.useQuery({ phaseId: phase.id });
  const depsQuery = trpc.getPhaseDependencies.useQuery({ phaseId: phase.id });
  const taskDepsQuery = trpc.listPhaseTaskDependencies.useQuery({ phaseId: phase.id });

  const tasks = tasksQuery.data ?? [];

  return (
    <PhaseWithTasksInner
      phase={phase}
      tasks={tasks}
      tasksLoaded={tasksQuery.isSuccess}
      phaseDependencyIds={depsQuery.data?.dependencies ?? []}
      taskDependencyEdges={taskDepsQuery.data ?? []}
      defaultExpanded={defaultExpanded}
      onTaskClick={onTaskClick}
      onTaskCounts={onTaskCounts}
      registerTasks={registerTasks}
    />
  );
}

interface PhaseWithTasksInnerProps {
  phase: PhaseWithTasksProps["phase"];
  tasks: SerializedTask[];
  tasksLoaded: boolean;
  phaseDependencyIds: string[];
  taskDependencyEdges: Array<{ taskId: string; dependsOn: string[] }>;
  defaultExpanded: boolean;
  onTaskClick: (taskId: string) => void;
  onTaskCounts: (phaseId: string, counts: TaskCounts) => void;
  registerTasks: (phaseId: string, entries: FlatTaskEntry[]) => void;
}

function PhaseWithTasksInner({
  phase,
  tasks,
  tasksLoaded,
  phaseDependencyIds: _phaseDependencyIds,
  taskDependencyEdges,
  defaultExpanded,
  onTaskClick,
  onTaskCounts,
  registerTasks,
}: PhaseWithTasksInnerProps) {
  // Build task dependency map
  const taskDepsMap = useMemo(() => {
    const map = new Map<string, Array<{ name: string; status: string }>>();
    for (const edge of taskDependencyEdges) {
      const blockers = edge.dependsOn
        .map((depId) => {
          const t = tasks.find((tk) => tk.id === depId);
          return t ? { name: t.name, status: t.status } : null;
        })
        .filter(Boolean) as Array<{ name: string; status: string }>;
      if (blockers.length > 0) map.set(edge.taskId, blockers);
    }
    return map;
  }, [taskDependencyEdges, tasks]);

  // Propagate task counts and entries
  useEffect(() => {
    const complete = tasks.filter(
      (t) => t.status === "completed",
    ).length;
    onTaskCounts(phase.id, { complete, total: tasks.length });

    const entries: FlatTaskEntry[] = tasks.map((task) => ({
      task,
      phaseName: phase.name,
      agentName: null,
      blockedBy: taskDepsMap.get(task.id) ?? [],
      dependents: [],
    }));
    registerTasks(phase.id, entries);
  }, [tasks, phase.id, phase.name, onTaskCounts, registerTasks, taskDepsMap]);

  const sortedTasks = sortByPriorityAndQueueTime(tasks);
  const taskEntries = sortedTasks.map((task) => ({
    task,
    agentName: null as string | null,
    blockedBy: taskDepsMap.get(task.id) ?? [] as Array<{ name: string; status: string }>,
  }));

  const phaseDeps: Array<{ name: string; status: string }> = [];

  if (!tasksLoaded) {
    return null;
  }

  return (
    <PhaseAccordion
      phase={phase}
      tasks={taskEntries}
      defaultExpanded={defaultExpanded}
      phaseDependencies={phaseDeps}
      onTaskClick={onTaskClick}
    />
  );
}
