"use client"; import type { ClientView } from "@/lib/client-view"; import { ApproveButton } from "@/components/client/ApproveButton"; import { isClosedTaskStatus, TASK_STATUS_VISUALS } from "@/components/client/TaskStatusIndicator"; import { TASK_STATUS_LABELS, TASK_STATUSES, type TaskStatus } from "@/lib/task-status"; type Task = ClientView["phases"][number]["tasks"][number] & { phaseTitle: string; }; const COLUMNS: { id: TaskStatus; label: string }[] = TASK_STATUSES.map((id) => ({ id, label: TASK_STATUS_LABELS[id], })); function TaskCard({ task, token }: { task: Task; token: string }) { return (

{task.phaseTitle}

{task.title}

{task.description && (

{task.description}

)} {task.deliverables.length > 0 && ( )}
); } export function ClientKanban({ phases, token }: { phases: ClientView["phases"]; token: string }) { const allTasks: Task[] = phases.flatMap((phase) => phase.tasks.map((task) => ({ ...task, phaseTitle: phase.title })) ); // Derived from the statuses, not a hand-written object: as three fixed keys it // dropped any task outside them from every column AND every counter, so the // client silently saw fewer tasks than the project had. const tasksByStatus = COLUMNS.reduce( (acc, col) => { acc[col.id] = allTasks.filter((t) => t.status === col.id); return acc; }, {} as Record ); // "Cancellate" è l'unica colonna che si nasconde da vuota: nella maggior parte // dei progetti non ce n'è nessuna, e una quinta colonna vuota ruberebbe spazio // alle quattro che raccontano il lavoro. Si nasconde solo se è vuota, quindi // nessun task sparisce mai dalla board — era proprio quello il bug di prima. const visibleColumns = COLUMNS.filter( (col) => col.id !== "cancelled" || tasksByStatus.cancelled.length > 0 ); return (
4 ? "xl:grid-cols-5" : "xl:grid-cols-4" }`} > {visibleColumns.map((col) => { // Stessa tinta dell'icona in Timeline: passando da una vista all'altra // "in corso" e "in revisione" restano riconoscibili senza rileggere. const v = TASK_STATUS_VISUALS[col.id]; return (
{tasksByStatus[col.id].length}
{tasksByStatus[col.id].map((task) => ( ))} {tasksByStatus[col.id].length === 0 && (

Nessun task

)}
); })}
); }