import React, { useState } from 'react';
import {
  View,
  Text,
  StyleSheet,
  FlatList,
  TouchableOpacity,
  Alert,
} from 'react-native';
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
import { COLORS, FONT_SIZE, SPACING, RADIUS } from '../../../theme';
import { useTheme } from '../../../theme';
import { Card, StatusBadge, Spinner, EmptyState, Button, Input } from '../../../components/ui';
import { useToast } from '../../../contexts/ToastContext';
import { documentsAPI, urlSourcesAPI } from '../../../services/api';
import { Document, URLSource } from '../../../types';

interface Props {
  chatbotId: string;
}

export function DocumentsTab({ chatbotId }: Props) {
  const { theme } = useTheme();
  const toast = useToast();
  const qc = useQueryClient();
  const [urlInput, setUrlInput] = useState('');
  const [addingUrl, setAddingUrl] = useState(false);
  const [showUrlInput, setShowUrlInput] = useState(false);

  const { data: documents, isLoading: loadingDocs } = useQuery({
    queryKey: ['documents', chatbotId],
    queryFn: () => documentsAPI.list(chatbotId),
  });

  const { data: urlSources } = useQuery({
    queryKey: ['urlSources', chatbotId],
    queryFn: () => urlSourcesAPI.list(chatbotId),
  });

  const deleteMutation = useMutation({
    mutationFn: (docId: string) => documentsAPI.delete(chatbotId, docId),
    onSuccess: () => {
      qc.invalidateQueries({ queryKey: ['documents', chatbotId] });
      toast.success('Document deleted');
    },
    onError: () => toast.error('Failed to delete document'),
  });

  const retryMutation = useMutation({
    mutationFn: (docId: string) => documentsAPI.retry(chatbotId, docId),
    onSuccess: () => {
      qc.invalidateQueries({ queryKey: ['documents', chatbotId] });
      toast.success('Retry started');
    },
  });

  const deleteUrlMutation = useMutation({
    mutationFn: (sourceId: string) => urlSourcesAPI.delete(chatbotId, sourceId),
    onSuccess: () => {
      qc.invalidateQueries({ queryKey: ['urlSources', chatbotId] });
      toast.success('URL source removed');
    },
  });

  const handleAddUrl = async () => {
    const url = urlInput.trim();
    if (!url) return;
    if (!url.startsWith('http://') && !url.startsWith('https://')) {
      toast.error('Enter a valid URL starting with http:// or https://');
      return;
    }
    setAddingUrl(true);
    try {
      await urlSourcesAPI.add(chatbotId, url);
      qc.invalidateQueries({ queryKey: ['urlSources', chatbotId] });
      setUrlInput('');
      setShowUrlInput(false);
      toast.success('URL added! Scraping in background...');
    } catch (err: any) {
      toast.error(err?.response?.data?.detail ?? 'Failed to add URL');
    } finally {
      setAddingUrl(false);
    }
  };

  const confirmDelete = (doc: Document) => {
    Alert.alert('Delete Document', `Remove "${doc.file_name}"?`, [
      { text: 'Cancel', style: 'cancel' },
      { text: 'Delete', style: 'destructive', onPress: () => deleteMutation.mutate(doc.id) },
    ]);
  };

  const formatSize = (bytes: number) => {
    if (bytes < 1024) return `${bytes} B`;
    if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;
    return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
  };

  type ListItem =
    | { type: 'doc'; data: Document }
    | { type: 'url'; data: URLSource }
    | { type: 'upload-tip' };

  const listData: ListItem[] = [
    { type: 'upload-tip' },
    ...(documents ?? []).map((d: Document) => ({ type: 'doc' as const, data: d })),
    ...(urlSources ?? []).map((u: URLSource) => ({ type: 'url' as const, data: u })),
  ];

  return (
    <View style={[styles.container, { backgroundColor: theme.bg }]}>
      {/* Add URL bar */}
      <View style={[styles.toolbar, { backgroundColor: theme.surface, borderBottomColor: theme.border }]}>
        <Button
          title="+ Add URL"
          size="sm"
          onPress={() => setShowUrlInput(v => !v)}
        />
        <Text style={[styles.toolbarHint, { color: theme.textMuted }]}>
          {(documents ?? []).length + (urlSources ?? []).length} sources
        </Text>
      </View>

      {showUrlInput && (
        <View style={[styles.urlBar, { backgroundColor: theme.surface, borderBottomColor: theme.border }]}>
          <Input
            value={urlInput}
            onChangeText={setUrlInput}
            placeholder="https://example.com/page"
            keyboardType="url"
            autoCapitalize="none"
            autoCorrect={false}
            style={styles.urlInput}
          />
          <View style={styles.urlActions}>
            <Button title="Cancel" variant="ghost" size="sm" onPress={() => { setShowUrlInput(false); setUrlInput(''); }} />
            <Button title="Scrape" size="sm" onPress={handleAddUrl} loading={addingUrl} />
          </View>
        </View>
      )}

      <FlatList
        data={listData}
        keyExtractor={(item, i) => (item.type === 'upload-tip' ? 'tip' : item.type === 'doc' ? item.data.id : item.data.id)}
        contentContainerStyle={styles.list}
        renderItem={({ item }) => {
          if (item.type === 'upload-tip') {
            return (
              <Card style={[styles.tipCard, { borderColor: COLORS.primaryUltraLight }] as any}>
                <Text style={styles.tipIcon}>💡</Text>
                <View style={styles.tipBody}>
                  <Text style={[styles.tipTitle, { color: theme.text }]}>Upload files from the web app</Text>
                  <Text style={[styles.tipDesc, { color: theme.textSecondary }]}>
                    PDF, DOCX, CSV, XLSX, TXT and MD files can be uploaded from the Contexta web dashboard. Use "Add URL" here to scrape web pages directly.
                  </Text>
                </View>
              </Card>
            );
          }

          if (item.type === 'doc') {
            const doc = item.data as Document;
            const icon = doc.file_type?.includes('pdf') ? '📄'
              : doc.file_type?.includes('csv') || doc.file_type?.includes('xlsx') ? '📊'
              : '📝';
            return (
              <View style={[styles.docItem, { backgroundColor: theme.surface, borderColor: theme.border }]}>
                <View style={[styles.docIcon, { backgroundColor: COLORS.primaryUltraLight }]}>
                  <Text style={styles.docIconText}>{icon}</Text>
                </View>
                <View style={styles.docInfo}>
                  <Text style={[styles.docName, { color: theme.text }]} numberOfLines={1}>{doc.file_name}</Text>
                  <View style={styles.docMeta}>
                    <Text style={[styles.docSize, { color: theme.textMuted }]}>{formatSize(doc.file_size)}</Text>
                    {doc.chunk_count > 0 && (
                      <Text style={[styles.docSize, { color: theme.textMuted }]}> · {doc.chunk_count} chunks</Text>
                    )}
                  </View>
                  <View style={styles.docFooter}>
                    <StatusBadge status={doc.status} />
                    {doc.status === 'failed' && (
                      <TouchableOpacity onPress={() => retryMutation.mutate(doc.id)}>
                        <Text style={[styles.retryText, { color: COLORS.primary }]}>Retry</Text>
                      </TouchableOpacity>
                    )}
                  </View>
                </View>
                <TouchableOpacity onPress={() => confirmDelete(doc)} hitSlop={{ top: 8, bottom: 8, left: 8, right: 8 }}>
                  <Text style={styles.deleteIcon}>✕</Text>
                </TouchableOpacity>
              </View>
            );
          }

          // url source
          const src = item.data as URLSource;
          return (
            <View style={[styles.docItem, { backgroundColor: theme.surface, borderColor: theme.border }]}>
              <View style={[styles.docIcon, { backgroundColor: '#e0f2fe' }]}>
                <Text style={styles.docIconText}>🌐</Text>
              </View>
              <View style={styles.docInfo}>
                <Text style={[styles.docName, { color: theme.text }]} numberOfLines={1}>
                  {src.page_title ?? src.url}
                </Text>
                <Text style={[styles.docSize, { color: theme.textMuted }]} numberOfLines={1}>{src.url}</Text>
                <View style={styles.docFooter}>
                  <StatusBadge status={src.status} />
                  {src.chunk_count ? (
                    <Text style={[styles.docSize, { color: theme.textMuted }]}>{src.chunk_count} chunks</Text>
                  ) : null}
                </View>
              </View>
              <TouchableOpacity onPress={() => deleteUrlMutation.mutate(src.id)} hitSlop={{ top: 8, bottom: 8, left: 8, right: 8 }}>
                <Text style={styles.deleteIcon}>✕</Text>
              </TouchableOpacity>
            </View>
          );
        }}
        ListEmptyComponent={
          loadingDocs ? <Spinner centered /> : null
        }
      />
    </View>
  );
}

const styles = StyleSheet.create({
  container: { flex: 1 },

  toolbar: {
    flexDirection: 'row',
    alignItems: 'center',
    justifyContent: 'space-between',
    paddingHorizontal: SPACING.md,
    paddingVertical: SPACING.sm,
    borderBottomWidth: 1,
  },
  toolbarHint: { fontSize: FONT_SIZE.xs },

  urlBar: {
    paddingHorizontal: SPACING.md,
    paddingBottom: SPACING.sm,
    borderBottomWidth: 1,
    gap: SPACING.xs,
  },
  urlInput: { marginBottom: 0 },
  urlActions: { flexDirection: 'row', justifyContent: 'flex-end', gap: SPACING.sm },

  list: { padding: SPACING.md, gap: SPACING.sm },

  tipCard: {
    flexDirection: 'row',
    gap: SPACING.md,
    backgroundColor: '#f0f4ff',
    borderWidth: 1,
  },
  tipIcon: { fontSize: 22 },
  tipBody: { flex: 1, gap: 4 },
  tipTitle: { fontSize: FONT_SIZE.sm, fontWeight: '600' },
  tipDesc: { fontSize: FONT_SIZE.xs, lineHeight: 18 },

  docItem: {
    flexDirection: 'row',
    alignItems: 'center',
    borderRadius: RADIUS.lg,
    padding: SPACING.md,
    borderWidth: 1,
    gap: SPACING.sm,
  },
  docIcon: {
    width: 40,
    height: 40,
    borderRadius: RADIUS.md,
    alignItems: 'center',
    justifyContent: 'center',
  },
  docIconText: { fontSize: 20 },
  docInfo: { flex: 1, gap: 3 },
  docName: { fontSize: FONT_SIZE.sm, fontWeight: '500' },
  docMeta: { flexDirection: 'row', alignItems: 'center' },
  docSize: { fontSize: FONT_SIZE.xs },
  docFooter: { flexDirection: 'row', alignItems: 'center', gap: SPACING.sm, marginTop: 2 },
  retryText: { fontSize: FONT_SIZE.xs, fontWeight: '600' },
  deleteIcon: { fontSize: 16, color: '#9ca3af', padding: SPACING.xs },
});
