import { useMemo } from 'react';
import { Link } from 'react-router';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import { faUserHeadset } from '@fortawesome/pro-duotone-svg-icons';
import { Avatar } from '@/components/base/avatar/avatar';
import { Badge } from '@/components/base/badges/badges';
import { Table, TableCard } from '@/components/application/table/table';
import { getInitials } from '@/lib/format';
import type { Call } from '@/types/entities';

const formatDuration = (seconds: number): string => {
    if (seconds < 60) return `${seconds}s`;
    const mins = Math.floor(seconds / 60);
    const secs = seconds % 60;
    return secs > 0 ? `${mins}m ${secs}s` : `${mins}m`;
};

const formatPercent = (value: number): string => {
    if (isNaN(value) || !isFinite(value)) return '0%';
    return `${Math.round(value)}%`;
};

interface AgentTableProps {
    calls: Call[];
}

export const AgentTable = ({ calls }: AgentTableProps) => {
    const agents = useMemo(() => {
        // Bucket by authoritative agent.id when present (from CDR enrichment);
        // fall back to raw agentName for legacy rows that haven't been
        // enriched yet. Skips rows with no agent info at all.
        const agentMap = new Map<string, { displayName: string; calls: Call[] }>();
        for (const call of calls) {
            let key: string;
            let displayName: string;
            if (call.agent?.id) {
                key = call.agent.id;
                displayName = call.agent.name ?? call.agent.ozonetelAgentId ?? 'Unknown';
            } else if (call.agentName) {
                key = `legacy:${call.agentName}`;
                displayName = call.agentName;
            } else {
                continue;
            }
            if (!agentMap.has(key)) agentMap.set(key, { displayName, calls: [] });
            agentMap.get(key)!.calls.push(call);
        }

        return Array.from(agentMap.entries()).map(([key, { displayName, calls: agentCalls }]) => {
            const inbound = agentCalls.filter((c) => c.callDirection === 'INBOUND').length;
            const outbound = agentCalls.filter((c) => c.callDirection === 'OUTBOUND').length;
            const missed = agentCalls.filter((c) => c.callStatus === 'MISSED').length;
            const total = agentCalls.length;
            const completedCalls = agentCalls.filter((c) => (c.durationSeconds ?? 0) > 0);
            const totalDuration = completedCalls.reduce((sum, c) => sum + (c.durationSeconds ?? 0), 0);
            const avgHandle = completedCalls.length > 0 ? Math.round(totalDuration / completedCalls.length) : 0;
            const booked = agentCalls.filter((c) => c.disposition === 'APPOINTMENT_BOOKED').length;
            const conversion = total > 0 ? (booked / total) * 100 : 0;
            const nameParts = displayName.split(' ');

            return {
                id: key,
                name: displayName,
                initials: getInitials(nameParts[0] ?? '', nameParts[1] ?? ''),
                inbound, outbound, missed, total, avgHandle, conversion,
            };
        }).sort((a, b) => b.total - a.total);
    }, [calls]);

    if (agents.length === 0) {
        return (
            <TableCard.Root size="sm">
                <TableCard.Header title="Agent Performance" description="Call metrics by agent" />
                <div className="flex flex-col items-center justify-center py-12 gap-2">
                    <FontAwesomeIcon icon={faUserHeadset} className="size-8 text-fg-quaternary" />
                    <p className="text-sm text-tertiary">No agent data available</p>
                </div>
            </TableCard.Root>
        );
    }

    return (
        <TableCard.Root size="sm">
            <TableCard.Header title="Agent Performance" badge={agents.length} description="Call metrics by agent" />
            <Table>
                <Table.Header>
                    <Table.Head label="AGENT" isRowHeader />
                    <Table.Head label="IN" />
                    <Table.Head label="OUT" />
                    <Table.Head label="MISSED" />
                    <Table.Head label="AVG HANDLE" />
                    <Table.Head label="CONVERSION" />
                </Table.Header>
                <Table.Body items={agents}>
                    {(agent) => (
                        <Table.Row id={agent.id}>
                            <Table.Cell>
                                <Link to={`/agent/${encodeURIComponent(agent.id)}`} className="no-underline">
                                    <div className="flex items-center gap-2">
                                        <Avatar size="xs" initials={agent.initials} />
                                        <span className="text-sm font-medium text-brand-secondary hover:text-brand-secondary_hover transition duration-100 ease-linear">{agent.name}</span>
                                    </div>
                                </Link>
                            </Table.Cell>
                            <Table.Cell><span className="text-sm text-success-primary">{agent.inbound}</span></Table.Cell>
                            <Table.Cell><span className="text-sm text-brand-secondary">{agent.outbound}</span></Table.Cell>
                            <Table.Cell>
                                {agent.missed > 0 ? <Badge size="sm" color="error">{agent.missed}</Badge> : <span className="text-sm text-tertiary">0</span>}
                            </Table.Cell>
                            <Table.Cell><span className="text-sm text-secondary">{formatDuration(agent.avgHandle)}</span></Table.Cell>
                            <Table.Cell>
                                <Badge size="sm" color={agent.conversion >= 30 ? 'success' : agent.conversion >= 15 ? 'warning' : 'gray'}>
                                    {formatPercent(agent.conversion)}
                                </Badge>
                            </Table.Cell>
                        </Table.Row>
                    )}
                </Table.Body>
            </Table>
        </TableCard.Root>
    );
};
