import { useState } from 'react';
import {
  Title, Text, Stack, Group, Button, Table, Badge, Card, ActionIcon,
  Loader, Center, Select, Modal, TextInput, Alert, SimpleGrid, Tooltip,
} from '@mantine/core';
import { DateInput } from '@mantine/dates';
import {
  IconPlus, IconArrowLeft, IconTrash, IconEdit,
  IconPlayerPlay, IconCoin, IconTrendingUp,
} from '@tabler/icons-react';
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
import { useParams, useNavigate } from 'react-router-dom';
import { notifications } from '@mantine/notifications';
import api from '../../services/api';
import { InvestmentForm } from './components/InvestmentForm';
import { ProjectionChart } from './components/ProjectionChart';
import { InvestmentTimeline } from './components/InvestmentTimeline';

const fmt = (v: number) => v.toLocaleString('en-US', { style: 'currency', currency: 'USD', maximumFractionDigits: 0 });
const fmtDec = (v: number) => v.toLocaleString('en-US', { style: 'currency', currency: 'USD', minimumFractionDigits: 2, maximumFractionDigits: 2 });

const statusColors: Record<string, string> = {
  draft: 'gray', active: 'blue', approved: 'green', archived: 'red',
};

export function InvestmentScenarioDetailPage() {
  const { id } = useParams<{ id: string }>();
  const navigate = useNavigate();
  const queryClient = useQueryClient();
  const [addOpen, setAddOpen] = useState(false);
  const [editInv, setEditInv] = useState<any>(null);
  const [executeInv, setExecuteInv] = useState<any>(null);
  const [executionDate, setExecutionDate] = useState<Date | null>(new Date());

  const { data: scenario, isLoading } = useQuery({
    queryKey: ['board-planning-scenario', id],
    queryFn: async () => {
      const { data } = await api.get(`/board-planning/scenarios/${id}`);
      return data;
    },
  });

  const { data: projection, isLoading: projLoading } = useQuery({
    queryKey: ['board-planning-projection', id],
    queryFn: async () => {
      const { data } = await api.get(`/board-planning/scenarios/${id}/projection`);
      return data;
    },
    enabled: !!id,
  });

  const addMutation = useMutation({
    mutationFn: (dto: any) => api.post(`/board-planning/scenarios/${id}/investments`, dto),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ['board-planning-scenario', id] });
      queryClient.invalidateQueries({ queryKey: ['board-planning-projection', id] });
      setAddOpen(false);
      notifications.show({ message: 'Investment added', color: 'green' });
    },
  });

  const updateMutation = useMutation({
    mutationFn: ({ invId, ...dto }: any) => api.put(`/board-planning/investments/${invId}`, dto),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ['board-planning-scenario', id] });
      queryClient.invalidateQueries({ queryKey: ['board-planning-projection', id] });
      setEditInv(null);
      notifications.show({ message: 'Investment updated', color: 'green' });
    },
  });

  const removeMutation = useMutation({
    mutationFn: (invId: string) => api.delete(`/board-planning/investments/${invId}`),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ['board-planning-scenario', id] });
      queryClient.invalidateQueries({ queryKey: ['board-planning-projection', id] });
      notifications.show({ message: 'Investment removed', color: 'orange' });
    },
  });

  const executeMutation = useMutation({
    mutationFn: ({ invId, executionDate }: { invId: string; executionDate: string }) =>
      api.post(`/board-planning/investments/${invId}/execute`, { executionDate }),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ['board-planning-scenario', id] });
      queryClient.invalidateQueries({ queryKey: ['board-planning-projection', id] });
      setExecuteInv(null);
      notifications.show({ message: 'Investment executed and recorded', color: 'green' });
    },
    onError: (err: any) => {
      notifications.show({ message: err.response?.data?.message || 'Execution failed', color: 'red' });
    },
  });

  const statusMutation = useMutation({
    mutationFn: (status: string) => api.put(`/board-planning/scenarios/${id}`, { status }),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ['board-planning-scenario', id] });
      queryClient.invalidateQueries({ queryKey: ['board-planning-scenarios'] });
    },
  });

  if (isLoading) return <Center h={400}><Loader size="lg" /></Center>;
  if (!scenario) return <Center h={400}><Text>Scenario not found</Text></Center>;

  const investments = scenario.investments || [];
  const summary = projection?.summary;

  // Build a lookup of per-investment interest from the projection
  const interestDetailMap: Record<string, { interest: number; principal: number }> = {};
  if (summary?.investment_interest_details) {
    for (const d of summary.investment_interest_details) {
      interestDetailMap[d.id] = { interest: d.interest, principal: d.principal };
    }
  }

  return (
    <Stack>
      {/* Header */}
      <Group justify="space-between" align="flex-start">
        <Group>
          <ActionIcon variant="subtle" onClick={() => navigate('/board-planning/investments')}>
            <IconArrowLeft size={20} />
          </ActionIcon>
          <div>
            <Group gap="xs">
              <Title order={2}>{scenario.name}</Title>
              <Badge color={statusColors[scenario.status]}>{scenario.status}</Badge>
            </Group>
            {scenario.description && <Text c="dimmed" size="sm">{scenario.description}</Text>}
          </div>
        </Group>
        <Group>
          <Select
            size="xs"
            value={scenario.status}
            onChange={(v) => v && statusMutation.mutate(v)}
            data={[
              { value: 'draft', label: 'Draft' },
              { value: 'active', label: 'Active' },
              { value: 'approved', label: 'Approved' },
            ]}
          />
          <Button size="sm" leftSection={<IconPlus size={16} />} onClick={() => setAddOpen(true)}>
            Add Investment
          </Button>
        </Group>
      </Group>

      {/* Summary Cards */}
      {summary && (
        <SimpleGrid cols={{ base: 1, sm: 2, lg: 4 }}>
          <Card withBorder p="md">
            <Text size="xs" c="dimmed" tt="uppercase" fw={700}>Total Principal</Text>
            <Text fw={700} size="xl" ff="monospace">{fmt(summary.total_principal_invested || 0)}</Text>
            <Text size="xs" c="dimmed">{investments.filter((i: any) => !i.executed_investment_id).length} planned investments</Text>
          </Card>
          <Card withBorder p="md">
            <Text size="xs" c="dimmed" tt="uppercase" fw={700}>Projected Interest Earned</Text>
            <Text fw={700} size="xl" ff="monospace" c="green">
              {summary.total_interest_earned > 0 ? `+${fmtDec(summary.total_interest_earned)}` : '$0.00'}
            </Text>
            {summary.total_interest_earned > 0 && (
              <Text size="xs" c="dimmed">Over projection period</Text>
            )}
            {summary.total_interest_earned === 0 && investments.length > 0 && (
              <Text size="xs" c="orange">Set purchase & maturity dates to calculate</Text>
            )}
          </Card>
          <Card withBorder p="md">
            <Text size="xs" c="dimmed" tt="uppercase" fw={700}>Return on Investment</Text>
            <Text fw={700} size="xl" ff="monospace" c={summary.roi_percentage > 0 ? 'green' : undefined}>
              {summary.roi_percentage > 0 ? `${summary.roi_percentage.toFixed(2)}%` : '-'}
            </Text>
            {summary.roi_percentage > 0 && (
              <Text size="xs" c="dimmed">Interest / Principal</Text>
            )}
          </Card>
          <Card withBorder p="md">
            <Text size="xs" c="dimmed" tt="uppercase" fw={700}>End Liquidity</Text>
            <Text fw={700} size="xl" ff="monospace">{fmt(summary.end_liquidity || 0)}</Text>
            <Text size="xs" c={summary.period_change >= 0 ? 'green' : 'red'}>
              {summary.period_change >= 0 ? '+' : ''}{fmt(summary.period_change || 0)} over period
            </Text>
          </Card>
        </SimpleGrid>
      )}

      {/* Investments Table */}
      <Card withBorder p="lg">
        <Title order={4} mb="md">Planned Investments ({investments.length})</Title>
        {investments.length > 0 ? (
          <Table striped highlightOnHover>
            <Table.Thead>
              <Table.Tr>
                <Table.Th>Label</Table.Th>
                <Table.Th>Type</Table.Th>
                <Table.Th>Fund</Table.Th>
                <Table.Th ta="right">Principal</Table.Th>
                <Table.Th ta="right">Rate</Table.Th>
                <Table.Th ta="right">Est. Interest</Table.Th>
                <Table.Th>Purchase</Table.Th>
                <Table.Th>Maturity</Table.Th>
                <Table.Th>Status</Table.Th>
                <Table.Th w={100}>Actions</Table.Th>
              </Table.Tr>
            </Table.Thead>
            <Table.Tbody>
              {investments.map((inv: any) => {
                const detail = interestDetailMap[inv.id];
                return (
                  <Table.Tr key={inv.id}>
                    <Table.Td fw={500}>{inv.label}</Table.Td>
                    <Table.Td><Badge size="sm" variant="light">{inv.investment_type || '-'}</Badge></Table.Td>
                    <Table.Td><Badge size="sm" color={inv.fund_type === 'reserve' ? 'violet' : 'blue'}>{inv.fund_type}</Badge></Table.Td>
                    <Table.Td ta="right" ff="monospace">{fmt(parseFloat(inv.principal))}</Table.Td>
                    <Table.Td ta="right">{inv.interest_rate ? `${parseFloat(inv.interest_rate).toFixed(2)}%` : '-'}</Table.Td>
                    <Table.Td ta="right" ff="monospace" c={detail?.interest ? 'green' : 'dimmed'}>
                      {detail?.interest ? `+${fmtDec(detail.interest)}` : '-'}
                    </Table.Td>
                    <Table.Td>{inv.purchase_date ? new Date(inv.purchase_date).toLocaleDateString() : <Text size="sm" c="orange">-</Text>}</Table.Td>
                    <Table.Td>{inv.maturity_date ? new Date(inv.maturity_date).toLocaleDateString() : <Text size="sm" c="orange">-</Text>}</Table.Td>
                    <Table.Td>
                      {inv.executed_investment_id
                        ? <Badge size="sm" color="green">Executed</Badge>
                        : <Badge size="sm" color="gray">Planned</Badge>}
                    </Table.Td>
                    <Table.Td>
                      <Group gap={4} wrap="nowrap">
                        <Tooltip label="Edit">
                          <ActionIcon variant="subtle" color="blue" size="sm" onClick={() => setEditInv(inv)}>
                            <IconEdit size={16} />
                          </ActionIcon>
                        </Tooltip>
                        {!inv.executed_investment_id && (
                          <Tooltip label="Execute">
                            <ActionIcon variant="subtle" color="green" size="sm" onClick={() => { setExecuteInv(inv); setExecutionDate(new Date()); }}>
                              <IconPlayerPlay size={16} />
                            </ActionIcon>
                          </Tooltip>
                        )}
                        <Tooltip label="Remove">
                          <ActionIcon variant="subtle" color="red" size="sm" onClick={() => removeMutation.mutate(inv.id)}>
                            <IconTrash size={16} />
                          </ActionIcon>
                        </Tooltip>
                      </Group>
                    </Table.Td>
                  </Table.Tr>
                );
              })}
            </Table.Tbody>
          </Table>
        ) : (
          <Text ta="center" c="dimmed" py="lg">
            No investments added yet. Click &quot;Add Investment&quot; to model an investment allocation.
          </Text>
        )}
      </Card>

      {/* Investment Timeline */}
      {investments.length > 0 && <InvestmentTimeline investments={investments} />}

      {/* Projection Chart */}
      {projection && (
        <ProjectionChart
          datapoints={projection.datapoints || []}
          title="Scenario Projection"
          summary={projection.summary}
        />
      )}
      {projLoading && <Center py="xl"><Loader /></Center>}

      {/* Add/Edit Investment Modal */}
      <InvestmentForm
        opened={addOpen || !!editInv}
        onClose={() => { setAddOpen(false); setEditInv(null); }}
        onSubmit={(data) => {
          if (editInv) {
            updateMutation.mutate({ invId: editInv.id, ...data });
          } else {
            addMutation.mutate(data);
          }
        }}
        initialData={editInv}
        loading={addMutation.isPending || updateMutation.isPending}
      />

      {/* Execute Confirmation Modal */}
      <Modal opened={!!executeInv} onClose={() => setExecuteInv(null)} title="Execute Investment">
        <Stack>
          <Alert color="blue" variant="light">
            This will create a real investment account record and post a journal entry transferring funds.
          </Alert>
          {executeInv && (
            <>
              <Text size="sm"><strong>Investment:</strong> {executeInv.label}</Text>
              <Text size="sm"><strong>Amount:</strong> {fmt(parseFloat(executeInv.principal))}</Text>
              <DateInput
                label="Execution Date"
                required
                value={executionDate}
                onChange={setExecutionDate}
                description="The date the investment is actually purchased"
              />
            </>
          )}
          <Group justify="flex-end">
            <Button variant="default" onClick={() => setExecuteInv(null)}>Cancel</Button>
            <Button
              color="green"
              leftSection={<IconPlayerPlay size={16} />}
              onClick={() => {
                if (executeInv && executionDate) {
                  executeMutation.mutate({
                    invId: executeInv.id,
                    executionDate: executionDate.toISOString().split('T')[0],
                  });
                }
              }}
              loading={executeMutation.isPending}
            >
              Execute Investment
            </Button>
          </Group>
        </Stack>
      </Modal>
    </Stack>
  );
}
