<script lang="ts">
	import { usersAPI, type User, type UserStats } from '$lib/api/dashboard/users';
	import { userRolesAPI, type UserRole } from '$lib/api/dashboard/admin/user-roles';
	import { rolesAPI, type CompanyRole } from '$lib/api/dashboard/admin/roles';
	import { rolePermissionsAPI, type RolePermission } from '$lib/api/dashboard/admin/role-permissions';
	import { permissionsAPI, type Permission } from '$lib/api/dashboard/admin/permissions';
	import { userPermissionsAPI, type UserPermission, type EffectiveUserPermissions } from '$lib/api/dashboard/admin/user-permissions';
	import { companyStore } from '$lib/stores/company.svelte';
	import * as Card from '$lib/components/ui/card';
	import * as Dialog from '$lib/components/ui/dialog';
	import * as AlertDialog from '$lib/components/ui/alert-dialog';
	import * as Table from '$lib/components/ui/table';
	import * as Tabs from '$lib/components/ui/tabs';
	import { Button } from '$lib/components/ui/button';
	import { Input } from '$lib/components/ui/input';
	import { Label } from '$lib/components/ui/label';
	import { Textarea } from '$lib/components/ui/textarea';
	import { Switch } from '$lib/components/ui/switch';
	import * as Select from '$lib/components/ui/select';
	import * as Tooltip from '$lib/components/ui/tooltip';
	import { Badge } from '$lib/components/ui/badge';
	import { Checkbox } from '$lib/components/ui/checkbox';
	import { 
		Plus, 
		Pencil, 
		Trash2, 
		Key, 
		UserCheck, 
		UserX, 
		Search,
		RefreshCw,
		Users,
		AlertCircle,
		Shield
	} from 'lucide-svelte';
	import { toast } from 'svelte-sonner';

	// ============================================================================
	// HELPERS PARA FORMATEO DE PERMISOS
	// ============================================================================

	/**
	 * Traduce nombres de módulos a español
	 */
	function getModuleLabel(module: string): string {
		const moduleLabels: Record<string, string> = {
			invoice: 'Facturas',
			user: 'Usuarios',
			role: 'Roles',
			permission: 'Permisos',
			report: 'Reportes',
			company: 'Empresa',
			tenant: 'Tenant',
			dashboard: 'Dashboard',
			settings: 'Configuración',
			client: 'Clientes',
			provider: 'Proveedores',
			product: 'Productos',
			order: 'Pedidos',
			payment: 'Pagos',
			a76: 'Anexo 76',
			a24: 'Anexo 24',
			customs: 'Aduanas',
			import: 'Importación',
			export: 'Exportación',
			exp: 'Exportación',
			imp: 'Importación',
			rep: 'Reportes'
		};
		return moduleLabels[module.toLowerCase()] || module.charAt(0).toUpperCase() + module.slice(1);
	}

	/**
	 * Traduce acciones a español
	 */
	function getActionLabel(action: string): string {
		const actionLabels: Record<string, string> = {
			view: 'Ver',
			create: 'Crear',
			edit: 'Editar',
			update: 'Actualizar',
			delete: 'Eliminar',
			list: 'Listar',
			read: 'Leer',
			write: 'Escribir',
			manage: 'Gestionar',
			process: 'Procesar',
			approve: 'Aprobar',
			reject: 'Rechazar',
			export: 'Exportar',
			import: 'Importar',
			download: 'Descargar',
			upload: 'Subir',
			generate: 'Generar',
			send: 'Enviar',
			receive: 'Recibir'
		};
		return actionLabels[action.toLowerCase()] || action.charAt(0).toUpperCase() + action.slice(1);
	}

	/**
	 * Formatea un código de permiso en una etiqueta legible
	 * Ej: "invoice.exp.rep.process" -> "Facturas > Exportación > Reportes > Procesar"
	 */
	function formatPermissionLabel(permission: Permission): string {
		if (permission.description) {
			return permission.description;
		}

		// Dividir el código en partes
		const parts = permission.code.split('.');
		
		// Si solo tiene module.action, formatear simple
		if (parts.length === 2) {
			const [module, action] = parts;
			return `${getModuleLabel(module)} - ${getActionLabel(action)}`;
		}

		// Si tiene más partes, formatear jerárquicamente
		// La última parte es la acción, el resto son módulos/submódulos
		const action = parts[parts.length - 1];
		const modules = parts.slice(0, -1);
		
		const modulePath = modules.map(m => getModuleLabel(m)).join(' › ');
		return `${modulePath} - ${getActionLabel(action)}`;
	}

	/**
	 * Obtiene una descripción corta del permiso para mostrar en tooltips
	 */
	function getPermissionHint(permission: Permission): string {
		return `Código: ${permission.code} | Módulo: ${permission.module} | Acción: ${permission.action}`;
	}

	// Estados principales - Usuarios
	let users = $state<User[]>([]);
	let stats = $state<UserStats | null>(null);
	let loading = $state(false);
	let searchTerm = $state('');
	let currentPage = $state(1);
	let pageSize = $state(20);
	let totalPages = $state(1);

	// Diálogos
	let showCreateDialog = $state(false);
	let showEditDialog = $state(false);
	let showDeleteDialog = $state(false);
	let showPasswordDialog = $state(false);
	let showRolesDialog = $state(false);

	// Estados para gestión de roles
	let availableRoles = $state<CompanyRole[]>([]);
	let userRoles = $state<UserRole[]>([]);
	let loadingRoles = $state(false);
	let selectedRoleId = $state<number | string>(0);

	// Estados para permisos individuales de usuario
	let effectivePermissions = $state<EffectiveUserPermissions | null>(null);
	let loadingUserPermissions = $state(false);
	let showUserPermissionsDialog = $state(false);
	let showGrantUserPermDialog = $state(false);
	let availablePermissionsForUser = $state<Permission[]>([]);
	let selectedUserPermissionIds = $state<number[]>([]);

	// Roles disponibles que NO están asignados
	const unassignedRoles = $derived(
		availableRoles.filter(
			role => !userRoles.some(ur => ur.company_role_id === role.id)
		)
	);

	// Usuario seleccionado para editar/eliminar
	let selectedUser = $state<User | null>(null);

	// Formulario de creación
	let createForm = $state({
		email: '',
		username: '',
		first_name: '',
		last_name: '',
		password: '',
		role: '',
		enabled: true,
		email_verified: false
	});

	// Formulario de edición
	let editForm = $state({
		first_name: '',
		last_name: '',
		email: '',
		enabled: true,
		email_verified: false,
		role: ''
	});

	// Formulario de cambio de contraseña
	let passwordForm = $state({
		password: '',
		confirmPassword: '',
		temporary: true
	});

	// Estados para Roles y Permisos
	let rolesState = $state<CompanyRole[]>([]);
	let selectedRoleForPermissions = $state<CompanyRole | null>(null);
	let rolePermissionsState = $state<RolePermission[]>([]);
	let allPermissionsState = $state<Permission[]>([]);
	let availablePermissionsState = $state<Permission[]>([]);
	let permissionsByModuleState = $state<Map<string, Permission[]>>(new Map());
	let loadingPermissionsState = $state(false);
	let showPermissionsDialog = $state(false);
	let showRoleDialog = $state(false);
	let showDeleteRoleDialog = $state(false);
	let roleToDelete = $state<CompanyRole | null>(null);
	let selectedPermissionIds = $state<number[]>([]);
	let permissionSearchQuery = $state('');
	let editingRole = $state<CompanyRole | null>(null);
	let roleFormData = $state({
		name: '',
		code: '',
		description: '',
		is_active: true
	});

	// Cargar estadísticas
	async function loadStats() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			stats = await usersAPI.getStats(companyId);
		} catch (error: any) {
			console.error('Error loading stats:', error);
			toast.error('Error al cargar estadísticas', {
				description: error.response?.data?.detail || error.message
			});
		}
	}

	// Cargar usuarios
	async function loadUsers() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		loading = true;
		try {
			const response = await usersAPI.list(companyId, {
				page: currentPage,
				page_size: pageSize,
				search: searchTerm || undefined
			});
			
			users = response.users;
			totalPages = response.total_pages;
		} catch (error: any) {
			console.error('Error loading users:', error);
			toast.error('Error al cargar usuarios', {
				description: error.response?.data?.detail || error.message
			});
		} finally {
			loading = false;
		}
	}

	// Buscar usuarios
	let searchTimeout: ReturnType<typeof setTimeout>;
	function handleSearch() {
		clearTimeout(searchTimeout);
		searchTimeout = setTimeout(() => {
			currentPage = 1;
			loadUsers();
		}, 500);
	}

	// Crear usuario
	async function handleCreate() {
		if (!createForm.email || !createForm.username || !createForm.first_name || 
		    !createForm.last_name || !createForm.password) {
			toast.error('Por favor complete todos los campos requeridos');
			return;
		}

		if (createForm.password.length < 8) {
			toast.error('La contraseña debe tener al menos 8 caracteres');
			return;
		}

		const companyId = companyStore.activeCompany?.id;
		if (!companyId) {
			toast.error('No hay compañía seleccionada');
			return;
		}

		try {
			await usersAPI.create(createForm, companyId);

			toast.success('Usuario creado exitosamente');
			showCreateDialog = false;
			resetCreateForm();
			await Promise.all([loadUsers(), loadStats()]);
		} catch (error: any) {
			console.error('Error creating user:', error);
			toast.error('Error al crear usuario', {
				description: error.response?.data?.detail || error.message
			});
		}
	}

	// Abrir diálogo de edición
	function openEditDialog(user: User) {
		selectedUser = user;
		editForm = {
			first_name: user.first_name,
			last_name: user.last_name,
			email: user.email,
			enabled: user.enabled,
			email_verified: user.email_verified,
			role: user.role || ''
		};
		showEditDialog = true;
	}

	// Actualizar usuario
	async function handleUpdate() {
		if (!selectedUser) return;

		const companyId = companyStore.activeCompany?.id;
		if (!companyId) {
			toast.error('No hay compañía seleccionada');
			return;
		}

		try {
			// Filtrar campos vacíos antes de enviar
			const updateData: any = {};
			if (editForm.first_name && editForm.first_name.trim()) {
				updateData.first_name = editForm.first_name.trim();
			}
			if (editForm.last_name && editForm.last_name.trim()) {
				updateData.last_name = editForm.last_name.trim();
			}
			if (editForm.email && editForm.email.trim()) {
				updateData.email = editForm.email.trim();
			}
			if (editForm.role !== undefined && editForm.role !== null) {
				updateData.role = editForm.role;
			}
			// Solo incluir enabled y email_verified si son diferentes del original
			if (editForm.enabled !== selectedUser.enabled) {
				updateData.enabled = editForm.enabled;
			}
			if (editForm.email_verified !== selectedUser.email_verified) {
				updateData.email_verified = editForm.email_verified;
			}

			await usersAPI.update(selectedUser.id, updateData, companyId);
			toast.success('Usuario actualizado exitosamente');
			showEditDialog = false;
			selectedUser = null;
			await loadUsers();
		} catch (error: any) {
			console.error('Error updating user:', error);
			toast.error('Error al actualizar usuario', {
				description: error.response?.data?.detail || error.message
			});
		}
	}

	// Abrir diálogo de eliminación
	function openDeleteDialog(user: User) {
		selectedUser = user;
		showDeleteDialog = true;
	}

	// Eliminar usuario
	async function handleDelete(softDelete: boolean = true) {
		if (!selectedUser) return;

		const companyId = companyStore.activeCompany?.id;
		if (!companyId) {
			toast.error('No hay compañía seleccionada');
			return;
		}

		try {
			await usersAPI.delete(selectedUser.id, companyId, softDelete);
			toast.success(softDelete ? 'Usuario desactivado exitosamente' : 'Usuario eliminado permanentemente');
			showDeleteDialog = false;
			selectedUser = null;
			await Promise.all([loadUsers(), loadStats()]);
		} catch (error: any) {
			console.error('Error deleting user:', error);
			toast.error('Error al eliminar usuario', {
				description: error.response?.data?.detail || error.message
			});
		}
	}

	// Abrir diálogo de cambio de contraseña
	function openPasswordDialog(user: User) {
		selectedUser = user;
		passwordForm = {
			password: '',
			confirmPassword: '',
			temporary: true
		};
		showPasswordDialog = true;
	}

	// Cambiar contraseña
	async function handleChangePassword() {
		if (!selectedUser) return;

		if (passwordForm.password !== passwordForm.confirmPassword) {
			toast.error('Las contraseñas no coinciden');
			return;
		}

		if (passwordForm.password.length < 8) {
			toast.error('La contraseña debe tener al menos 8 caracteres');
			return;
		}

		const companyId = companyStore.activeCompany?.id;
		if (!companyId) {
			toast.error('No hay compañía seleccionada');
			return;
		}

		try {
			await usersAPI.changePassword(selectedUser.id, {
				password: passwordForm.password,
				temporary: passwordForm.temporary
			}, companyId);
			toast.success('Contraseña actualizada exitosamente');
			showPasswordDialog = false;
			selectedUser = null;
			passwordForm = { password: '', confirmPassword: '', temporary: true };
		} catch (error: any) {
			console.error('Error changing password:', error);
			toast.error('Error al cambiar contraseña', {
				description: error.response?.data?.detail || error.message
			});
		}
	}

	// Gestión de roles
	async function openRolesDialog(user: User) {
		selectedUser = user;
		showRolesDialog = true;
		await Promise.all([
			loadUserRoles(),
			loadAvailableRoles(),
			loadUserEffectivePermissions()
		]);
	}

	async function loadAvailableRoles() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			const response = await rolesAPI.list(companyId);
			availableRoles = (response.items || []).filter((r: CompanyRole) => r.is_active);
		} catch (error: any) {
			console.error('Error loading roles:', error);
			toast.error('Error al cargar roles');
		}
	}

	async function loadUserRoles() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId || !selectedUser) return;

		try {
			loadingRoles = true;
			const response = await userRolesAPI.list(companyId, { user_id: selectedUser.id });
			userRoles = response.items;
		} catch (error: any) {
			console.error('Error loading user roles:', error);
		} finally {
			loadingRoles = false;
		}
	}

	async function assignRole() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId || !selectedUser || !selectedRoleId || selectedRoleId === 0) {
			toast.error('Selecciona un rol');
			return;
		}

		try {
			const roleId = typeof selectedRoleId === 'string' ? parseInt(selectedRoleId) : selectedRoleId;
			await userRolesAPI.assign(companyId, {
				user_id: selectedUser.id,
				company_role_id: roleId
			});
			toast.success('Rol asignado correctamente');
			selectedRoleId = 0;
			await loadUserRoles();
			await loadUsers(); // Actualizar la tabla de usuarios
		} catch (error: any) {
			console.error('Error assigning role:', error);
			if (error.response?.status === 409) {
				toast.error('El usuario ya tiene este rol asignado');
			} else {
				toast.error('Error al asignar rol', {
					description: error.response?.data?.detail || error.message
				});
			}
		}
	}

	async function removeRole(userRoleId: number) {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			await userRolesAPI.remove(userRoleId, companyId);
			toast.success('Rol removido correctamente');
			await loadUserRoles();
			await loadUsers(); // Actualizar la tabla de usuarios
		} catch (error: any) {
			console.error('Error removing role:', error);
			toast.error('Error al remover rol');
		}
	}

	// ============================================================================
	// FUNCIONES PARA PERMISOS INDIVIDUALES
	// ============================================================================

	async function loadUserEffectivePermissions() {
		if (!selectedUser) return;
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			loadingUserPermissions = true;
			effectivePermissions = await userPermissionsAPI.getEffective(selectedUser.id, companyId);
		} catch (error) {
			toast.error('Error al cargar permisos del usuario');
			console.error(error);
		} finally {
			loadingUserPermissions = false;
		}
	}

	function openUserPermissionsDialog() {
		if (!effectivePermissions) return;
		
		// Permisos disponibles son todos los permisos que no están:
		// - Ya concedidos individualmente
		// - Ya revocados individualmente
		const grantedIds = new Set(effectivePermissions.granted_permissions.map(p => p.id));
		const revokedIds = new Set(effectivePermissions.revoked_permissions.map(p => p.id));
		
		availablePermissionsForUser = allPermissionsState.filter(
			p => !grantedIds.has(p.id) && !revokedIds.has(p.id)
		);
		
		selectedUserPermissionIds = [];
		showUserPermissionsDialog = true;
	}

	function openGrantUserPermDialog() {
		if (!effectivePermissions) return;
		
		// Permisos disponibles son todos los permisos que no están:
		// - Ya concedidos individualmente
		// - Ya revocados individualmente
		const grantedIds = new Set(effectivePermissions.granted_permissions.map(p => p.id));
		const revokedIds = new Set(effectivePermissions.revoked_permissions.map(p => p.id));
		
		availablePermissionsForUser = allPermissionsState.filter(
			p => !grantedIds.has(p.id) && !revokedIds.has(p.id)
		);
		
		selectedUserPermissionIds = [];
		permissionSearchQuery = '';
		showGrantUserPermDialog = true;
	}

	async function handleGrantUserPermissions() {
		if (!selectedUser || selectedUserPermissionIds.length === 0) return;
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		const userId = selectedUser.id; // Guardar para evitar null check

		try {
			// Conceder cada permiso seleccionado
			await Promise.all(
				selectedUserPermissionIds.map(permId =>
					userPermissionsAPI.grant(userId, companyId, permId)
				)
			);
			
			toast.success(`${selectedUserPermissionIds.length} permiso(s) concedido(s)`);
			// Cerrar todos los diálogos
			showGrantUserPermDialog = false;
			showUserPermissionsDialog = false;
			showRolesDialog = false;
			selectedUserPermissionIds = [];
			permissionSearchQuery = '';
			await loadUserEffectivePermissions();
		} catch (error) {
			toast.error('Error al conceder permisos');
			console.error(error);
		}
	}

	async function handleRevokeUserPermission(permissionId: number) {
		if (!selectedUser) return;
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			await userPermissionsAPI.revoke(selectedUser.id, companyId, permissionId);
			toast.success('Permiso revocado');
			await loadUserEffectivePermissions();
		} catch (error) {
			toast.error('Error al revocar permiso');
			console.error(error);
		}
	}

	async function handleRemoveUserPermission(permissionId: number) {
		if (!selectedUser) return;
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			await userPermissionsAPI.remove(selectedUser.id, companyId, permissionId);
			toast.success('Permiso individual eliminado');
			await loadUserEffectivePermissions();
		} catch (error) {
			toast.error('Error al eliminar permiso');
			console.error(error);
		}
	}

	function toggleUserPermission(permId: number) {
		if (selectedUserPermissionIds.includes(permId)) {
			selectedUserPermissionIds = selectedUserPermissionIds.filter(id => id !== permId);
		} else {
			selectedUserPermissionIds = [...selectedUserPermissionIds, permId];
		}
	}

	// Resetear formularios
	function resetCreateForm() {
		createForm = {
			email: '',
			username: '',
			first_name: '',
			last_name: '',
			password: '',
			role: '',
			enabled: true,
			email_verified: false
		};
	}

	// Cambiar página
	function goToPage(page: number) {
		if (page >= 1 && page <= totalPages) {
			currentPage = page;
			loadUsers();
		}
	}

	// ========================================
	// Funciones para Roles y Permisos
	// ========================================

	async function loadRolesTab() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			loadingRoles = true;
			const response = await rolesAPI.list(companyId);
			rolesState = response.items || [];
			if (rolesState.length > 0 && !selectedRoleForPermissions) {
				await selectRoleForPermissions(rolesState[0]);
			}
		} catch (error) {
			toast.error('Error al cargar roles');
			console.error(error);
		} finally {
			loadingRoles = false;
		}
	}

	async function loadAllPermissionsForRoles() {
		try {
			const response = await permissionsAPI.list();
			allPermissionsState = response.items || [];
			if (selectedRoleForPermissions) {
				updateAvailablePermissionsForRole();
			}
		} catch (error) {
			toast.error('Error al cargar permisos');
			console.error(error);
		}
	}

	async function selectRoleForPermissions(role: CompanyRole) {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		selectedRoleForPermissions = role;
		loadingPermissionsState = true;

		try {
			const response = await rolePermissionsAPI.listByRole(role.id, companyId);
			rolePermissionsState = response.permissions;
			updateAvailablePermissionsForRole();
		} catch (error) {
			toast.error('Error al cargar permisos del rol');
			console.error(error);
		} finally {
			loadingPermissionsState = false;
		}
	}

	function updateAvailablePermissionsForRole() {
		const assignedIds = rolePermissionsState.map((rp) => rp.permission_id);
		availablePermissionsState = allPermissionsState.filter((p) => !assignedIds.includes(p.id));
		updatePermissionsByModuleForRole();
	}

	function updatePermissionsByModuleForRole() {
		const grouped = new Map<string, Permission[]>();
		
		const filtered = availablePermissionsState.filter((p) => {
			if (!permissionSearchQuery.trim()) return true;
			const search = permissionSearchQuery.toLowerCase();
			return (
				p.code.toLowerCase().includes(search) ||
				p.description?.toLowerCase().includes(search) ||
				p.action.toLowerCase().includes(search)
			);
		});
		
		filtered.forEach((p) => {
			if (!grouped.has(p.module)) {
				grouped.set(p.module, []);
			}
			grouped.get(p.module)!.push(p);
		});
		
		permissionsByModuleState = grouped;
	}

	function openAddPermissionsDialog() {
		const assignedIds = rolePermissionsState.map((rp) => rp.permission_id);
		availablePermissionsState = allPermissionsState.filter((p) => !assignedIds.includes(p.id));
		selectedPermissionIds = [];
		permissionSearchQuery = '';
		updatePermissionsByModuleForRole();
		showPermissionsDialog = true;
	}

	function openCreateRoleDialog() {
		editingRole = null;
		roleFormData = { name: '', code: '', description: '', is_active: true };
		showRoleDialog = true;
	}

	function openEditRoleDialog(role: CompanyRole) {
		editingRole = role;
		roleFormData = {
			name: role.name,
			code: role.code,
			description: role.description || '',
			is_active: role.is_active
		};
		showRoleDialog = true;
	}

	async function handleRoleSubmit() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			if (editingRole) {
				await rolesAPI.update(editingRole.id, companyId, roleFormData);
				toast.success('Rol actualizado correctamente');
				if (selectedRoleForPermissions?.id === editingRole.id) {
					selectedRoleForPermissions = { ...selectedRoleForPermissions, ...roleFormData };
				}
			} else {
				const newRole = await rolesAPI.create(companyId, roleFormData);
				toast.success('Rol creado correctamente');
				selectedRoleForPermissions = newRole;
			}
			showRoleDialog = false;
			await loadRolesTab();
			await loadAvailableRoles(); // También recargar roles para el diálogo de asignación
		} catch (error: any) {
			const message =
				error?.response?.data?.detail ||
				error?.message ||
				(editingRole ? 'Error al actualizar rol' : 'Error al crear rol');
			toast.error(message);
			console.error(error);
		}
	}

	async function handleDeleteRole(role: CompanyRole) {
		roleToDelete = role;
		showDeleteRoleDialog = true;
	}

	async function confirmDeleteRole() {
		if (!roleToDelete) return;
		const companyId = companyStore.activeCompany?.id;
		if (!companyId) return;

		try {
			await rolesAPI.delete(roleToDelete.id, companyId);
			
			// Limpiar estado si el rol eliminado estaba seleccionado
			if (selectedRoleForPermissions?.id === roleToDelete.id) {
				selectedRoleForPermissions = null;
				rolePermissionsState = [];
			}
			
			showDeleteRoleDialog = false;
			const deletedRoleId = roleToDelete.id;
			roleToDelete = null;
			
			// Recargar listas
			await Promise.all([loadRolesTab(), loadAvailableRoles()]);
			
			// Verificar que el rol ya no esté en la lista
			rolesState = rolesState.filter(r => r.id !== deletedRoleId);
			
			toast.success('Rol eliminado permanentemente');
		} catch (error: any) {
			// Manejar error específico cuando el rol tiene usuarios asignados
			if (error?.response?.data?.detail) {
				toast.error(error.response.data.detail);
			} else {
				toast.error('Error al eliminar rol');
			}
			console.error(error);
		}
	}

	async function handleAssignPermissions() {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId || !selectedRoleForPermissions || selectedPermissionIds.length === 0) return;

		try {
			await rolePermissionsAPI.assignMultiple(selectedRoleForPermissions.id, companyId, selectedPermissionIds);
			toast.success('Permisos asignados correctamente');
			showPermissionsDialog = false;
			await selectRoleForPermissions(selectedRoleForPermissions);
		} catch (error) {
			toast.error('Error al asignar permisos');
			console.error(error);
		}
	}

	async function handleRemovePermission(permissionId: number) {
		const companyId = companyStore.activeCompany?.id;
		if (!companyId || !selectedRoleForPermissions) return;
		if (!confirm('¿Estás seguro de remover este permiso?')) return;

		try {
			await rolePermissionsAPI.remove(selectedRoleForPermissions.id, permissionId, companyId);
			toast.success('Permiso removido correctamente');
			await selectRoleForPermissions(selectedRoleForPermissions);
		} catch (error) {
			toast.error('Error al remover permiso');
			console.error(error);
		}
	}

	function togglePermission(permissionId: number) {
		if (selectedPermissionIds.includes(permissionId)) {
			selectedPermissionIds = selectedPermissionIds.filter((id) => id !== permissionId);
		} else {
			selectedPermissionIds = [...selectedPermissionIds, permissionId];
		}
	}


	// Cargar datos reactivamente cuando cambia la compañía
	$effect(() => {
		const companyId = companyStore.activeCompany?.id;
		if (companyId) {
			Promise.all([loadUsers(), loadStats(), loadRolesTab(), loadAllPermissionsForRoles()]);
		}
	});
</script>

<div class="container mx-auto py-6 space-y-6">
	<!-- Header -->
	<div class="flex justify-between items-center">
		<div>
			<h1 class="text-3xl font-bold">Gestión de Usuarios y Roles</h1>
			<p class="text-muted-foreground">Administra usuarios, roles y permisos de tu organización</p>
		</div>
	</div>

	<!-- Tabs -->
	<Tabs.Root value="usuarios" class="w-full">
		<Tabs.List class="grid w-full grid-cols-2">
			<Tabs.Trigger value="usuarios">
				<Users class="w-4 h-4 mr-2" />
				Usuarios
			</Tabs.Trigger>
			<Tabs.Trigger value="roles">
				<Shield class="w-4 h-4 mr-2" />
				Roles y Permisos
			</Tabs.Trigger>
		</Tabs.List>

		<!-- Tab: Usuarios -->
		<Tabs.Content value="usuarios" class="space-y-6 mt-6">
			<div class="flex justify-end">
				<Button onclick={() => showCreateDialog = true}>
					<Plus class="w-4 h-4 mr-2" />
					Nuevo Usuario
				</Button>
			</div>

	<!-- Estadísticas -->
	{#if stats}
		<div class="grid gap-4 md:grid-cols-4">
			<Card.Root>
				<Card.Header class="flex flex-row items-center justify-between space-y-0 pb-2">
					<Card.Title class="text-sm font-medium">Total Usuarios</Card.Title>
					<Users class="h-4 w-4 text-muted-foreground" />
				</Card.Header>
				<Card.Content>
					<div class="text-2xl font-bold">{stats.total_users}</div>
				</Card.Content>
			</Card.Root>

			<Card.Root>
				<Card.Header class="flex flex-row items-center justify-between space-y-0 pb-2">
					<Card.Title class="text-sm font-medium">Activos</Card.Title>
					<UserCheck class="h-4 w-4 text-green-600" />
				</Card.Header>
				<Card.Content>
					<div class="text-2xl font-bold text-green-600">{stats.active_users}</div>
				</Card.Content>
			</Card.Root>

			<Card.Root>
				<Card.Header class="flex flex-row items-center justify-between space-y-0 pb-2">
					<Card.Title class="text-sm font-medium">Disponibles</Card.Title>
					<AlertCircle class="h-4 w-4 text-blue-600" />
				</Card.Header>
				<Card.Content>
					<div class="text-2xl font-bold text-blue-600">{stats.users_available}</div>
					<p class="text-xs text-muted-foreground">de {stats.max_users_allowed} permitidos</p>
				</Card.Content>
			</Card.Root>

			<Card.Root>
				<Card.Header class="flex flex-row items-center justify-between space-y-0 pb-2">
					<Card.Title class="text-sm font-medium">Uso de Licencia</Card.Title>
				</Card.Header>
				<Card.Content>
					<div class="text-2xl font-bold">{stats.usage_percentage.toFixed(1)}%</div>
					<div class="w-full bg-gray-200 rounded-full h-2 mt-2">
						<div 
							class="h-2 rounded-full transition-all"
							class:bg-green-600={stats.usage_percentage < 70}
							class:bg-yellow-600={stats.usage_percentage >= 70 && stats.usage_percentage < 90}
							class:bg-red-600={stats.usage_percentage >= 90}
							style="width: {stats.usage_percentage}%"
						></div>
					</div>
				</Card.Content>
			</Card.Root>
		</div>
	{/if}

	<!-- Tabla de usuarios -->
	<Card.Root>
		<Card.Header>
			<div class="flex justify-between items-center">
				<Card.Title>Usuarios</Card.Title>
				<div class="flex gap-2">
					<div class="relative">
						<Search class="absolute left-3 top-1/2 transform -translate-y-1/2 h-4 w-4 text-muted-foreground" />
						<Input
							type="text"
							placeholder="Buscar usuarios..."
							bind:value={searchTerm}
							oninput={handleSearch}
							class="pl-10 w-64"
						/>
					</div>
					<Button variant="outline" size="icon" onclick={() => loadUsers()}>
						<RefreshCw class={`h-4 w-4 ${loading ? 'animate-spin' : ''}`} />
					</Button>
				</div>
			</div>
		</Card.Header>
		<Card.Content>
			<Table.Root>
				<Table.Header>
					<Table.Row>
						<Table.Head>Usuario</Table.Head>
						<Table.Head>Email</Table.Head>
						<Table.Head>Nombre</Table.Head>
						<Table.Head>Rol</Table.Head>
						<Table.Head>Estado</Table.Head>
						<Table.Head class="text-right">Acciones</Table.Head>
					</Table.Row>
				</Table.Header>
				<Table.Body>
					{#if loading && users.length === 0}
						<Table.Row>
							<Table.Cell colspan={6} class="text-center py-8">
								<RefreshCw class="h-8 w-8 animate-spin mx-auto text-muted-foreground" />
							</Table.Cell>
						</Table.Row>
					{:else if users.length === 0}
						<Table.Row>
							<Table.Cell colspan={6} class="text-center py-8 text-muted-foreground">
								No se encontraron usuarios
							</Table.Cell>
						</Table.Row>
					{:else}
						{#each users as user}
							<Table.Row>
								<Table.Cell class="font-medium">{user.username}</Table.Cell>
								<Table.Cell>
									<div class="flex items-center gap-2">
										{user.email}
										{#if user.email_verified}
											<Badge variant="outline" class="text-xs">Verificado</Badge>
										{/if}
									</div>
								</Table.Cell>
								<Table.Cell>{user.first_name} {user.last_name}</Table.Cell>
								<Table.Cell>
									{#if user.role}
										<div class="flex flex-wrap gap-1">
											{#each user.role.split(', ') as roleName}
												<Badge variant="secondary">{roleName}</Badge>
											{/each}
										</div>
									{:else}
										<span class="text-muted-foreground">-</span>
									{/if}
								</Table.Cell>
								<Table.Cell>
									{#if user.enabled}
										<Badge variant="default" class="bg-green-600">Activo</Badge>
									{:else}
										<Badge variant="destructive">Inactivo</Badge>
									{/if}
								</Table.Cell>
								<Table.Cell class="text-right">
									<div class="flex justify-end gap-2">
										<Tooltip.Root>
											<Tooltip.Trigger asChild>
												<Button 
													variant="ghost" 
													size="icon"
													onclick={() => openRolesDialog(user)}
													aria-label="Gestionar roles"
												>
													<Shield class="h-4 w-4" />
												</Button>
											</Tooltip.Trigger>
											<Tooltip.Content side="top">Gestionar roles</Tooltip.Content>
										</Tooltip.Root>
										<Tooltip.Root>
											<Tooltip.Trigger asChild>
												<Button 
													variant="ghost" 
													size="icon"
													onclick={() => openEditDialog(user)}
													aria-label="Editar usuario"
												>
													<Pencil class="h-4 w-4" />
												</Button>
											</Tooltip.Trigger>
											<Tooltip.Content side="top">Editar usuario</Tooltip.Content>
										</Tooltip.Root>
										<Tooltip.Root>
											<Tooltip.Trigger asChild>
												<Button 
													variant="ghost" 
													size="icon"
													onclick={() => openPasswordDialog(user)}
													aria-label="Restablecer contrasena"
												>
													<Key class="h-4 w-4" />
												</Button>
											</Tooltip.Trigger>
											<Tooltip.Content side="top">Restablecer contrasena</Tooltip.Content>
										</Tooltip.Root>
										<Tooltip.Root>
											<Tooltip.Trigger asChild>
												<Button 
													variant="ghost" 
													size="icon"
													onclick={() => openDeleteDialog(user)}
													aria-label="Eliminar usuario"
												>
													<Trash2 class="h-4 w-4 text-destructive" />
												</Button>
											</Tooltip.Trigger>
											<Tooltip.Content side="top">Eliminar usuario</Tooltip.Content>
										</Tooltip.Root>
									</div>
								</Table.Cell>
							</Table.Row>
						{/each}
					{/if}
				</Table.Body>
			</Table.Root>

			<!-- Paginación -->
			{#if totalPages > 1}
				<div class="flex items-center justify-between mt-4">
					<p class="text-sm text-muted-foreground">
						Página {currentPage} de {totalPages}
					</p>
					<div class="flex gap-2">
						<Button 
							variant="outline" 
							size="sm"
							disabled={currentPage === 1}
							onclick={() => goToPage(currentPage - 1)}
						>
							Anterior
						</Button>
						<Button 
							variant="outline" 
							size="sm"
							disabled={currentPage === totalPages}
							onclick={() => goToPage(currentPage + 1)}
						>
							Siguiente
						</Button>
					</div>
				</div>
			{/if}
		</Card.Content>
	</Card.Root>
		</Tabs.Content>

		<!-- Tab: Roles y Permisos -->
		<Tabs.Content value="roles" class="space-y-6 mt-6">
			<div class="grid grid-cols-1 lg:grid-cols-3 gap-6">
				<!-- Roles List -->
				<div class="lg:col-span-1">
					<div class="border rounded-lg p-4">
						<div class="flex items-center justify-between mb-4">
							<h2 class="text-lg font-semibold flex items-center gap-2">
								<Shield class="h-5 w-5" />
								Roles
							</h2>
							<Button size="sm" onclick={openCreateRoleDialog}>
								<Plus class="h-4 w-4" />
							</Button>
						</div>

						{#if loadingRoles}
							<p class="text-muted-foreground text-center py-4">Cargando...</p>
						{:else if rolesState.length === 0}
							<div class="text-center py-8">
								<p class="text-muted-foreground mb-4">No hay roles disponibles</p>
								<Button size="sm" onclick={openCreateRoleDialog}>
									<Plus class="mr-2 h-4 w-4" />
									Crear primer rol
								</Button>
							</div>
						{:else}
							<div class="space-y-2">
								{#each rolesState as role (role.id)}
									<div
										class="flex items-center gap-2 p-2 rounded-lg border {selectedRoleForPermissions?.id ===
										role.id
											? 'bg-primary/10 border-primary'
											: 'hover:bg-accent'}"
									>
										<Button
											variant="ghost"
											class="flex-1 justify-start h-auto p-2"
											onclick={() => selectRoleForPermissions(role)}
										>
											<div class="flex flex-col items-start gap-1 w-full">
												<div class="flex items-center gap-2 w-full">
													<Shield class="h-4 w-4 flex-shrink-0" />
													<span class="font-medium text-sm truncate">{role.name}</span>
												</div>
												{#if !role.is_active}
													<Badge variant="secondary" class="text-xs">Inactivo</Badge>
												{/if}
											</div>
										</Button>
										<div class="flex gap-1">
											<Button
												variant="ghost"
												size="sm"
												class="h-8 w-8 p-0"
												onclick={() => openEditRoleDialog(role)}
											>
												<Pencil class="h-3 w-3" />
											</Button>
											<Button
												variant="ghost"
												size="sm"
												class="h-8 w-8 p-0"
												onclick={() => handleDeleteRole(role)}
											>
												<Trash2 class="h-3 w-3" />
											</Button>
										</div>
									</div>
								{/each}
							</div>
						{/if}
					</div>
				</div>

				<!-- Permissions List -->
				<div class="lg:col-span-2">
					{#if selectedRoleForPermissions}
						<div class="border rounded-lg">
							<div class="p-4 border-b flex items-center justify-between">
								<div>
									<h2 class="text-lg font-semibold flex items-center gap-2">
										<Key class="h-5 w-5" />
										Permisos de "{selectedRoleForPermissions.name}"
									</h2>
									<p class="text-sm text-muted-foreground">
										{rolePermissionsState.length} permisos asignados
									</p>
								</div>
								<Button onclick={openAddPermissionsDialog} disabled={availablePermissionsState.length === 0}>
									<Plus class="mr-2 h-4 w-4" />
									Agregar Permisos
								</Button>
							</div>

							<Table.Root>
								<Table.Header>
									<Table.Row>
										<Table.Head class="w-[150px]">Módulo</Table.Head>
										<Table.Head class="w-[120px]">Acción</Table.Head>
										<Table.Head>Permiso</Table.Head>
										<Table.Head class="text-right w-[80px]">Acciones</Table.Head>
									</Table.Row>
								</Table.Header>
								<Table.Body>
									{#if loadingPermissionsState}
										<Table.Row>
											<Table.Cell colspan={4} class="text-center py-8">
												Cargando permisos...
											</Table.Cell>
										</Table.Row>
									{:else if rolePermissionsState.length === 0}
										<Table.Row>
											<Table.Cell colspan={4} class="text-center py-8">
												Este rol no tiene permisos asignados
											</Table.Cell>
										</Table.Row>
									{:else}
										{#each rolePermissionsState as rp (rp.id)}
											<Table.Row>
												<Table.Cell>
													<Badge variant="outline">{rp.permission?.module ? getModuleLabel(rp.permission.module) : '-'}</Badge>
												</Table.Cell>
												<Table.Cell>
													<span class="font-medium">{rp.permission?.action ? getActionLabel(rp.permission.action) : '-'}</span>
												</Table.Cell>
												<Table.Cell>
													{#if rp.permission}
														<div class="space-y-1">
															<div>{formatPermissionLabel(rp.permission)}</div>
															<code class="text-xs text-muted-foreground">{rp.permission.code}</code>
														</div>
													{:else}
														<span class="text-muted-foreground">-</span>
													{/if}
												</Table.Cell>
												<Table.Cell class="text-right">
													<Button
														variant="ghost"
														size="sm"
														onclick={() => handleRemovePermission(rp.permission_id)}
														title="Quitar permiso"
													>
														<Trash2 class="h-4 w-4" />
													</Button>
												</Table.Cell>
											</Table.Row>
										{/each}
									{/if}
								</Table.Body>
							</Table.Root>
						</div>
					{:else}
						<div class="border rounded-lg p-12 text-center">
							<Shield class="h-12 w-12 mx-auto mb-4 text-muted-foreground" />
							<p class="text-muted-foreground">Selecciona un rol para ver sus permisos</p>
						</div>
					{/if}
				</div>
			</div>
		</Tabs.Content>
	</Tabs.Root>
</div>

<!-- ========================================
     DIÁLOGOS - USUARIOS
     ======================================== -->
<Dialog.Root bind:open={showCreateDialog}>
	<Dialog.Content class="max-w-md">
		<Dialog.Header>
			<Dialog.Title>Crear Nuevo Usuario</Dialog.Title>
			<Dialog.Description>
				Ingresa la información del nuevo usuario. Se enviará un correo para configurar su contraseña.
			</Dialog.Description>
		</Dialog.Header>
		<div class="space-y-4">
			<div class="grid grid-cols-2 gap-4">
				<div class="space-y-2">
					<Label for="first_name">Nombre *</Label>
					<Input id="first_name" bind:value={createForm.first_name} required />
				</div>
				<div class="space-y-2">
					<Label for="last_name">Apellido *</Label>
					<Input id="last_name" bind:value={createForm.last_name} required />
				</div>
			</div>
			<div class="space-y-2">
				<Label for="username">Usuario *</Label>
				<Input id="username" bind:value={createForm.username} required />
			</div>
			<div class="space-y-2">
				<Label for="email">Email *</Label>
				<Input id="email" type="email" bind:value={createForm.email} required />
			</div>
			<div class="space-y-2">
				<Label for="password">Contraseña Temporal *</Label>
				<Input id="password" type="password" bind:value={createForm.password} required />
				<p class="text-xs text-muted-foreground">Mínimo 8 caracteres</p>
			</div>
		</div>
		<Dialog.Footer>
			<Button variant="outline" onclick={() => showCreateDialog = false}>Cancelar</Button>
			<Button onclick={handleCreate}>Crear Usuario</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Diálogo Editar Usuario -->
<Dialog.Root bind:open={showEditDialog}>
	<Dialog.Content class="max-w-md">
		<Dialog.Header>
			<Dialog.Title>Editar Usuario</Dialog.Title>
			<Dialog.Description>
				Modifica la información del usuario {selectedUser?.username}
			</Dialog.Description>
		</Dialog.Header>
		<div class="space-y-4">
			<div class="grid grid-cols-2 gap-4">
				<div class="space-y-2">
					<Label for="edit_first_name">Nombre</Label>
					<Input id="edit_first_name" bind:value={editForm.first_name} />
				</div>
				<div class="space-y-2">
					<Label for="edit_last_name">Apellido</Label>
					<Input id="edit_last_name" bind:value={editForm.last_name} />
				</div>
			</div>
			<div class="space-y-2">
				<Label for="edit_email">Email</Label>
				<Input id="edit_email" type="email" bind:value={editForm.email} />
			</div>
			<div class="flex items-center space-x-2">
				<input type="checkbox" id="edit_enabled" bind:checked={editForm.enabled} class="h-4 w-4" />
				<Label for="edit_enabled">Usuario activo</Label>
			</div>
			<div class="flex items-center space-x-2">
				<input type="checkbox" id="edit_email_verified" bind:checked={editForm.email_verified} class="h-4 w-4" />
				<Label for="edit_email_verified">Email verificado</Label>
			</div>
		</div>
		<Dialog.Footer>
			<Button variant="outline" onclick={() => showEditDialog = false}>Cancelar</Button>
			<Button onclick={handleUpdate}>Guardar Cambios</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Diálogo Cambiar Contraseña -->
<Dialog.Root bind:open={showPasswordDialog}>
	<Dialog.Content class="max-w-md">
		<Dialog.Header>
			<Dialog.Title>Cambiar Contraseña</Dialog.Title>
			<Dialog.Description>
				Establece una nueva contraseña para {selectedUser?.username}
			</Dialog.Description>
		</Dialog.Header>
		<div class="space-y-4">
			<div class="space-y-2">
				<Label for="new_password">Nueva Contraseña</Label>
				<Input id="new_password" type="password" bind:value={passwordForm.password} />
			</div>
			<div class="space-y-2">
				<Label for="confirm_password">Confirmar Contraseña</Label>
				<Input id="confirm_password" type="password" bind:value={passwordForm.confirmPassword} />
			</div>
			<div class="flex items-center space-x-2">
				<input type="checkbox" id="temporary" bind:checked={passwordForm.temporary} class="h-4 w-4" />
				<Label for="temporary">Contraseña temporal (debe cambiarla al iniciar sesión)</Label>
			</div>
		</div>
		<Dialog.Footer>
			<Button variant="outline" onclick={() => showPasswordDialog = false}>Cancelar</Button>
			<Button onclick={handleChangePassword}>Cambiar Contraseña</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Diálogo Eliminar Usuario -->
<AlertDialog.Root bind:open={showDeleteDialog}>
	<AlertDialog.Content>
		<AlertDialog.Header>
			<AlertDialog.Title>¿Eliminar usuario?</AlertDialog.Title>
			<AlertDialog.Description>
				¿Estás seguro de que deseas eliminar a {selectedUser?.username}?
				<br /><br />
				Puedes desactivar el usuario (recomendado) o eliminarlo permanentemente.
			</AlertDialog.Description>
		</AlertDialog.Header>
		<AlertDialog.Footer>
			<AlertDialog.Cancel>Cancelar</AlertDialog.Cancel>
			<Button variant="outline" onclick={() => handleDelete(true)}>
				<UserX class="w-4 h-4 mr-2" />
				Desactivar
			</Button>
			<AlertDialog.Action onclick={() => handleDelete(false)} class="bg-destructive text-destructive-foreground hover:bg-destructive/90">
				<Trash2 class="w-4 h-4 mr-2" />
				Eliminar Permanente
			</AlertDialog.Action>
		</AlertDialog.Footer>
	</AlertDialog.Content>
</AlertDialog.Root>
<!-- Diálogo Gestión de Roles -->
<Dialog.Root bind:open={showRolesDialog}>
	<Dialog.Content class="max-w-2xl">
		<Dialog.Header>
			<Dialog.Title>Gestionar Roles - {selectedUser?.username}</Dialog.Title>
			<Dialog.Description>
				Asigna o remueve roles para este usuario
			</Dialog.Description>
		</Dialog.Header>

		<div class="space-y-6 py-4">
			<!-- Lista de roles asignados -->
			<div class="space-y-2">
				<Label>Roles Asignados</Label>
				{#if loadingRoles}
					<div class="flex items-center justify-center py-8">
						<RefreshCw class="h-6 w-6 animate-spin text-muted-foreground" />
					</div>
				{:else if userRoles.length === 0}
					<div class="text-center py-8 text-muted-foreground">
						Este usuario no tiene roles asignados
					</div>
				{:else}
					<div class="space-y-2">
						{#each userRoles as userRole}
							<div class="flex items-center justify-between p-3 border rounded-lg">
								<div class="flex items-center gap-3">
									<Shield class="h-5 w-5 text-primary" />
									<div>
									<div class="font-medium">{userRole.company_role?.name || 'Rol desconocido'}</div>
										<div class="text-sm text-muted-foreground">
										Asignado el {new Date(userRole.created_at).toLocaleDateString()}
										</div>
									</div>
								</div>
								<Button 
									variant="ghost" 
									size="sm"
									onclick={() => removeRole(userRole.id)}
								>
									<Trash2 class="h-4 w-4 text-destructive" />
								</Button>
							</div>
						{/each}
					</div>
				{/if}
			</div>
			
			<!-- Asignar nuevo rol -->
			<div class="space-y-2">
				<Label>Asignar Nuevo Rol</Label>
				{#if unassignedRoles.length === 0}
					<p class="text-sm text-muted-foreground">
						No hay roles disponibles. Para cambiar de rol, primero remueve el rol actual usando el botón de eliminar arriba.
					</p>
				{:else}
					<div class="flex gap-2">
						<Select.Root
							type="single"
							value={typeof selectedRoleId === 'number' ? selectedRoleId.toString() : selectedRoleId}
							onValueChange={(v: string | undefined) => selectedRoleId = v ? parseInt(v) : 0}
						>
							<Select.Trigger class="flex-1">
								{selectedRoleId && selectedRoleId !== 0 
									? availableRoles.find(r => r.id === (typeof selectedRoleId === 'string' ? parseInt(selectedRoleId) : selectedRoleId))?.name || 'Selecciona un rol' 
									: 'Selecciona un rol'}
							</Select.Trigger>
							<Select.Content>
								{#each unassignedRoles as role}
									<Select.Item value={role.id.toString()}>{role.name}</Select.Item>
								{/each}
							</Select.Content>
						</Select.Root>
						<Button onclick={assignRole} disabled={!selectedRoleId || selectedRoleId === 0}>
							<Plus class="h-4 w-4 mr-2" />
							Asignar
						</Button>
					</div>
				{/if}
			</div>
		</div>

		<Dialog.Footer class="flex justify-between">
			<Button variant="outline" onclick={() => {
				if (selectedUser) {
					loadUserEffectivePermissions().then(() => {
						showRolesDialog = false;
						showUserPermissionsDialog = true;
					});
				}
			}}>
				<Key class="h-4 w-4 mr-2" />
				Permisos Individuales
			</Button>
			<Button variant="outline" onclick={() => showRolesDialog = false}>Cerrar</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Diálogo Permisos Individuales de Usuario -->
<Dialog.Root bind:open={showUserPermissionsDialog}>
	<Dialog.Content class="max-w-3xl max-h-[85vh] overflow-hidden flex flex-col">
		<Dialog.Header>
			<Dialog.Title>Permisos Individuales - {selectedUser?.username}</Dialog.Title>
			<Dialog.Description>
				Concede permisos extra o revoca permisos del rol para este usuario específico
			</Dialog.Description>
		</Dialog.Header>

		<div class="overflow-y-auto flex-1 space-y-4 py-4">
			{#if loadingUserPermissions}
				<div class="flex items-center justify-center py-12">
					<RefreshCw class="h-8 w-8 animate-spin text-muted-foreground" />
				</div>
			{:else if effectivePermissions}
				<!-- Resumen de permisos -->
				<div class="grid grid-cols-3 gap-3 p-4 bg-accent/50 rounded-lg">
					<div class="text-center">
						<div class="text-2xl font-bold text-primary">{effectivePermissions.role_permissions.length}</div>
						<div class="text-xs text-muted-foreground">Del Rol</div>
					</div>
					<div class="text-center">
						<div class="text-2xl font-bold text-green-600">{effectivePermissions.granted_permissions.length}</div>
						<div class="text-xs text-muted-foreground">Concedidos Extra</div>
					</div>
					<div class="text-center">
						<div class="text-2xl font-bold text-destructive">{effectivePermissions.revoked_permissions.length}</div>
						<div class="text-xs text-muted-foreground">Revocados</div>
					</div>
				</div>

				<!-- Permisos Concedidos Extra -->
				{#if effectivePermissions.granted_permissions.length > 0}
					<div class="space-y-2">
						<div class="flex items-center justify-between">
							<Label class="text-green-600 flex items-center gap-2">
								<Plus class="h-4 w-4" />
								Permisos Extra Concedidos
							</Label>
							<Badge variant="secondary">{effectivePermissions.granted_permissions.length}</Badge>
						</div>
						<div class="space-y-1 border rounded-lg p-2 max-h-48 overflow-y-auto">
							{#each effectivePermissions.granted_permissions as perm}
								<div class="flex items-center justify-between px-3 py-2 hover:bg-accent/50 rounded">
									<div class="flex-1 min-w-0">
										<div class="text-sm font-medium truncate">{formatPermissionLabel(perm)}</div>
										<code class="text-xs text-muted-foreground">{perm.code}</code>
									</div>
									<Button
										variant="ghost"
										size="sm"
										onclick={() => handleRemoveUserPermission(perm.id)}
										title="Eliminar permiso individual"
									>
										<Trash2 class="h-3 w-3 text-destructive" />
									</Button>
								</div>
							{/each}
						</div>
					</div>
				{/if}

				<!-- Permisos Revocados -->
				{#if effectivePermissions.revoked_permissions.length > 0}
					<div class="space-y-2">
						<div class="flex items-center justify-between">
							<Label class="text-destructive flex items-center gap-2">
								<AlertCircle class="h-4 w-4" />
								Permisos Revocados del Rol
							</Label>
							<Badge variant="destructive">{effectivePermissions.revoked_permissions.length}</Badge>
						</div>
						<div class="space-y-1 border rounded-lg p-2 max-h-48 overflow-y-auto">
							{#each effectivePermissions.revoked_permissions as perm}
								<div class="flex items-center justify-between px-3 py-2 hover:bg-accent/50 rounded">
									<div class="flex-1 min-w-0">
										<div class="text-sm font-medium line-through truncate">{formatPermissionLabel(perm)}</div>
										<code class="text-xs text-muted-foreground">{perm.code}</code>
									</div>
									<Button
										variant="ghost"
										size="sm"
										onclick={() => handleRemoveUserPermission(perm.id)}
										title="Eliminar revocación (restaurar permiso)"
									>
										<Trash2 class="h-3 w-3" />
									</Button>
								</div>
							{/each}
						</div>
					</div>
				{/if}

				<!-- Permisos del Rol (solo info + opción de revocar) -->
				{#if effectivePermissions.role_permissions.length > 0}
					<div class="space-y-2 pt-4 border-t">
						<div class="flex items-center justify-between">
							<Label class="text-muted-foreground">Permisos Heredados del Rol</Label>
							<Badge variant="outline">{effectivePermissions.role_permissions.length}</Badge>
						</div>
						<div class="text-xs text-muted-foreground space-y-1 max-h-48 overflow-y-auto border rounded-lg p-2">
							{#each effectivePermissions.role_permissions as perm}
								<div class="flex items-center justify-between px-2 py-1 hover:bg-accent/30 rounded">
									<div class="flex-1 min-w-0 truncate">
										{formatPermissionLabel(perm)}
									</div>
									{#if !effectivePermissions.revoked_permissions.some(r => r.id === perm.id)}
										<Button
											variant="ghost"
											size="sm"
											onclick={() => handleRevokeUserPermission(perm.id)}
											title="Revocar este permiso para este usuario"
										>
											<span class="text-xs text-destructive">Revocar</span>
										</Button>
									{/if}
								</div>
							{/each}
						</div>
					</div>
				{/if}
			{/if}
		</div>

		<Dialog.Footer class="flex-shrink-0">
			<Button variant="outline" onclick={() => {
				showUserPermissionsDialog = false;
				showRolesDialog = true;
			}}>
				Volver a Roles
			</Button>
			<div class="flex-1"></div>
			<Button variant="default" onclick={() => {
				showUserPermissionsDialog = false;
				openGrantUserPermDialog();
			}}>
				<Plus class="h-4 w-4 mr-2" />
				Conceder Permisos
			</Button>
			<Button onclick={() => showUserPermissionsDialog = false}>Cerrar</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- ========================================
     DIÁLOGOS - ROLES Y PERMISOS
     ======================================== -->

<!-- Diálogo Conceder Permisos a Usuario -->
<Dialog.Root bind:open={showGrantUserPermDialog}>
	<Dialog.Content class="max-w-2xl max-h-[80vh] overflow-hidden flex flex-col">
		<Dialog.Header>
			<Dialog.Title>Conceder Permisos Extra a {selectedUser?.username}</Dialog.Title>
			<Dialog.Description>
				Selecciona los permisos adicionales que este usuario tendrá (además de su rol)
			</Dialog.Description>
		</Dialog.Header>

		<div class="overflow-y-auto flex-1 py-4">
			<div class="px-4 pb-2">
				<Input
					type="text"
					placeholder="Buscar permisos..."
					bind:value={permissionSearchQuery}
					class="w-full"
				/>
			</div>

			{#if availablePermissionsForUser.length === 0}
				<p class="text-center text-muted-foreground py-8">
					No hay permisos disponibles para conceder
				</p>
			{:else}
				<div class="space-y-4">
					{#each [...availablePermissionsForUser.reduce((map, p) => {
						const module = p.module;
						if (!map.has(module)) map.set(module, []);
						map.get(module).push(p);
						return map;
					}, new Map())] as [module, permissions] (module)}
						<div class="border rounded-lg p-4">
							<h3 class="font-semibold mb-3 flex items-center gap-2">
								<Badge variant="secondary">{getModuleLabel(module)}</Badge>
								<span class="text-xs text-muted-foreground">({permissions.length} {permissions.length === 1 ? 'permiso' : 'permisos'})</span>
							</h3>
							<div class="space-y-2">
								{#each permissions as permission (permission.id)}
									{#if !permissionSearchQuery || formatPermissionLabel(permission).toLowerCase().includes(permissionSearchQuery.toLowerCase()) || permission.code.toLowerCase().includes(permissionSearchQuery.toLowerCase())}
										<div class="flex items-start space-x-3 p-2 rounded hover:bg-accent/50 transition-colors">
											<Checkbox
												id="user-perm-{permission.id}"
												checked={selectedUserPermissionIds.includes(permission.id)}
												onCheckedChange={() => toggleUserPermission(permission.id)}
											/>
											<div class="flex-1 min-w-0">
												<Label
													for="user-perm-{permission.id}"
													class="text-sm font-medium leading-none cursor-pointer block"
													title={getPermissionHint(permission)}
												>
													{formatPermissionLabel(permission)}
												</Label>
												<div class="flex items-center gap-2 mt-1.5">
													<Badge variant="outline" class="text-xs font-mono">{getActionLabel(permission.action)}</Badge>
													<code class="text-xs text-muted-foreground truncate">{permission.code}</code>
												</div>
											</div>
										</div>
									{/if}
								{/each}
							</div>
						</div>
					{/each}
				</div>
			{/if}
		</div>

		<Dialog.Footer class="flex-shrink-0">
			<Button variant="outline" onclick={() => showGrantUserPermDialog = false}>Cancelar</Button>
			<Button onclick={handleGrantUserPermissions} disabled={selectedUserPermissionIds.length === 0}>
				Conceder {selectedUserPermissionIds.length} permiso(s)
			</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Add Permissions Dialog -->
<Dialog.Root bind:open={showPermissionsDialog}>
	<Dialog.Content class="max-w-2xl max-h-[80vh]">
		<Dialog.Header>
			<Dialog.Title>Agregar Permisos a "{selectedRoleForPermissions?.name}"</Dialog.Title>
		</Dialog.Header>

		<div class="overflow-y-auto max-h-96 py-4">
			<div class="px-4 pb-2">
				<Input
					type="text"
					placeholder="Buscar permisos..."
					bind:value={permissionSearchQuery}
					oninput={() => updatePermissionsByModuleForRole()}
					class="w-full"
				/>
			</div>

			{#if availablePermissionsState.length === 0}
				<p class="text-center text-muted-foreground py-8">
					No hay permisos disponibles para asignar
				</p>
			{:else}
				<div class="space-y-4">
					{#each [...permissionsByModuleState] as [module, permissions] (module)}
						<div class="border rounded-lg p-4">
							<h3 class="font-semibold mb-3 flex items-center gap-2">
								<Badge variant="secondary">{getModuleLabel(module)}</Badge>
								<span class="text-xs text-muted-foreground">({permissions.length} {permissions.length === 1 ? 'permiso' : 'permisos'})</span>
							</h3>
							<div class="space-y-2">
								{#each permissions as permission (permission.id)}
									<div class="flex items-start space-x-3 p-2 rounded hover:bg-accent/50 transition-colors">
										<Checkbox
											id="perm-{permission.id}"
											checked={selectedPermissionIds.includes(permission.id)}
											onCheckedChange={() => togglePermission(permission.id)}
										/>
										<div class="flex-1 min-w-0">
											<Label
												for="perm-{permission.id}"
												class="text-sm font-medium leading-none cursor-pointer block"
												title={getPermissionHint(permission)}
											>
												{formatPermissionLabel(permission)}
											</Label>
											<div class="flex items-center gap-2 mt-1.5">
												<Badge variant="outline" class="text-xs font-mono">{getActionLabel(permission.action)}</Badge>
												<code class="text-xs text-muted-foreground truncate">{permission.code}</code>
											</div>
										</div>
									</div>
								{/each}
							</div>
						</div>
					{/each}
				</div>
			{/if}
		</div>

		<Dialog.Footer>
			<Button variant="outline" onclick={() => (showPermissionsDialog = false)}>Cancelar</Button>
			<Button onclick={handleAssignPermissions} disabled={selectedPermissionIds.length === 0}>
				Asignar {selectedPermissionIds.length} permisos
			</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Create/Edit Role Dialog -->
<Dialog.Root bind:open={showRoleDialog}>
	<Dialog.Content>
		<Dialog.Header>
			<Dialog.Title>
				{editingRole ? 'Editar Rol' : 'Nuevo Rol'}
			</Dialog.Title>
		</Dialog.Header>

		<div class="grid gap-4 py-4">
			<div class="grid gap-2">
				<Label for="role-name">Nombre</Label>
				<Input id="role-name" bind:value={roleFormData.name} placeholder="Administrador" />
			</div>

			<div class="grid gap-2">
				<Label for="role-code">Código</Label>
				<Input id="role-code" bind:value={roleFormData.code} placeholder="ADMIN" />
			</div>

			<div class="grid gap-2">
				<Label for="role-description">Descripción</Label>
				<Textarea
					id="role-description"
					bind:value={roleFormData.description}
					placeholder="Rol con acceso completo al sistema"
				/>
			</div>

			<div class="flex items-center space-x-2">
				<Switch id="role-is_active" bind:checked={roleFormData.is_active} />
				<Label for="role-is_active">Activo</Label>
			</div>
		</div>

		<Dialog.Footer>
			<Button variant="outline" onclick={() => (showRoleDialog = false)}>Cancelar</Button>
			<Button onclick={handleRoleSubmit}>
				{editingRole ? 'Actualizar' : 'Crear'}
			</Button>
		</Dialog.Footer>
	</Dialog.Content>
</Dialog.Root>

<!-- Delete Role Confirmation Dialog -->
<AlertDialog.Root bind:open={showDeleteRoleDialog}>
	<AlertDialog.Content>
		<AlertDialog.Header>
			<AlertDialog.Title>¿Eliminar rol permanentemente?</AlertDialog.Title>
			<AlertDialog.Description>
				{#if roleToDelete}
					Estás a punto de eliminar el rol <strong>"{roleToDelete.name}"</strong> de forma permanente.
					<br /><br />
					Esta acción <strong class="text-destructive">NO se puede deshacer</strong> y el rol será eliminado completamente del sistema.
					<br /><br />
					{#if rolePermissionsState.length > 0 && selectedRoleForPermissions?.id === roleToDelete.id}
						<span class="text-muted-foreground">Este rol tiene {rolePermissionsState.length} {rolePermissionsState.length === 1 ? 'permiso asignado' : 'permisos asignados'}.</span>
					{/if}
					<br />
					Si solo deseas desactivarlo temporalmente, usa el interruptor "Activo" en el modo de edición.
				{/if}
			</AlertDialog.Description>
		</AlertDialog.Header>
		<AlertDialog.Footer>
			<AlertDialog.Cancel>Cancelar</AlertDialog.Cancel>
			<AlertDialog.Action onclick={confirmDeleteRole} class="bg-destructive hover:bg-destructive/90">
				Eliminar permanentemente
			</AlertDialog.Action>
		</AlertDialog.Footer>
	</AlertDialog.Content>
</AlertDialog.Root>
