<!-- [DEF:DashboardGrid:Component] -->
<!--
@SEMANTICS: dashboard, grid, selection, pagination
@PURPOSE:   Displays a grid of dashboards with selection and pagination.
@LAYER:     Component
@RELATION:  USED_BY -> frontend/src/routes/migration/+page.svelte

@INVARIANT: Selected IDs must be a subset of available dashboards.
-->

<script lang="ts">
  // [SECTION: IMPORTS]
  import { createEventDispatcher } from 'svelte';
  import type { DashboardMetadata } from '../types/dashboard';
  // [/SECTION]

  // [SECTION: PROPS]
  export let dashboards: DashboardMetadata[] = [];
  export let selectedIds: number[] = [];
  // [/SECTION]

  // [SECTION: STATE]
  let filterText = "";
  let currentPage = 0;
  let pageSize = 20;
  let sortColumn: keyof DashboardMetadata = "title";
  let sortDirection: "asc" | "desc" = "asc";
  // [/SECTION]

  // [SECTION: DERIVED]
  $: filteredDashboards = dashboards.filter(d =>
    d.title.toLowerCase().includes(filterText.toLowerCase())
  );

  $: sortedDashboards = [...filteredDashboards].sort((a, b) => {
    let aVal = a[sortColumn];
    let bVal = b[sortColumn];
    if (sortColumn === "id") {
      aVal = Number(aVal);
      bVal = Number(bVal);
    }
    if (aVal < bVal) return sortDirection === "asc" ? -1 : 1;
    if (aVal > bVal) return sortDirection === "asc" ? 1 : -1;
    return 0;
  });

  $: paginatedDashboards = sortedDashboards.slice(
    currentPage * pageSize,
    (currentPage + 1) * pageSize
  );

  $: totalPages = Math.ceil(sortedDashboards.length / pageSize);

  $: allSelected = paginatedDashboards.length > 0 && paginatedDashboards.every(d => selectedIds.includes(d.id));
  $: someSelected = paginatedDashboards.some(d => selectedIds.includes(d.id));
  // [/SECTION]

  // [SECTION: EVENTS]
  const dispatch = createEventDispatcher<{ selectionChanged: number[] }>();
  // [/SECTION]

  // [DEF:handleSort:Function]
  // @PURPOSE: Toggles sort direction or changes sort column.
  function handleSort(column: keyof DashboardMetadata) {
    if (sortColumn === column) {
      sortDirection = sortDirection === "asc" ? "desc" : "asc";
    } else {
      sortColumn = column;
      sortDirection = "asc";
    }
  }
  // [/DEF:handleSort]

  // [DEF:handleSelectionChange:Function]
  // @PURPOSE: Handles individual checkbox changes.
  function handleSelectionChange(id: number, checked: boolean) {
    let newSelected = [...selectedIds];
    if (checked) {
      if (!newSelected.includes(id)) newSelected.push(id);
    } else {
      newSelected = newSelected.filter(sid => sid !== id);
    }
    selectedIds = newSelected;
    dispatch('selectionChanged', newSelected);
  }
  // [/DEF:handleSelectionChange]

  // [DEF:handleSelectAll:Function]
  // @PURPOSE: Handles select all checkbox.
  function handleSelectAll(checked: boolean) {
    let newSelected = [...selectedIds];
    if (checked) {
      paginatedDashboards.forEach(d => {
        if (!newSelected.includes(d.id)) newSelected.push(d.id);
      });
    } else {
      paginatedDashboards.forEach(d => {
        newSelected = newSelected.filter(sid => sid !== d.id);
      });
    }
    selectedIds = newSelected;
    dispatch('selectionChanged', newSelected);
  }
  // [/DEF:handleSelectAll]

  // [DEF:goToPage:Function]
  // @PURPOSE: Changes current page.
  function goToPage(page: number) {
    if (page >= 0 && page < totalPages) {
      currentPage = page;
    }
  }
  // [/DEF:goToPage]

</script>

<!-- [SECTION: TEMPLATE] -->
<div class="dashboard-grid">
  <!-- Filter Input -->
  <div class="mb-4">
    <input
      type="text"
      bind:value={filterText}
      placeholder="Search dashboards..."
      class="w-full px-3 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500"
    />
  </div>

  <!-- Grid/Table -->
  <div class="overflow-x-auto">
    <table class="min-w-full bg-white border border-gray-300">
      <thead class="bg-gray-50">
        <tr>
          <th class="px-4 py-2 border-b">
            <input
              type="checkbox"
              checked={allSelected}
              indeterminate={someSelected && !allSelected}
              on:change={(e) => handleSelectAll((e.target as HTMLInputElement).checked)}
            />
          </th>
          <th class="px-4 py-2 border-b cursor-pointer" on:click={() => handleSort('title')}>
            Title {sortColumn === 'title' ? (sortDirection === 'asc' ? '↑' : '↓') : ''}
          </th>
          <th class="px-4 py-2 border-b cursor-pointer" on:click={() => handleSort('last_modified')}>
            Last Modified {sortColumn === 'last_modified' ? (sortDirection === 'asc' ? '↑' : '↓') : ''}
          </th>
          <th class="px-4 py-2 border-b cursor-pointer" on:click={() => handleSort('status')}>
            Status {sortColumn === 'status' ? (sortDirection === 'asc' ? '↑' : '↓') : ''}
          </th>
        </tr>
      </thead>
      <tbody>
        {#each paginatedDashboards as dashboard (dashboard.id)}
          <tr class="hover:bg-gray-50">
            <td class="px-4 py-2 border-b">
              <input
                type="checkbox"
                checked={selectedIds.includes(dashboard.id)}
                on:change={(e) => handleSelectionChange(dashboard.id, (e.target as HTMLInputElement).checked)}
              />
            </td>
            <td class="px-4 py-2 border-b">{dashboard.title}</td>
            <td class="px-4 py-2 border-b">{new Date(dashboard.last_modified).toLocaleDateString()}</td>
            <td class="px-4 py-2 border-b">
              <span class="px-2 py-1 text-xs font-medium rounded-full {dashboard.status === 'published' ? 'bg-green-100 text-green-800' : 'bg-gray-100 text-gray-800'}">
                {dashboard.status}
              </span>
            </td>
          </tr>
        {/each}
      </tbody>
    </table>
  </div>

  <!-- Pagination Controls -->
  <div class="flex items-center justify-between mt-4">
    <div class="text-sm text-gray-700">
      Showing {currentPage * pageSize + 1} to {Math.min((currentPage + 1) * pageSize, sortedDashboards.length)} of {sortedDashboards.length} dashboards
    </div>
    <div class="flex space-x-2">
      <button
        class="px-3 py-1 text-sm border border-gray-300 rounded-md hover:bg-gray-50 disabled:opacity-50 disabled:cursor-not-allowed"
        disabled={currentPage === 0}
        on:click={() => goToPage(currentPage - 1)}
      >
        Previous
      </button>
      <button
        class="px-3 py-1 text-sm border border-gray-300 rounded-md hover:bg-gray-50 disabled:opacity-50 disabled:cursor-not-allowed"
        disabled={currentPage >= totalPages - 1}
        on:click={() => goToPage(currentPage + 1)}
      >
        Next
      </button>
    </div>
  </div>
</div>
<!-- [/SECTION] -->

<style>
  /* Component styles */
</style>

<!-- [/DEF:DashboardGrid] -->