<script lang="ts">
	import { invalidateAll } from '$app/navigation';
	import type { PageData } from './$types';
	import { ContentContainer } from '$lib/components/layout';
	import { MonthSelector, AdminDashboardHeader } from '$lib/components/admin';
	import { client } from '$lib/graphql/client';
	import {
		ASSIGN_SERVICE_TEAM_MEMBER,
		REMOVE_SERVICE_TEAM_MEMBER,
		DELETE_SERVICE
	} from '$lib/graphql/mutations/service';
	import GenerateServicesModal from '$lib/components/admin/services/GenerateServicesModal.svelte';
	import type { ServiceForAssignment, ServiceTeamMember } from '$lib/graphql/queries/services';
	import type { TeamProfile } from '$lib/graphql/queries/team';

	let { data }: { data: PageData } = $props();

	// Modal states
	let showGenerateModal = $state(false);
	let showDeleteConfirm = $state(false);
	let serviceToDelete = $state<ServiceForAssignment | null>(null);
	let processingDelete = $state(false);

	// Local state for services (to update UI immediately)
	let unassigned = $state<ServiceForAssignment[]>([]);
	let readyToAssign = $state<ServiceForAssignment[]>([]);
	let assigned = $state<ServiceForAssignment[]>([]);

	// Initialize from data
	$effect(() => {
		unassigned = [...data.services.unassigned];
		readyToAssign = [...data.services.readyToAssign];
		assigned = [...data.services.assigned];
	});

	// Selection state per column
	let selectedUnassigned = $state<Set<string>>(new Set());
	let selectedReadyToAssign = $state<Set<string>>(new Set());
	let selectedAssigned = $state<Set<string>>(new Set());

	// Loading states
	let processingDispatch = $state(false);
	let processingAssign = $state(false);
	let processingRemove = $state(false);
	let processingRemoveDispatch = $state(false);

	// Expanded service for granular team management in Assigned column
	let expandedServiceForTeam = $state<string | null>(null);
	let addingTeamMemberTo = $state<string | null>(null);
	let newTeamMemberForService = $state<string>('');

	// Team member selection for assign action
	let selectedTeamMember = $state<string>('');

	// Grouping mode
	type GroupMode = 'date' | 'week' | 'account';
	let groupMode = $state<GroupMode>('date');

	// Team profiles from data
	let teamProfiles = $derived(data.teamProfiles);

	// Current user (admin) for dispatch - passed from server
	let currentUserId = $derived(data.currentUserProfileId);

	// Helper functions
	function formatDate(dateStr: string): string {
		const date = new Date(dateStr + 'T00:00:00');
		return date.toLocaleDateString('en-US', {
			weekday: 'short',
			month: 'short',
			day: 'numeric'
		});
	}

	function formatAddress(
		address: { name: string | null; city: string; state: string } | null
	): string {
		if (!address) return '';
		if (address.name) return `${address.name} - ${address.city}, ${address.state}`;
		return `${address.city}, ${address.state}`;
	}

	function getTeamMemberNames(teamMembers: ServiceTeamMember[]): string {
		return teamMembers
			.filter((m) => m.teamProfile?.role !== 'ADMIN')
			.map((m) => m.teamProfile?.fullName ?? '')
			.filter(Boolean)
			.join(', ');
	}

	// Selection helpers
	function toggleSelection(set: Set<string>, id: string): Set<string> {
		const newSet = new Set(set);
		if (newSet.has(id)) {
			newSet.delete(id);
		} else {
			newSet.add(id);
		}
		return newSet;
	}

	function selectAll(list: ServiceForAssignment[]): Set<string> {
		return new Set(list.map((s) => s.id));
	}

	function clearSelection(): Set<string> {
		return new Set();
	}

	// Bulk actions
	async function handleAddDispatch() {
		if (selectedUnassigned.size === 0 || !currentUserId) return;
		processingDispatch = true;

		for (const serviceId of selectedUnassigned) {
			try {
				await client.mutate({
					mutation: ASSIGN_SERVICE_TEAM_MEMBER,
					variables: { serviceId, teamProfileId: currentUserId }
				});
			} catch (e) {
				console.error('Failed to assign dispatch:', e);
			}
		}

		selectedUnassigned = new Set();
		processingDispatch = false;
		invalidateAll();
	}

	async function handleAssignTeamMember() {
		if (selectedReadyToAssign.size === 0 || !selectedTeamMember) return;
		processingAssign = true;

		for (const serviceId of selectedReadyToAssign) {
			try {
				await client.mutate({
					mutation: ASSIGN_SERVICE_TEAM_MEMBER,
					variables: { serviceId, teamProfileId: selectedTeamMember }
				});
			} catch (e) {
				console.error('Failed to assign team member:', e);
			}
		}

		selectedReadyToAssign = new Set();
		selectedTeamMember = '';
		processingAssign = false;
		invalidateAll();
	}

	async function handleRemoveNonDispatch() {
		if (selectedAssigned.size === 0) return;
		processingRemove = true;

		for (const serviceId of selectedAssigned) {
			const service = assigned.find((s) => s.id === serviceId);
			if (!service) continue;

			// Remove all team members except the dispatcher (admin/team leader who dispatched)
			// Keep anyone with ADMIN role OR the current user (who may be a TEAM_LEADER dispatcher)
			for (const member of service.teamMembers) {
				const isAdmin = member.teamProfile?.role === 'ADMIN';
				const isCurrentUser = member.teamProfileId === currentUserId;
				if (!isAdmin && !isCurrentUser) {
					try {
						await client.mutate({
							mutation: REMOVE_SERVICE_TEAM_MEMBER,
							variables: { id: member.id }
						});
					} catch (e) {
						console.error('Failed to remove team member:', e);
					}
				}
			}
		}

		selectedAssigned = new Set();
		processingRemove = false;
		invalidateAll();
	}

	// Remove dispatch - moves from Dispatched back to Unassigned
	async function handleRemoveDispatch() {
		if (selectedReadyToAssign.size === 0) return;
		processingRemoveDispatch = true;

		for (const serviceId of selectedReadyToAssign) {
			const service = readyToAssign.find((s) => s.id === serviceId);
			if (!service) continue;

			// Remove ALL team members (including dispatch)
			for (const member of service.teamMembers) {
				try {
					await client.mutate({
						mutation: REMOVE_SERVICE_TEAM_MEMBER,
						variables: { id: member.id }
					});
				} catch (e) {
					console.error('Failed to remove dispatch:', e);
				}
			}
		}

		selectedReadyToAssign = new Set();
		processingRemoveDispatch = false;
		invalidateAll();
	}

	// Granular team member management for Assigned services
	async function handleAddTeamMemberToService(serviceId: string) {
		if (!newTeamMemberForService) return;

		try {
			await client.mutate({
				mutation: ASSIGN_SERVICE_TEAM_MEMBER,
				variables: { serviceId, teamProfileId: newTeamMemberForService }
			});
			newTeamMemberForService = '';
			addingTeamMemberTo = null;
			invalidateAll();
		} catch (e) {
			console.error('Failed to add team member:', e);
		}
	}

	async function handleRemoveTeamMemberFromService(memberId: string) {
		try {
			await client.mutate({
				mutation: REMOVE_SERVICE_TEAM_MEMBER,
				variables: { id: memberId }
			});
			invalidateAll();
		} catch (e) {
			console.error('Failed to remove team member:', e);
		}
	}

	// Delete service
	function promptDeleteService(service: ServiceForAssignment) {
		serviceToDelete = service;
		showDeleteConfirm = true;
	}

	async function confirmDeleteService() {
		if (!serviceToDelete) return;
		processingDelete = true;

		try {
			await client.mutate({
				mutation: DELETE_SERVICE,
				variables: { id: serviceToDelete.id }
			});
			showDeleteConfirm = false;
			serviceToDelete = null;
			invalidateAll();
		} catch (e) {
			console.error('Failed to delete service:', e);
			alert('Failed to delete service');
		} finally {
			processingDelete = false;
		}
	}

	function cancelDelete() {
		showDeleteConfirm = false;
		serviceToDelete = null;
	}

	// Generate services success
	function handleGenerateSuccess() {
		showGenerateModal = false;
		invalidateAll();
	}

	// Grouping
	function groupServices(
		services: ServiceForAssignment[],
		mode: GroupMode
	): Map<string, ServiceForAssignment[]> {
		const groups = new Map<string, ServiceForAssignment[]>();

		for (const service of services) {
			let key: string;
			switch (mode) {
				case 'date':
					key = service.date;
					break;
				case 'week': {
					const date = new Date(service.date + 'T00:00:00');
					const startOfWeek = new Date(date);
					startOfWeek.setDate(date.getDate() - date.getDay());
					key = startOfWeek.toISOString().split('T')[0];
					break;
				}
				case 'account':
					key = service.account?.name ?? 'Unknown';
					break;
			}

			if (!groups.has(key)) {
				groups.set(key, []);
			}
			groups.get(key)!.push(service);
		}

		return groups;
	}

	function formatGroupKey(key: string, mode: GroupMode): string {
		switch (mode) {
			case 'date':
				return formatDate(key);
			case 'week': {
				const date = new Date(key + 'T00:00:00');
				const endDate = new Date(date);
				endDate.setDate(date.getDate() + 6);
				return `${formatDate(key)} - ${formatDate(endDate.toISOString().split('T')[0])}`;
			}
			case 'account':
				return key;
		}
	}

	// Derived grouped services
	let groupedUnassigned = $derived(groupServices(unassigned, groupMode));
	let groupedReadyToAssign = $derived(groupServices(readyToAssign, groupMode));
	let groupedAssigned = $derived(groupServices(assigned, groupMode));

	// Expanded state for each column's groups
	let expandedUnassigned = $state<Set<string>>(new Set());
	let expandedReadyToAssign = $state<Set<string>>(new Set());
	let expandedAssigned = $state<Set<string>>(new Set());

	// Reset expanded state when group mode changes
	$effect(() => {
		// Reference groupMode to create dependency
		const _ = groupMode;
		expandedUnassigned = new Set();
		expandedReadyToAssign = new Set();
		expandedAssigned = new Set();
	});

	function toggleExpanded(set: Set<string>, key: string): Set<string> {
		const newSet = new Set(set);
		if (newSet.has(key)) {
			newSet.delete(key);
		} else {
			newSet.add(key);
		}
		return newSet;
	}

	function expandAll(groups: Map<string, ServiceForAssignment[]>): Set<string> {
		return new Set(groups.keys());
	}

	function collapseAll(): Set<string> {
		return new Set();
	}
</script>

<svelte:head>
	<title>Bulk Assign Services - Admin - Nexus</title>
</svelte:head>

<div class="py-8">
	<ContentContainer>
		<!-- Header -->
		<AdminDashboardHeader
			title="Bulk Assign Services"
			subtitle="Assign team members to services for {data.month}"
			backHref="/admin/services"
		>
			{#snippet actions()}
				<button
					type="button"
					class="btn-secondary inline-flex items-center justify-center gap-2"
					onclick={() => (showGenerateModal = true)}
				>
					<svg class="h-5 w-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
						<path
							stroke-linecap="round"
							stroke-linejoin="round"
							stroke-width="2"
							d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5a2 2 0 00-2 2v12a2 2 0 002 2z"
						/>
					</svg>
					Generate
				</button>
			{/snippet}
		</AdminDashboardHeader>

		<!-- Controls -->
		<div class="mb-6 flex flex-wrap items-center gap-4">
			<MonthSelector month={data.month} />

			<!-- Grouping Toggle -->
			<div class="flex items-center gap-2">
				<span class="text-sm text-theme-secondary">Group by:</span>
				<div class="flex rounded-lg border border-theme bg-theme p-1">
					<button
						type="button"
						class="rounded-md px-3 py-1 text-sm {groupMode === 'date'
							? 'bg-primary-500 text-white'
							: 'text-theme-secondary hover:text-theme'}"
						onclick={() => (groupMode = 'date')}
					>
						Date
					</button>
					<button
						type="button"
						class="rounded-md px-3 py-1 text-sm {groupMode === 'week'
							? 'bg-primary-500 text-white'
							: 'text-theme-secondary hover:text-theme'}"
						onclick={() => (groupMode = 'week')}
					>
						Week
					</button>
					<button
						type="button"
						class="rounded-md px-3 py-1 text-sm {groupMode === 'account'
							? 'bg-primary-500 text-white'
							: 'text-theme-secondary hover:text-theme'}"
						onclick={() => (groupMode = 'account')}
					>
						Account
					</button>
				</div>
			</div>
		</div>

		<!-- Three Column Layout -->
		<div class="grid grid-cols-1 gap-6 lg:grid-cols-3">
			<!-- Scheduled Column -->
			<div class="bg-theme-secondary/30 rounded-xl border border-theme p-4">
				<div class="mb-4 flex items-center justify-between">
					<div class="flex items-center gap-2">
						<span class="h-3 w-3 rounded-full bg-secondary-500"></span>
						<h2 class="font-semibold text-theme">Scheduled</h2>
						<span
							class="rounded-full bg-secondary-100 px-2 py-0.5 text-xs font-medium text-secondary-700 dark:bg-secondary-900/30 dark:text-secondary-400"
						>
							{unassigned.length}
						</span>
					</div>
					<div class="flex gap-2">
						<button
							type="button"
							class="text-xs text-primary-500 hover:text-primary-600"
							onclick={() => (selectedUnassigned = selectAll(unassigned))}
						>
							Select All
						</button>
						<button
							type="button"
							class="text-xs text-theme-muted hover:text-theme"
							onclick={() => (selectedUnassigned = clearSelection())}
						>
							Clear
						</button>
					</div>
				</div>

				<!-- Expand/Collapse All -->
				{#if groupedUnassigned.size > 0}
					<div class="mb-3 flex gap-2 text-xs">
						<button
							type="button"
							class="text-theme-muted hover:text-theme"
							onclick={() => (expandedUnassigned = expandAll(groupedUnassigned))}
						>
							Expand All
						</button>
						<span class="text-theme-muted">|</span>
						<button
							type="button"
							class="text-theme-muted hover:text-theme"
							onclick={() => (expandedUnassigned = collapseAll())}
						>
							Collapse All
						</button>
					</div>
				{/if}

				<!-- Bulk Action -->
				{#if selectedUnassigned.size > 0}
					<div class="mb-4">
						<button
							type="button"
							class="btn-primary w-full text-sm"
							disabled={processingDispatch}
							onclick={handleAddDispatch}
						>
							{#if processingDispatch}
								Adding Dispatch...
							{:else}
								Add Dispatch ({selectedUnassigned.size})
							{/if}
						</button>
					</div>
				{/if}

				<!-- Services List -->
				<div class="max-h-[50vh] space-y-2 overflow-y-auto">
					{#each [...groupedUnassigned.entries()] as [key, services] (key)}
						<div class="overflow-hidden card-service">
							<button
								type="button"
								class="hover:bg-theme-secondary/50 -m-6 flex w-full items-start justify-between gap-2 p-6"
								onclick={() => (expandedUnassigned = toggleExpanded(expandedUnassigned, key))}
							>
								<span class="flex items-start gap-2 text-left">
									<svg
										class="mt-0.5 h-4 w-4 shrink-0 text-secondary-500 transition-transform {expandedUnassigned.has(
											key
										)
											? 'rotate-90'
											: ''}"
										fill="none"
										stroke="currentColor"
										viewBox="0 0 24 24"
									>
										<path
											stroke-linecap="round"
											stroke-linejoin="round"
											stroke-width="2"
											d="M9 5l7 7-7 7"
										/>
									</svg>
									<span class="text-sm font-medium text-theme"
										>{formatGroupKey(key, groupMode)}</span
									>
								</span>
								<span
									class="shrink-0 rounded-full bg-secondary-100 px-2 py-0.5 text-xs font-medium text-secondary-600 dark:bg-secondary-900/30 dark:text-secondary-400"
								>
									{services.length}
								</span>
							</button>
							{#if expandedUnassigned.has(key)}
								<div class="-mx-6 mt-4 -mb-6 space-y-2 border-t border-theme px-4 pt-4 pb-4">
									{#each services as service (service.id)}
										<div
											class="hover:bg-theme-secondary/50 flex items-start gap-3 rounded-lg border border-theme bg-theme p-3"
										>
											<input
												type="checkbox"
												checked={selectedUnassigned.has(service.id)}
												onchange={() =>
													(selectedUnassigned = toggleSelection(selectedUnassigned, service.id))}
												class="mt-1 h-4 w-4 rounded border-theme text-primary-500 focus:ring-primary-500"
											/>
											<div class="min-w-0 flex-1">
												<p class="truncate font-medium text-theme">
													{service.account?.name ?? 'Unknown'}
												</p>
												<p class="truncate text-sm text-theme-muted">
													{formatAddress(service.accountAddress)}
												</p>
												{#if groupMode !== 'date'}
													<p class="text-xs text-theme-secondary">{formatDate(service.date)}</p>
												{/if}
											</div>
											<button
												type="button"
												class="shrink-0 rounded-md p-1.5 text-red-500 hover:bg-red-100 hover:text-red-600 dark:hover:bg-red-900/30"
												onclick={() => promptDeleteService(service)}
												aria-label="Delete service"
											>
												<svg class="h-4 w-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
													<path
														stroke-linecap="round"
														stroke-linejoin="round"
														stroke-width="2"
														d="M19 7l-.867 12.142A2 2 0 0116.138 21H7.862a2 2 0 01-1.995-1.858L5 7m5 4v6m4-6v6m1-10V4a1 1 0 00-1-1h-4a1 1 0 00-1 1v3M4 7h16"
													/>
												</svg>
											</button>
										</div>
									{/each}
								</div>
							{/if}
						</div>
					{/each}

					{#if unassigned.length === 0}
						<p class="py-8 text-center text-theme-muted">No scheduled services</p>
					{/if}
				</div>
			</div>

			<!-- Dispatched Column -->
			<div class="bg-theme-secondary/30 rounded-xl border border-theme p-4">
				<div class="mb-4 flex items-center justify-between">
					<div class="flex items-center gap-2">
						<span class="h-3 w-3 rounded-full bg-purple-500"></span>
						<h2 class="font-semibold text-theme">Dispatched</h2>
						<span
							class="rounded-full bg-purple-100 px-2 py-0.5 text-xs font-medium text-purple-700 dark:bg-purple-900/30 dark:text-purple-400"
						>
							{readyToAssign.length}
						</span>
					</div>
					<div class="flex gap-2">
						<button
							type="button"
							class="text-xs text-primary-500 hover:text-primary-600"
							onclick={() => (selectedReadyToAssign = selectAll(readyToAssign))}
						>
							Select All
						</button>
						<button
							type="button"
							class="text-xs text-theme-muted hover:text-theme"
							onclick={() => (selectedReadyToAssign = clearSelection())}
						>
							Clear
						</button>
					</div>
				</div>

				<!-- Expand/Collapse All -->
				{#if groupedReadyToAssign.size > 0}
					<div class="mb-3 flex gap-2 text-xs">
						<button
							type="button"
							class="text-theme-muted hover:text-theme"
							onclick={() => (expandedReadyToAssign = expandAll(groupedReadyToAssign))}
						>
							Expand All
						</button>
						<span class="text-theme-muted">|</span>
						<button
							type="button"
							class="text-theme-muted hover:text-theme"
							onclick={() => (expandedReadyToAssign = collapseAll())}
						>
							Collapse All
						</button>
					</div>
				{/if}

				<!-- Bulk Actions -->
				{#if selectedReadyToAssign.size > 0}
					<div class="mb-4 space-y-2">
						<!-- Assign Team Member -->
						<div class="flex gap-2">
							<select
								class="flex-1 rounded-lg border border-theme bg-theme px-3 py-2 text-sm text-theme focus:border-primary-500 focus:ring-1 focus:ring-primary-500 focus:outline-none"
								onchange={(e) => (selectedTeamMember = e.currentTarget.value)}
							>
								<option value="" selected={!selectedTeamMember}>Select team member...</option>
								{#each teamProfiles as profile (profile.id)}
									<option value={profile.id} selected={selectedTeamMember === profile.id}>
										{profile.fullName}
									</option>
								{/each}
							</select>
							<button
								type="button"
								class="btn-primary shrink-0 text-sm"
								disabled={processingAssign || !selectedTeamMember}
								onclick={handleAssignTeamMember}
							>
								{#if processingAssign}
									Assigning...
								{:else}
									Assign ({selectedReadyToAssign.size})
								{/if}
							</button>
						</div>
						<!-- Remove Dispatch -->
						<button
							type="button"
							class="btn-secondary w-full text-sm"
							disabled={processingRemoveDispatch}
							onclick={handleRemoveDispatch}
						>
							{#if processingRemoveDispatch}
								Removing...
							{:else}
								Remove Dispatch ({selectedReadyToAssign.size})
							{/if}
						</button>
					</div>
				{/if}

				<!-- Services List -->
				<div class="max-h-[50vh] space-y-2 overflow-y-auto">
					{#each [...groupedReadyToAssign.entries()] as [key, services] (key)}
						<div class="overflow-hidden card-service">
							<button
								type="button"
								class="hover:bg-theme-secondary/50 -m-6 flex w-full items-start justify-between gap-2 p-6"
								onclick={() => (expandedReadyToAssign = toggleExpanded(expandedReadyToAssign, key))}
							>
								<span class="flex items-start gap-2 text-left">
									<svg
										class="mt-0.5 h-4 w-4 shrink-0 text-purple-500 transition-transform {expandedReadyToAssign.has(
											key
										)
											? 'rotate-90'
											: ''}"
										fill="none"
										stroke="currentColor"
										viewBox="0 0 24 24"
									>
										<path
											stroke-linecap="round"
											stroke-linejoin="round"
											stroke-width="2"
											d="M9 5l7 7-7 7"
										/>
									</svg>
									<span class="text-sm font-medium text-theme"
										>{formatGroupKey(key, groupMode)}</span
									>
								</span>
								<span
									class="shrink-0 rounded-full bg-purple-100 px-2 py-0.5 text-xs font-medium text-purple-600 dark:bg-purple-900/30 dark:text-purple-400"
								>
									{services.length}
								</span>
							</button>
							{#if expandedReadyToAssign.has(key)}
								<div class="-mx-6 mt-4 -mb-6 space-y-2 border-t border-theme px-4 pt-4 pb-4">
									{#each services as service (service.id)}
										<label
											class="hover:bg-theme-secondary/50 flex cursor-pointer items-start gap-3 rounded-lg border border-theme bg-theme p-3"
										>
											<input
												type="checkbox"
												checked={selectedReadyToAssign.has(service.id)}
												onchange={() =>
													(selectedReadyToAssign = toggleSelection(
														selectedReadyToAssign,
														service.id
													))}
												class="mt-1 h-4 w-4 rounded border-theme text-primary-500 focus:ring-primary-500"
											/>
											<div class="min-w-0 flex-1">
												<p class="truncate font-medium text-theme">
													{service.account?.name ?? 'Unknown'}
												</p>
												<p class="truncate text-sm text-theme-muted">
													{formatAddress(service.accountAddress)}
												</p>
												{#if groupMode !== 'date'}
													<p class="text-xs text-theme-secondary">{formatDate(service.date)}</p>
												{/if}
											</div>
										</label>
									{/each}
								</div>
							{/if}
						</div>
					{/each}

					{#if readyToAssign.length === 0}
						<p class="py-8 text-center text-theme-muted">No dispatched services</p>
					{/if}
				</div>
			</div>

			<!-- Assigned Column -->
			<div class="bg-theme-secondary/30 rounded-xl border border-theme p-4">
				<div class="mb-4 flex items-center justify-between">
					<div class="flex items-center gap-2">
						<span class="h-3 w-3 rounded-full bg-blue-500"></span>
						<h2 class="font-semibold text-theme">Assigned</h2>
						<span
							class="rounded-full bg-blue-100 px-2 py-0.5 text-xs font-medium text-blue-700 dark:bg-blue-900/30 dark:text-blue-400"
						>
							{assigned.length}
						</span>
					</div>
					<div class="flex gap-2">
						<button
							type="button"
							class="text-xs text-primary-500 hover:text-primary-600"
							onclick={() => (selectedAssigned = selectAll(assigned))}
						>
							Select All
						</button>
						<button
							type="button"
							class="text-xs text-theme-muted hover:text-theme"
							onclick={() => (selectedAssigned = clearSelection())}
						>
							Clear
						</button>
					</div>
				</div>

				<!-- Expand/Collapse All -->
				{#if groupedAssigned.size > 0}
					<div class="mb-3 flex gap-2 text-xs">
						<button
							type="button"
							class="text-theme-muted hover:text-theme"
							onclick={() => (expandedAssigned = expandAll(groupedAssigned))}
						>
							Expand All
						</button>
						<span class="text-theme-muted">|</span>
						<button
							type="button"
							class="text-theme-muted hover:text-theme"
							onclick={() => (expandedAssigned = collapseAll())}
						>
							Collapse All
						</button>
					</div>
				{/if}

				<!-- Bulk Action -->
				{#if selectedAssigned.size > 0}
					<div class="mb-4">
						<button
							type="button"
							class="btn-secondary w-full text-sm"
							disabled={processingRemove}
							onclick={handleRemoveNonDispatch}
						>
							{#if processingRemove}
								Removing...
							{:else}
								Remove Team ({selectedAssigned.size})
							{/if}
						</button>
					</div>
				{/if}

				<!-- Services List -->
				<div class="max-h-[50vh] space-y-2 overflow-y-auto">
					{#each [...groupedAssigned.entries()] as [key, services] (key)}
						<div class="overflow-hidden card-service">
							<button
								type="button"
								class="hover:bg-theme-secondary/50 -m-6 flex w-full items-start justify-between gap-2 p-6"
								onclick={() => (expandedAssigned = toggleExpanded(expandedAssigned, key))}
							>
								<span class="flex items-start gap-2 text-left">
									<svg
										class="mt-0.5 h-4 w-4 shrink-0 text-blue-500 transition-transform {expandedAssigned.has(
											key
										)
											? 'rotate-90'
											: ''}"
										fill="none"
										stroke="currentColor"
										viewBox="0 0 24 24"
									>
										<path
											stroke-linecap="round"
											stroke-linejoin="round"
											stroke-width="2"
											d="M9 5l7 7-7 7"
										/>
									</svg>
									<span class="text-sm font-medium text-theme"
										>{formatGroupKey(key, groupMode)}</span
									>
								</span>
								<span
									class="shrink-0 rounded-full bg-blue-100 px-2 py-0.5 text-xs font-medium text-blue-600 dark:bg-blue-900/30 dark:text-blue-400"
								>
									{services.length}
								</span>
							</button>
							{#if expandedAssigned.has(key)}
								<div class="-mx-6 mt-4 -mb-6 space-y-2 border-t border-theme px-4 pt-4 pb-4">
									{#each services as service (service.id)}
										<div class="rounded-lg border border-theme bg-theme p-3">
											<div class="flex items-start gap-3">
												<input
													type="checkbox"
													checked={selectedAssigned.has(service.id)}
													onchange={() =>
														(selectedAssigned = toggleSelection(selectedAssigned, service.id))}
													class="mt-1 h-4 w-4 rounded border-theme text-primary-500 focus:ring-primary-500"
												/>
												<div class="min-w-0 flex-1">
													<p class="truncate font-medium text-theme">
														{service.account?.name ?? 'Unknown'}
													</p>
													<p class="truncate text-sm text-theme-muted">
														{formatAddress(service.accountAddress)}
													</p>
													{#if groupMode !== 'date'}
														<p class="text-xs text-theme-secondary">{formatDate(service.date)}</p>
													{/if}

													<!-- Team Members with granular controls -->
													<div class="mt-2 space-y-1">
														{#each service.teamMembers as member (member.id)}
															{@const isDispatcher =
																member.teamProfile?.role === 'ADMIN' ||
																member.teamProfileId === currentUserId}
															<div class="flex items-center justify-between gap-2 text-xs">
																<span
																	class={isDispatcher
																		? 'text-theme-muted italic'
																		: 'text-blue-600 dark:text-blue-400'}
																>
																	{member.teamProfile?.fullName ?? 'Unknown'}
																	{#if isDispatcher}
																		<span class="text-theme-muted">(dispatch)</span>
																	{/if}
																</span>
																{#if !isDispatcher}
																	<button
																		type="button"
																		class="text-red-500 hover:text-red-600"
																		onclick={() => handleRemoveTeamMemberFromService(member.id)}
																		aria-label="Remove {member.teamProfile?.fullName}"
																	>
																		<svg
																			class="h-4 w-4"
																			fill="none"
																			stroke="currentColor"
																			viewBox="0 0 24 24"
																		>
																			<path
																				stroke-linecap="round"
																				stroke-linejoin="round"
																				stroke-width="2"
																				d="M6 18L18 6M6 6l12 12"
																			/>
																		</svg>
																	</button>
																{/if}
															</div>
														{/each}

														<!-- Add team member -->
														{#if addingTeamMemberTo === service.id}
															<div class="flex gap-1 pt-1">
																<select
																	class="flex-1 rounded border border-theme bg-theme-secondary px-2 py-1 text-xs focus:border-primary-500 focus:outline-none"
																	onchange={(e) =>
																		(newTeamMemberForService = e.currentTarget.value)}
																>
																	<option value="">Select...</option>
																	{#each teamProfiles.filter((p) => !service.teamMembers.some((m) => m.teamProfileId === p.id)) as profile (profile.id)}
																		<option value={profile.id}>{profile.fullName}</option>
																	{/each}
																</select>
																<button
																	type="button"
																	class="rounded bg-primary-500 px-2 py-1 text-xs text-white hover:bg-primary-600 disabled:opacity-50"
																	disabled={!newTeamMemberForService}
																	onclick={() => handleAddTeamMemberToService(service.id)}
																>
																	Add
																</button>
																<button
																	type="button"
																	class="rounded bg-theme-secondary px-2 py-1 text-xs text-theme-muted hover:bg-theme-tertiary"
																	onclick={() => {
																		addingTeamMemberTo = null;
																		newTeamMemberForService = '';
																	}}
																>
																	Cancel
																</button>
															</div>
														{:else}
															<button
																type="button"
																class="mt-1 text-xs text-primary-500 hover:text-primary-600"
																onclick={() => (addingTeamMemberTo = service.id)}
															>
																+ Add team member
															</button>
														{/if}
													</div>
												</div>
											</div>
										</div>
									{/each}
								</div>
							{/if}
						</div>
					{/each}

					{#if assigned.length === 0}
						<p class="py-8 text-center text-theme-muted">No assigned services</p>
					{/if}
				</div>
			</div>
		</div>
	</ContentContainer>
</div>

<!-- Generate Services Modal -->
<GenerateServicesModal
	open={showGenerateModal}
	onClose={() => (showGenerateModal = false)}
	onSuccess={handleGenerateSuccess}
/>

<!-- Delete Confirmation Modal -->
{#if showDeleteConfirm && serviceToDelete}
	<div
		class="fixed inset-0 z-50 flex items-center justify-center bg-black/50 p-4"
		onclick={(e) => e.target === e.currentTarget && cancelDelete()}
		onkeydown={(e) => e.key === 'Escape' && cancelDelete()}
		role="dialog"
		aria-modal="true"
		tabindex="-1"
	>
		<div class="w-full max-w-md rounded-xl border border-theme bg-theme p-6 shadow-2xl">
			<div class="mb-4 flex items-center gap-3">
				<div
					class="flex h-10 w-10 items-center justify-center rounded-full bg-red-100 dark:bg-red-900/30"
				>
					<svg
						class="h-6 w-6 text-red-600 dark:text-red-400"
						fill="none"
						stroke="currentColor"
						viewBox="0 0 24 24"
					>
						<path
							stroke-linecap="round"
							stroke-linejoin="round"
							stroke-width="2"
							d="M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-3L13.732 4c-.77-1.333-2.694-1.333-3.464 0L3.34 16c-.77 1.333.192 3 1.732 3z"
						/>
					</svg>
				</div>
				<h2 class="text-xl font-semibold text-theme">Delete Service</h2>
			</div>
			<p class="mb-6 text-theme-secondary">
				Are you sure you want to delete the service for
				<span class="font-medium text-theme">{serviceToDelete.account?.name ?? 'Unknown'}</span>
				on
				<span class="font-medium text-theme">{formatDate(serviceToDelete.date)}</span>? This action
				cannot be undone.
			</p>
			<div class="flex justify-end gap-3">
				<button
					type="button"
					class="btn-secondary"
					onclick={cancelDelete}
					disabled={processingDelete}
				>
					Cancel
				</button>
				<button
					type="button"
					class="rounded-lg bg-red-600 px-4 py-2 font-medium text-white hover:bg-red-700 disabled:opacity-50"
					onclick={confirmDeleteService}
					disabled={processingDelete}
				>
					{#if processingDelete}
						Deleting...
					{:else}
						Delete
					{/if}
				</button>
			</div>
		</div>
	</div>
{/if}
