mirror of
https://github.com/pacnpal/thrilltrack-explorer.git
synced 2025-12-21 10:11:12 -05:00
feat: Add debouncing to sort changes
This commit is contained in:
@@ -152,8 +152,8 @@ export function useModerationQueueManager(config: ModerationQueueManagerConfig):
|
|||||||
pauseFetchingRef: pauseFetchingRef.current,
|
pauseFetchingRef: pauseFetchingRef.current,
|
||||||
documentHidden: document.hidden,
|
documentHidden: document.hidden,
|
||||||
caller: callerLine,
|
caller: callerLine,
|
||||||
sortField: sort.config.field,
|
sortField: sort.debouncedConfig.field,
|
||||||
sortDirection: sort.config.direction,
|
sortDirection: sort.debouncedConfig.direction,
|
||||||
timestamp: new Date().toISOString(),
|
timestamp: new Date().toISOString(),
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -183,8 +183,8 @@ export function useModerationQueueManager(config: ModerationQueueManagerConfig):
|
|||||||
console.log("🔍 fetchItems called:", {
|
console.log("🔍 fetchItems called:", {
|
||||||
entityFilter: filters.debouncedEntityFilter,
|
entityFilter: filters.debouncedEntityFilter,
|
||||||
statusFilter: filters.debouncedStatusFilter,
|
statusFilter: filters.debouncedStatusFilter,
|
||||||
sortField: sort.config.field,
|
sortField: sort.debouncedConfig.field,
|
||||||
sortDirection: sort.config.direction,
|
sortDirection: sort.debouncedConfig.direction,
|
||||||
silent,
|
silent,
|
||||||
timestamp: new Date().toISOString(),
|
timestamp: new Date().toISOString(),
|
||||||
});
|
});
|
||||||
@@ -227,14 +227,14 @@ export function useModerationQueueManager(config: ModerationQueueManagerConfig):
|
|||||||
// Level 1: Always sort by escalated first (descending)
|
// Level 1: Always sort by escalated first (descending)
|
||||||
submissionsQuery = submissionsQuery.order('escalated', { ascending: false });
|
submissionsQuery = submissionsQuery.order('escalated', { ascending: false });
|
||||||
|
|
||||||
// Level 2: Apply user-selected sort
|
// Level 2: Apply user-selected sort (use debounced config)
|
||||||
submissionsQuery = submissionsQuery.order(
|
submissionsQuery = submissionsQuery.order(
|
||||||
sort.config.field,
|
sort.debouncedConfig.field,
|
||||||
{ ascending: sort.config.direction === 'asc' }
|
{ ascending: sort.debouncedConfig.direction === 'asc' }
|
||||||
);
|
);
|
||||||
|
|
||||||
// Level 3: Tertiary sort by created_at (if not already primary)
|
// Level 3: Tertiary sort by created_at (if not already primary)
|
||||||
if (sort.config.field !== 'created_at') {
|
if (sort.debouncedConfig.field !== 'created_at') {
|
||||||
submissionsQuery = submissionsQuery.order('created_at', { ascending: true });
|
submissionsQuery = submissionsQuery.order('created_at', { ascending: true });
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -475,8 +475,8 @@ export function useModerationQueueManager(config: ModerationQueueManagerConfig):
|
|||||||
pagination.setTotalCount,
|
pagination.setTotalCount,
|
||||||
pagination.startIndex,
|
pagination.startIndex,
|
||||||
pagination.endIndex,
|
pagination.endIndex,
|
||||||
sort.config.field,
|
sort.debouncedConfig.field,
|
||||||
sort.config.direction,
|
sort.debouncedConfig.direction,
|
||||||
profileCache,
|
profileCache,
|
||||||
entityCache,
|
entityCache,
|
||||||
toast
|
toast
|
||||||
@@ -812,9 +812,11 @@ export function useModerationQueueManager(config: ModerationQueueManagerConfig):
|
|||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (!user || !initialFetchCompleteRef.current || isMountingRef.current) return;
|
if (!user || !initialFetchCompleteRef.current || isMountingRef.current) return;
|
||||||
|
|
||||||
console.log('🔄 [SORT CHANGE] Detected sort config change:', {
|
console.log('🔄 [SORT/FILTER CHANGE] Detected change:', {
|
||||||
field: sort.config.field,
|
entityFilter: filters.debouncedEntityFilter,
|
||||||
direction: sort.config.direction,
|
statusFilter: filters.debouncedStatusFilter,
|
||||||
|
sortField: sort.debouncedConfig.field,
|
||||||
|
sortDirection: sort.debouncedConfig.direction,
|
||||||
timestamp: new Date().toISOString()
|
timestamp: new Date().toISOString()
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -823,8 +825,8 @@ export function useModerationQueueManager(config: ModerationQueueManagerConfig):
|
|||||||
}, [
|
}, [
|
||||||
filters.debouncedEntityFilter,
|
filters.debouncedEntityFilter,
|
||||||
filters.debouncedStatusFilter,
|
filters.debouncedStatusFilter,
|
||||||
sort.config.field,
|
sort.debouncedConfig.field,
|
||||||
sort.config.direction,
|
sort.debouncedConfig.direction,
|
||||||
fetchItems,
|
fetchItems,
|
||||||
pagination.reset,
|
pagination.reset,
|
||||||
user
|
user
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
import { useState, useCallback, useEffect } from 'react';
|
import { useState, useCallback, useEffect } from 'react';
|
||||||
|
import { useDebounce } from '@/hooks/useDebounce';
|
||||||
import type { SortConfig, SortField } from '@/types/moderation';
|
import type { SortConfig, SortField } from '@/types/moderation';
|
||||||
|
|
||||||
const STORAGE_KEY = 'moderationQueue_sortConfig';
|
const STORAGE_KEY = 'moderationQueue_sortConfig';
|
||||||
|
const SORT_DEBOUNCE_MS = 300;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Default sort configuration
|
* Default sort configuration
|
||||||
@@ -43,8 +45,10 @@ function saveSortConfig(config: SortConfig): void {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export interface UseModerationSortReturn {
|
export interface UseModerationSortReturn {
|
||||||
/** Current sort configuration */
|
/** Current sort configuration (immediate) */
|
||||||
config: SortConfig;
|
config: SortConfig;
|
||||||
|
/** Debounced sort configuration (use this for queries) */
|
||||||
|
debouncedConfig: SortConfig;
|
||||||
/** Update the sort configuration */
|
/** Update the sort configuration */
|
||||||
setConfig: (config: SortConfig) => void;
|
setConfig: (config: SortConfig) => void;
|
||||||
/** Sort by a specific field, toggling direction if already sorting by that field */
|
/** Sort by a specific field, toggling direction if already sorting by that field */
|
||||||
@@ -64,12 +68,16 @@ export interface UseModerationSortReturn {
|
|||||||
export function useModerationSort(): UseModerationSortReturn {
|
export function useModerationSort(): UseModerationSortReturn {
|
||||||
const [config, setConfigState] = useState<SortConfig>(loadSortConfig);
|
const [config, setConfigState] = useState<SortConfig>(loadSortConfig);
|
||||||
|
|
||||||
|
// Debounce the config to prevent rapid-fire fetches
|
||||||
|
const debouncedConfig = useDebounce(config, SORT_DEBOUNCE_MS);
|
||||||
|
|
||||||
// Persist to localStorage whenever config changes
|
// Persist to localStorage whenever config changes
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
saveSortConfig(config);
|
saveSortConfig(config);
|
||||||
}, [config]);
|
}, [config]);
|
||||||
|
|
||||||
const setConfig = useCallback((newConfig: SortConfig) => {
|
const setConfig = useCallback((newConfig: SortConfig) => {
|
||||||
|
console.log('📝 [SORT] setConfig called:', newConfig);
|
||||||
setConfigState(newConfig);
|
setConfigState(newConfig);
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
@@ -96,6 +104,7 @@ export function useModerationSort(): UseModerationSortReturn {
|
|||||||
|
|
||||||
return {
|
return {
|
||||||
config,
|
config,
|
||||||
|
debouncedConfig,
|
||||||
setConfig,
|
setConfig,
|
||||||
sortBy,
|
sortBy,
|
||||||
toggleDirection,
|
toggleDirection,
|
||||||
|
|||||||
Reference in New Issue
Block a user