<script lang="ts">
	import { onMount } from 'svelte';
	import { browser } from '$app/environment';
	import { getAccessTokenFromDocument } from '$lib/access-token-cookie-browser';
	import { goto } from '$app/navigation';
	import { page } from '$app/stores';
	import {
		clientsProvidersApi,
		type ClientProvider
	} from '$lib/api/dashboard/a76/clients-providers';
	import { Button } from '$lib/components/ui/button';
	import * as Card from '$lib/components/ui/card';
	import { Input } from '$lib/components/ui/input';
	import { Label } from '$lib/components/ui/label';
	import * as Select from '$lib/components/ui/select';
	import { Plus, RefreshCw, Users, Building2, MapPin, Mail, Phone, Hash } from 'lucide-svelte';
	import { toast } from 'svelte-sonner';
	import { companyStore } from '$lib/stores/company.svelte';
	import type { ApiError } from '$lib/utils/error-handler';
	import { currentUser } from '$lib/auth';
	import {
		canCreateClientsAndProviders,
		canDeleteClientsAndProviders,
		canEditClientsAndProviders
	} from '$lib/permissions/clients-providers-permissions';

	const canCreatePartner = $derived(canCreateClientsAndProviders($currentUser));
	const canEditPartner = $derived(canEditClientsAndProviders($currentUser));
	const canDeletePartner = $derived(canDeleteClientsAndProviders($currentUser));

	// Los datos iniciales vienen del servidor
	let { data }: { data: any } = $props();

	// State
	let allItems = $state<ClientProvider[]>(data.items || []);
	let selectedItem = $state<ClientProvider | null>(null);
	let isLoading = $state(false);

	// Server-side filtering/pagination parameters
	let currentPage = $state(data.page || 1);
	let pageSize = $state(50);
	let totalItems = $state(data.total || 0);
	let hasMore = $derived(allItems.length < totalItems);

	// Filter state
	let searchName = $state('');
	let searchRfc = $state('');
	let searchType = $state<string>($page.url.searchParams.get('type') || 'both');
	let searchTimeout: ReturnType<typeof setTimeout>;
	let hasMounted = false;
	let scrollContainer = $state<HTMLDivElement>();
	let loadingTrigger = $state<HTMLDivElement>();

	// Estado para el diálogo de crear
	let showCreateDialog = $state(false);
	let error = $state<string | ApiError | null>(data.error || null);

	// --- Lifecycle ---

	onMount(() => {
		hasMounted = true;
		if (browser) {
			// Sincronizar token de cookies a localStorage si es necesario
			const getCookie = (name: string) => {
				const value = `; ${document.cookie}`;
				const parts = value.split(`; ${name}=`);
				if (parts.length === 2) return parts.pop()?.split(';').shift() || null;
				return null;
			};
			const cookieToken = getAccessTokenFromDocument();
			const localToken = localStorage.getItem('access_token');
			if (cookieToken && cookieToken !== localToken)
				localStorage.setItem('access_token', cookieToken);

			// Listen for company changes
			const handleCompanyChange = () => loadItems(1); // Reload from page 1
			window.addEventListener('companyChanged', handleCompanyChange);
			return () => window.removeEventListener('companyChanged', handleCompanyChange);
		}
	});

	$effect(() => {
		const type = searchType;
		const name = searchName;
		const rfc = searchRfc;
		if (!browser || !hasMounted) return;

		clearTimeout(searchTimeout);
		searchTimeout = setTimeout(() => {
			void loadItems(1);
		}, 400);

		return () => clearTimeout(searchTimeout);
	});

	$effect(() => {
		if (!browser || !scrollContainer || !loadingTrigger) return;
		const observer = new IntersectionObserver(
			(entries) => {
				const [entry] = entries;
				if (entry.isIntersecting && hasMore && !isLoading) {
					void loadMore();
				}
			},
			{
				root: scrollContainer,
				threshold: 0.1
			}
		);
		observer.observe(loadingTrigger);
		return () => observer.disconnect();
	});

	// --- Actions ---

	async function loadItems(pageToLoad = 1, append = false) {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		isLoading = true;
		try {
			const filters: any = {};
			if (searchType !== 'both') filters.type = searchType;
			// Note: The API technically supports name/rfc fitlering if backend implements it.
			// Assuming backend supports 'name' and 'rfc' query params based on standard patterns,
			// or we filter client side if the list is small.
			// Given pagination, we should try sending them. If backend ignores them, we might need client filtering.
			// Ideally backend should handle this. I will assume backend filters for now or add query params.
			if (searchName) filters.name = searchName;
			if (searchRfc) filters.rfc = searchRfc;

			const response = await clientsProvidersApi.list(companyId, pageToLoad, pageSize, filters);

			if (response.error) {
				if (response.status === 401 || response.status === 403) {
					toast.error('Sesión expirada. Recargando...');
					setTimeout(() => window.location.reload(), 2000);
					return;
				}
				toast.error(response.error);
				return;
			}

			if (response.data) {
				allItems = append ? [...allItems, ...response.data.items] : response.data.items;
				totalItems = response.data.total;
				currentPage = response.data.page;
			}
		} catch (e) {
			console.error('Error loading items:', e);
			toast.error('Error al cargar datos');
		} finally {
			isLoading = false;
		}
	}

	function handleTypeChange(value: string) {
		searchType = value;
	}

	async function loadMore() {
		if (isLoading || !hasMore) return;
		await loadItems(currentPage + 1, true);
	}

	function selectItem(item: ClientProvider) {
		selectedItem = item;
	}

	function handleRowDoubleClick(item: ClientProvider) {
		if (!canEditPartner) {
			toast.error('No tienes permiso para editar clientes o proveedores');
			return;
		}
		selectedItem = item;
		goto(`/dashboard/clients_and_providers/edit/${item.id}`);
	}

	function taxIdOrRfcLabel(cp: ClientProvider | null): string {
		if (!cp) return 'RFC';
		const proc = (cp.type_nat_foreign || 'N').toUpperCase();
		return proc === 'E' ? 'TAX-ID' : 'RFC';
	}

	function handleEdit() {
		if (!canEditPartner) {
			toast.error('No tienes permiso para editar clientes o proveedores');
			return;
		}
		if (selectedItem) goto(`/dashboard/clients_and_providers/edit/${selectedItem.id}`);
	}

	import { useShortcuts } from '$lib/hooks/use-shortcuts';
	import { obtenerAtajosListaSocios } from '$lib/config/shortcuts/dashboard/clients_and_providers/list';

	async function handleDelete() {
		if (!canDeletePartner) {
			toast.error('No tienes permiso para eliminar clientes o proveedores');
			return;
		}
		if (!selectedItem || !companyStore.activeCompany?.id) return;
		if (!confirm('¿Estás seguro de eliminar este registro?')) return;

		try {
			await clientsProvidersApi.delete(selectedItem.id, companyStore.activeCompany.id);
			toast.success('Registro eliminado');
			selectedItem = null;
			loadItems(1);
		} catch (e) {
			toast.error('Error al eliminar');
		}
	}

	useShortcuts(
		'Clients Providers List',
		obtenerAtajosListaSocios({
			filtrarTodos: () => handleTypeChange('both'),
			filtrarClientes: () => handleTypeChange('client'),
			filtrarProveedores: () => handleTypeChange('provider'),
			nuevo: () => {
				if (!canCreatePartner) {
					toast.error('No tienes permiso para crear clientes o proveedores');
					return;
				}
				goto('/dashboard/clients_and_providers/edit/new');
			},
			recargar: () => loadItems(1)
		})
	);
</script>

<div class="flex flex-col h-[calc(100vh-4rem)] p-4 gap-4 pb-15">
	<!-- Title -->
	<div class="flex flex-col gap-1">
		<h1 class="text-2xl font-bold">CLIENTES Y PROVEEDORES</h1>
		<p class="text-sm text-muted-foreground">
			Gestiona el catálogo de clientes y proveedores de tu empresa
		</p>
	</div>

	<!-- Error Message -->
	{#if error}
		<Card.Root
			class="bg-card dark:bg-black text-card-foreground dark:text-white border-destructive dark:border-red-800"
		>
			<Card.Header>
				<Card.Title class="text-destructive">Error</Card.Title>
				<Card.Description>
					{typeof error === 'string' ? error : error.detail}
				</Card.Description>
			</Card.Header>
		</Card.Root>
	{/if}

	<div class="flex-1 flex gap-4 overflow-hidden">
		<!-- Left Panel: Table -->
		<div class="flex-1 flex flex-col gap-4 overflow-hidden">
			<!-- Filters -->
			<div class="border rounded-lg bg-card">
				<div class="p-4 space-y-4">
					<div class="flex items-center justify-between">
						<h2 class="text-sm font-semibold">Filtros</h2>
						<span class="text-xs text-muted-foreground">Busque por nombre, RFC/TAX-ID o tipo</span>
					</div>
					<div class="grid grid-cols-4 gap-4">
						<div class="space-y-2">
							<Label class="text-xs">Nombre / Razón Social</Label>
							<Input
								bind:value={searchName}
								placeholder="Buscar por nombre..."
								class="h-9"
							/>
						</div>
						<div class="space-y-2">
							<Label class="text-xs">RFC / TAX-ID</Label>
							<Input
								bind:value={searchRfc}
								placeholder="RFC / TAX-ID..."
								class="h-9"
							/>
						</div>
						<div class="space-y-2">
							<Label class="text-xs">Tipo</Label>
							<Select.Root type="single" value={searchType} onValueChange={handleTypeChange}>
								<Select.Trigger class="h-9">
									{searchType === 'both'
										? 'Todos'
										: searchType === 'client'
											? 'Clientes'
											: 'Proveedores'}
								</Select.Trigger>
								<Select.Content>
									<Select.Item value="both">Todos</Select.Item>
									<Select.Item value="client">Clientes</Select.Item>
									<Select.Item value="provider">Proveedores</Select.Item>
								</Select.Content>
							</Select.Root>
						</div>
						<div class="flex items-end">
							<div class="text-xs text-muted-foreground pb-2">
								Los filtros se aplican automáticamente
							</div>
						</div>
					</div>
				</div>
			</div>

			<!-- Table -->
			<div class="flex-1 flex flex-col border rounded-lg overflow-hidden">
				<div class="flex items-center justify-between p-3 border-b bg-muted/30">
					<h2 class="text-sm font-semibold">Listado</h2>
					<div class="flex items-center gap-2">
						<span class="text-xs text-muted-foreground">
							{totalItems} registros
						</span>
						<Button variant="outline" size="sm" onclick={() => loadItems(currentPage)}>
							<RefreshCw class="h-4 w-4 mr-2" />
							Actualizar
						</Button>
					</div>
				</div>

				<div class="flex-1 overflow-auto bg-card" bind:this={scrollContainer}>
					<table class="w-full text-sm">
						<thead class="bg-muted text-muted-foreground border-b">
							<tr>
								<th class="px-3 py-2 text-left w-8">#</th>
								<th class="px-3 py-2 text-left">RFC / TAX-ID</th>
								<th class="px-3 py-2 text-left">Nombre</th>
								<th class="px-3 py-2 text-left">Tipo</th>
								<th class="px-3 py-2 text-left">Estatus</th>
							</tr>
						</thead>
						<tbody>
							{#if isLoading && allItems.length === 0}
								<tr
									><td colspan="5" class="text-center py-8 text-muted-foreground">Cargando...</td
									></tr
								>
							{:else if allItems.length === 0}
								<tr
									><td colspan="5" class="text-center py-8 text-muted-foreground"
										>No se encontraron registros</td
									></tr
								>
							{:else}
								{#each allItems as item (item.id)}
									<tr
										class="border-b cursor-pointer transition-colors hover:bg-muted/50 {selectedItem?.id ===
										item.id
											? 'bg-muted'
											: ''}"
										onclick={() => selectItem(item)}
										ondblclick={() => handleRowDoubleClick(item)}
									>
										<td class="px-3 py-2 font-mono text-xs text-muted-foreground">{item.id}</td>
										<td class="px-3 py-2 font-mono font-medium">{item.rfc}</td>
										<td class="px-3 py-2">{item.name}</td>
										<td class="px-3 py-2">
											{#if item.client_or_provider === 'client'}
												<span
													class="inline-flex items-center rounded-full bg-blue-100 px-2 py-0.5 text-xs font-medium text-blue-700"
													>Cliente</span
												>
											{:else if item.client_or_provider === 'provider'}
												<span
													class="inline-flex items-center rounded-full bg-purple-100 px-2 py-0.5 text-xs font-medium text-purple-700"
													>Proveedor</span
												>
											{:else}
												<span
													class="inline-flex items-center rounded-full bg-gray-100 px-2 py-0.5 text-xs font-medium text-gray-700"
													>Ambos</span
												>
											{/if}
										</td>
										<td class="px-3 py-2">
											<span
												class="inline-flex items-center rounded-full px-2 py-0.5 text-xs font-medium {item.is_active
													? 'bg-green-100 text-green-700'
													: 'bg-red-100 text-red-700'}"
											>
												{item.is_active ? 'Activo' : 'Inactivo'}
											</span>
										</td>
									</tr>
								{/each}
							{/if}
							{#if hasMore && allItems.length > 0}
								<tr>
									<td colspan="5" class="p-0">
										<div bind:this={loadingTrigger} class="flex items-center justify-center py-5">
											{#if isLoading}
												<span class="text-xs text-muted-foreground">Cargando más registros...</span>
											{:else}
												<span class="text-xs text-muted-foreground">Desplázate para cargar más</span>
											{/if}
										</div>
									</td>
								</tr>
							{/if}
						</tbody>
					</table>
				</div>
				<div class="p-2 border-t flex justify-end">
					<span class="flex items-center text-xs text-muted-foreground px-2">
						Mostrando {allItems.length} de {totalItems}
					</span>
				</div>
			</div>
		</div>

		<!-- Right Panel: Details -->
		<div
			class="w-96 flex-none flex flex-col border rounded-xl bg-muted/30 shadow-sm overflow-hidden"
		>
			<div class="p-4 border-b bg-card">
				<p class="text-[10px] uppercase tracking-widest opacity-80 text-muted-foreground">
					Detalles del Registro
				</p>
				<h2
					class="text-xl font-black font-mono tracking-tighter truncate"
					title={selectedItem?.name || ''}
				>
					{selectedItem?.name || '---'}
				</h2>
				<div class="flex items-center gap-2 mt-1">
					<span class="text-xs font-medium text-muted-foreground">{taxIdOrRfcLabel(selectedItem)}:</span>
					<span class="text-xs font-mono text-muted-foreground">{selectedItem?.rfc || ''}</span>
				</div>
			</div>

			<div class="flex-1 overflow-auto p-5 space-y-6 bg-card">
				{#if selectedItem}
					<div class="grid grid-cols-1 gap-4">
						<div class="space-y-1">
							<Label
								class="text-[10px] uppercase text-muted-foreground font-bold flex items-center gap-1"
							>
								<Users size={10} /> Tipo
							</Label>
							<p class="text-sm font-medium capitalize">{selectedItem.client_or_provider}</p>
						</div>

						{#if selectedItem.address}
							<div class="pt-4 border-t space-y-3">
								<Label
									class="text-[10px] uppercase text-muted-foreground font-bold flex items-center gap-1"
								>
									<MapPin size={10} /> Dirección
								</Label>
								<div class="text-sm space-y-1">
									<p>
										{selectedItem.address.streets || ''}
										{selectedItem.address.exterior_number || ''}
										{selectedItem.address.interior_number
											? 'Int ' + selectedItem.address.interior_number
											: ''}
									</p>
									<p>{selectedItem.address.neighborhood || ''}</p>
									<p>{selectedItem.address.city || ''}, {selectedItem.address.state || ''}</p>
									<p>
										{selectedItem.address.postal_code || ''}, {selectedItem.address.country || ''}
									</p>
								</div>
							</div>

							<div class="pt-4 border-t space-y-3">
								<Label
									class="text-[10px] uppercase text-muted-foreground font-bold flex items-center gap-1"
								>
									<Hash size={10} /> Contacto
								</Label>
								{#if selectedItem.address.email}
									<div class="flex items-center gap-2 text-sm">
										<Mail size={14} class="text-muted-foreground" />
										<span>{selectedItem.address.email}</span>
									</div>
								{/if}
								{#if selectedItem.address.phone}
									<div class="flex items-center gap-2 text-sm">
										<Phone size={14} class="text-muted-foreground" />
										<span>{selectedItem.address.phone}</span>
									</div>
								{/if}
							</div>
						{:else}
							<div
								class="p-4 rounded-md bg-yellow-50 dark:bg-yellow-900/10 border border-yellow-200 dark:border-yellow-900"
							>
								<p class="text-xs text-yellow-600 dark:text-yellow-400">Sin dirección registrada</p>
							</div>
						{/if}

						{#if selectedItem.programs}
							<div class="pt-4 border-t space-y-3">
								<Label
									class="text-[10px] uppercase text-muted-foreground font-bold flex items-center gap-1"
								>
									<Building2 size={10} /> Programas
								</Label>
								<div class="grid grid-cols-2 gap-2 text-sm">
									<div>
										<span class="text-xs text-muted-foreground block">Programa</span>
										<span class="font-medium">{selectedItem.programs.program || '-'}</span>
									</div>
									<div>
										<span class="text-xs text-muted-foreground block">Número</span>
										<span class="font-medium">{selectedItem.programs.program_number || '-'}</span>
									</div>
								</div>
							</div>
						{/if}
					</div>
				{:else}
					<div
						class="flex flex-col items-center justify-center h-full text-center text-muted-foreground opacity-50"
					>
						<Building2 class="h-12 w-12 mb-3" />
						<p class="text-sm">Selecciona un registro</p>
					</div>
				{/if}
			</div>
		</div>
	</div>
</div>

<!-- Sticky Footer Actions -->
<div
	class="fixed bottom-0 left-0 right-0 bg-background/95 backdrop-blur supports-[backdrop-filter]:bg-background/80 border-t shadow-lg z-[5] group-has-data-[state=collapsed]/sidebar-wrapper:ml-[calc(var(--sidebar-width-icon))] ml-[calc(var(--sidebar-width))]"
>
	<div class="px-4 py-4 max-w-[1400px] mx-auto">
		<div class="flex justify-end gap-2">
			{#if canCreatePartner}
				<Button size="sm" href="/dashboard/clients_and_providers/edit/new">
					<Plus class="h-4 w-4 mr-1" />
					Nuevo
				</Button>
			{/if}
			{#if canEditPartner}
				<Button variant="outline" size="sm" onclick={handleEdit} disabled={!selectedItem}>
					Editar
				</Button>
			{/if}
			{#if canDeletePartner}
				<Button
					variant="outline"
					size="sm"
					onclick={handleDelete}
					disabled={!selectedItem}
					class="text-destructive hover:text-destructive"
				>
					Borrar
				</Button>
			{/if}
		</div>
	</div>
</div>
