import React, { useState, useEffect } from 'react';
import {
  Stack,
  Title,
  Card,
  Table,
  Text,
  Badge,
  Group,
  TextInput,
  MultiSelect,
  Button,
  Pagination,
  Loader,
  Modal,
  Alert,
  Grid,
  Select,
  Code,
  Divider,
} from '@mantine/core';
import {
  IconSearch,
  IconFilter,
  IconEye,
  IconActivity,
  IconAlertCircle,
  IconRefresh,
} from '@tabler/icons-react';
import { DatePickerInput } from '@mantine/dates';
import { notifications } from '@mantine/notifications';
import {
  apiService,
  AuditEvent,
  AuditQueryParams,
  AuditResponse,
} from '../services/apiService';
import dayjs from 'dayjs';

const Audit: React.FC = () => {
  const [events, setEvents] = useState<AuditEvent[]>([]);
  const [loading, setLoading] = useState(false);
  const [totalEvents, setTotalEvents] = useState(0);
  const [currentPage, setCurrentPage] = useState(1);
  const [pageSize] = useState(20);
  const [detailModalOpen, setDetailModalOpen] = useState(false);
  const [selectedEvent, setSelectedEvent] = useState<AuditEvent | null>(null);
  
  // Filter states
  const [filters, setFilters] = useState<AuditQueryParams>({
    limit: pageSize,
    offset: 0,
    order_by: 'timestamp',
    order_desc: true,
  });

  const eventTypeOptions = [
    { value: 'auth.login', label: 'Authentication - Login' },
    { value: 'auth.logout', label: 'Authentication - Logout' },
    { value: 'auth.token_verified', label: 'Authentication - Token Verified' },
    { value: 'app.created', label: 'Application - Created' },
    { value: 'app.updated', label: 'Application - Updated' },
    { value: 'app.deleted', label: 'Application - Deleted' },
    { value: 'token.created', label: 'Token - Created' },
    { value: 'token.revoked', label: 'Token - Revoked' },
    { value: 'token.validated', label: 'Token - Validated' },
    { value: 'permission.granted', label: 'Permission - Granted' },
    { value: 'permission.denied', label: 'Permission - Denied' },
  ];

  const statusOptions = [
    { value: 'success', label: 'Success' },
    { value: 'failure', label: 'Failure' },
    { value: 'error', label: 'Error' },
    { value: 'warning', label: 'Warning' },
  ];

  useEffect(() => {
    loadAuditEvents();
  }, [filters]);

  const loadAuditEvents = async () => {
    try {
      setLoading(true);
      const response = await apiService.getAuditEvents(filters);
      setEvents(response.events);
      setTotalEvents(response.total);
    } catch (error) {
      console.error('Failed to load audit events:', error);
      notifications.show({
        title: 'Error',
        message: 'Failed to load audit events',
        color: 'red',
      });
    } finally {
      setLoading(false);
    }
  };

  const handlePageChange = (page: number) => {
    setCurrentPage(page);
    setFilters(prev => ({
      ...prev,
      offset: (page - 1) * pageSize,
    }));
  };

  const handleFilterChange = (key: keyof AuditQueryParams, value: any) => {
    setCurrentPage(1);
    setFilters(prev => ({
      ...prev,
      [key]: value,
      offset: 0,
    }));
  };

  const clearFilters = () => {
    setCurrentPage(1);
    setFilters({
      limit: pageSize,
      offset: 0,
      order_by: 'timestamp',
      order_desc: true,
    });
  };

  const getStatusColor = (status: string) => {
    switch (status.toLowerCase()) {
      case 'success':
        return 'green';
      case 'failure':
      case 'error':
        return 'red';
      case 'warning':
        return 'yellow';
      default:
        return 'gray';
    }
  };

  const getEventTypeColor = (type: string) => {
    if (type.startsWith('auth.')) return 'blue';
    if (type.startsWith('app.')) return 'purple';
    if (type.startsWith('token.')) return 'green';
    if (type.startsWith('permission.')) return 'orange';
    return 'gray';
  };

  const handleViewDetails = (event: AuditEvent) => {
    setSelectedEvent(event);
    setDetailModalOpen(true);
  };

  const totalPages = Math.ceil(totalEvents / pageSize);

  const rows = events.map((event) => (
    <Table.Tr key={event.id}>
      <Table.Td>
        <Text size="sm">
          {dayjs(event.timestamp).format('MMM DD, HH:mm:ss')}
        </Text>
      </Table.Td>
      <Table.Td>
        <Badge color={getEventTypeColor(event.type)} variant="light" size="sm">
          {event.type}
        </Badge>
      </Table.Td>
      <Table.Td>
        <Badge color={getStatusColor(event.status)} variant="light" size="sm">
          {event.status}
        </Badge>
      </Table.Td>
      <Table.Td>
        <Text size="sm" c="dimmed">
          {event.actor_id || 'System'}
        </Text>
      </Table.Td>
      <Table.Td>
        <Text size="sm" lineClamp={2}>
          {event.description}
        </Text>
      </Table.Td>
      <Table.Td>
        <Group gap="xs">
          <Button
            variant="subtle"
            size="xs"
            leftSection={<IconEye size={14} />}
            onClick={() => handleViewDetails(event)}
          >
            Details
          </Button>
        </Group>
      </Table.Td>
    </Table.Tr>
  ));

  return (
    <Stack gap="lg">
      <Group justify="space-between">
        <div>
          <Title order={2} mb="xs">
            Audit Log
          </Title>
          <Text c="dimmed">
            View and search system audit events and security logs
          </Text>
        </div>
        <Button
          leftSection={<IconRefresh size={16} />}
          variant="light"
          onClick={loadAuditEvents}
          loading={loading}
        >
          Refresh
        </Button>
      </Group>

      {/* Filters */}
      <Card shadow="sm" radius="md" withBorder p="md">
        <Stack gap="md">
          <Group justify="space-between">
            <Text fw={500} size="sm">Filters</Text>
            <Button variant="subtle" size="xs" onClick={clearFilters}>
              Clear All
            </Button>
          </Group>
          
          <Grid>
            <Grid.Col span={{ base: 12, sm: 6, md: 3 }}>
              <MultiSelect
                label="Event Types"
                placeholder="All types"
                data={eventTypeOptions}
                value={filters.event_types || []}
                onChange={(value) => handleFilterChange('event_types', value.length ? value : undefined)}
                clearable
                searchable
                size="sm"
              />
            </Grid.Col>
            
            <Grid.Col span={{ base: 12, sm: 6, md: 3 }}>
              <MultiSelect
                label="Status"
                placeholder="All statuses"
                data={statusOptions}
                value={filters.statuses || []}
                onChange={(value) => handleFilterChange('statuses', value.length ? value : undefined)}
                clearable
                size="sm"
              />
            </Grid.Col>

            <Grid.Col span={{ base: 12, sm: 6, md: 3 }}>
              <TextInput
                label="Actor ID"
                placeholder="user@example.com"
                value={filters.actor_id || ''}
                onChange={(event) => handleFilterChange('actor_id', event.target.value || undefined)}
                size="sm"
                leftSection={<IconSearch size={16} />}
              />
            </Grid.Col>

            <Grid.Col span={{ base: 12, sm: 6, md: 3 }}>
              <TextInput
                label="Resource ID"
                placeholder="Resource identifier"
                value={filters.resource_id || ''}
                onChange={(event) => handleFilterChange('resource_id', event.target.value || undefined)}
                size="sm"
                leftSection={<IconSearch size={16} />}
              />
            </Grid.Col>
          </Grid>
        </Stack>
      </Card>

      {/* Events Table */}
      <Card shadow="sm" radius="md" withBorder>
        {loading ? (
          <Stack align="center" justify="center" h={300}>
            <Loader size="lg" />
            <Text>Loading audit events...</Text>
          </Stack>
        ) : events.length === 0 ? (
          <Stack align="center" justify="center" h={300}>
            <IconActivity size={48} color="gray" />
            <div style={{ textAlign: 'center' }}>
              <Text fw={500} mb="xs">
                No audit events found
              </Text>
              <Text size="sm" c="dimmed">
                {Object.keys(filters).filter(k => k !== 'limit' && k !== 'offset' && k !== 'order_by' && k !== 'order_desc').some(k => filters[k as keyof AuditQueryParams])
                  ? 'Try adjusting your filters or clearing them to see more results'
                  : 'Audit events will appear here as system activities occur'}
              </Text>
            </div>
          </Stack>
        ) : (
          <>
            <Table>
              <Table.Thead>
                <Table.Tr>
                  <Table.Th>Timestamp</Table.Th>
                  <Table.Th>Event Type</Table.Th>
                  <Table.Th>Status</Table.Th>
                  <Table.Th>Actor</Table.Th>
                  <Table.Th>Description</Table.Th>
                  <Table.Th>Actions</Table.Th>
                </Table.Tr>
              </Table.Thead>
              <Table.Tbody>{rows}</Table.Tbody>
            </Table>
            
            {totalPages > 1 && (
              <Group justify="space-between" mt="md" px="md" pb="md">
                <Text size="sm" c="dimmed">
                  Showing {(currentPage - 1) * pageSize + 1} to {Math.min(currentPage * pageSize, totalEvents)} of {totalEvents} events
                </Text>
                <Pagination
                  total={totalPages}
                  value={currentPage}
                  onChange={handlePageChange}
                  size="sm"
                />
              </Group>
            )}
          </>
        )}
      </Card>

      {/* Event Detail Modal */}
      <Modal
        opened={detailModalOpen}
        onClose={() => setDetailModalOpen(false)}
        title="Audit Event Details"
        size="lg"
      >
        {selectedEvent && (
          <Stack gap="md">
            <Group justify="space-between">
              <Text fw={500}>Event ID:</Text>
              <Text size="sm" style={{ fontFamily: 'monospace' }}>
                {selectedEvent.id}
              </Text>
            </Group>

            <Group justify="space-between">
              <Text fw={500}>Timestamp:</Text>
              <Text size="sm">
                {dayjs(selectedEvent.timestamp).format('MMMM DD, YYYY HH:mm:ss')}
              </Text>
            </Group>

            <Group justify="space-between">
              <Text fw={500}>Event Type:</Text>
              <Badge color={getEventTypeColor(selectedEvent.type)} variant="light">
                {selectedEvent.type}
              </Badge>
            </Group>

            <Group justify="space-between">
              <Text fw={500}>Status:</Text>
              <Badge color={getStatusColor(selectedEvent.status)} variant="light">
                {selectedEvent.status}
              </Badge>
            </Group>

            <Group justify="space-between">
              <Text fw={500}>Action:</Text>
              <Text size="sm">{selectedEvent.action}</Text>
            </Group>

            <Divider />

            <div>
              <Text fw={500} mb="xs">Description:</Text>
              <Text size="sm">{selectedEvent.description}</Text>
            </div>

            {selectedEvent.actor_id && (
              <Group justify="space-between">
                <Text fw={500}>Actor ID:</Text>
                <Text size="sm">{selectedEvent.actor_id}</Text>
              </Group>
            )}

            {selectedEvent.actor_ip && (
              <Group justify="space-between">
                <Text fw={500}>IP Address:</Text>
                <Text size="sm" style={{ fontFamily: 'monospace' }}>
                  {selectedEvent.actor_ip}
                </Text>
              </Group>
            )}

            {selectedEvent.resource_id && (
              <Group justify="space-between">
                <Text fw={500}>Resource ID:</Text>
                <Text size="sm">{selectedEvent.resource_id}</Text>
              </Group>
            )}

            {selectedEvent.resource_type && (
              <Group justify="space-between">
                <Text fw={500}>Resource Type:</Text>
                <Badge variant="outline" size="sm">
                  {selectedEvent.resource_type}
                </Badge>
              </Group>
            )}

            {selectedEvent.request_id && (
              <Group justify="space-between">
                <Text fw={500}>Request ID:</Text>
                <Text size="sm" style={{ fontFamily: 'monospace' }}>
                  {selectedEvent.request_id}
                </Text>
              </Group>
            )}

            {selectedEvent.session_id && (
              <Group justify="space-between">
                <Text fw={500}>Session ID:</Text>
                <Text size="sm" style={{ fontFamily: 'monospace' }}>
                  {selectedEvent.session_id}
                </Text>
              </Group>
            )}

            {selectedEvent.user_agent && (
              <div>
                <Text fw={500} mb="xs">User Agent:</Text>
                <Text size="xs" c="dimmed" style={{ fontFamily: 'monospace' }}>
                  {selectedEvent.user_agent}
                </Text>
              </div>
            )}

            {selectedEvent.details && Object.keys(selectedEvent.details).length > 0 && (
              <>
                <Divider />
                <div>
                  <Text fw={500} mb="xs">Additional Details:</Text>
                  <Code block>
                    {JSON.stringify(selectedEvent.details, null, 2)}
                  </Code>
                </div>
              </>
            )}
          </Stack>
        )}
      </Modal>
    </Stack>
  );
};

export default Audit;