refactor: Standardize document and folder identification with a new entryKey module.

This commit is contained in:
2025-11-24 23:13:11 +01:00
parent 096c377897
commit 22f0c040a2
12 changed files with 146 additions and 202 deletions
@@ -1,4 +1,5 @@
import { useCallback, useEffect, useMemo, useRef } from 'react';
import { createDocumentEntryKey, createFolderEntryKey, isFolderEntry } from '../../app/entryKey';
interface FolderEntry {
id: string | number;
@@ -17,11 +18,9 @@ interface NavigableRow {
}
interface UseDocumentsSelectionOptions {
showingSearchResults: boolean;
currentSubfolders: FolderEntry[];
visibleDocuments: DocumentEntry[];
resolveFolderRowKey: (id: string | number) => string | null;
resolveDocumentRowKey: (id: string | number) => string | null;
showingSearchResults?: boolean;
currentSubfolders?: FolderEntry[];
visibleDocuments?: DocumentEntry[];
configureSelectionEnvironment: (config: { visibleRowKeySet: Set<string>; navigableRowKeys: string[] }) => void;
visibleRowKeySet: Set<string>;
selectedEntries: string[];
@@ -33,15 +32,12 @@ interface UseDocumentsSelectionOptions {
focusedDocumentId: string | number | null;
setFocusedRowKey: (value: string | null | ((current: string | null) => string | null)) => void;
focusedRowKey: string | null;
isFolderRowKey: (key: string | null) => boolean;
}
const useDocumentsSelection = ({
showingSearchResults,
currentSubfolders,
visibleDocuments,
resolveFolderRowKey,
resolveDocumentRowKey,
configureSelectionEnvironment,
visibleRowKeySet,
selectedEntries,
@@ -53,26 +49,25 @@ const useDocumentsSelection = ({
focusedDocumentId,
setFocusedRowKey,
focusedRowKey,
isFolderRowKey,
}: UseDocumentsSelectionOptions) => {
const navigableRows = useMemo<NavigableRow[]>(() => {
const entries: NavigableRow[] = [];
if (!showingSearchResults) {
currentSubfolders.forEach((folder) => {
const key = resolveFolderRowKey(folder.id);
const key = createFolderEntryKey(folder.id);
if (key) {
entries.push({ key, type: 'folder', id: folder.id });
}
});
}
visibleDocuments.forEach((doc) => {
const key = resolveDocumentRowKey(doc.id);
const key = createDocumentEntryKey(doc.id);
if (key) {
entries.push({ key, type: 'document', id: doc.id });
}
});
return entries;
}, [showingSearchResults, currentSubfolders, visibleDocuments, resolveFolderRowKey, resolveDocumentRowKey]);
}, [showingSearchResults, currentSubfolders, visibleDocuments]);
const navigableRowKeys = useMemo(
() => navigableRows.map((entry) => entry.key),
@@ -90,14 +85,14 @@ const useDocumentsSelection = ({
(docId: string | number | null) => {
if (!docId) return;
promoteSelectionOrderRaw(docId);
const rowKey = resolveDocumentRowKey(docId);
const rowKey = createDocumentEntryKey(docId);
if (rowKey) {
selectionAnchorRef.current = rowKey;
}
setFocusedDocumentId(docId);
setActivePreviewId(docId);
},
[promoteSelectionOrderRaw, resolveDocumentRowKey, selectionAnchorRef, setFocusedDocumentId, setActivePreviewId],
[promoteSelectionOrderRaw, selectionAnchorRef, setFocusedDocumentId, setActivePreviewId],
);
const clearDocumentSelection = useCallback(() => {
@@ -112,11 +107,11 @@ const useDocumentsSelection = ({
}
prevFocusedDocIdRef.current = focusedDocumentId;
if (focusedDocumentId) {
setFocusedRowKey(resolveDocumentRowKey(focusedDocumentId));
setFocusedRowKey(createDocumentEntryKey(focusedDocumentId));
} else {
setFocusedRowKey((current) => (isFolderRowKey(current) ? current : null));
setFocusedRowKey((current) => (isFolderEntry(current) ? current : null));
}
}, [focusedDocumentId, resolveDocumentRowKey, setFocusedRowKey, isFolderRowKey]);
}, [focusedDocumentId, setFocusedRowKey]);
useEffect(() => {
if (!navigableRowKeys.length) {
@@ -130,7 +125,7 @@ const useDocumentsSelection = ({
return;
}
const docKey = focusedDocumentId ? resolveDocumentRowKey(focusedDocumentId) : null;
const docKey = focusedDocumentId ? createDocumentEntryKey(focusedDocumentId) : null;
if (docKey && navigableRowKeys.includes(docKey)) {
setFocusedRowKey(docKey);
return;
@@ -145,7 +140,7 @@ const useDocumentsSelection = ({
if (focusedRowKey) {
setFocusedRowKey(null);
}
}, [focusedRowKey, focusedDocumentId, navigableRowKeys, selectedEntries, setFocusedRowKey, resolveDocumentRowKey]);
}, [focusedRowKey, focusedDocumentId, navigableRowKeys, selectedEntries, setFocusedRowKey]);
return {
navigableRows,
+3 -6
View File
@@ -1,4 +1,5 @@
import { useCallback } from 'react';
import { createDocumentEntryKey, createFolderEntryKey } from '../app/entryKey';
export type PointerEventLike = MouseEvent | PointerEvent;
@@ -26,8 +27,6 @@ export interface WorkspaceEntry {
}
interface UseEntryPointerOptions {
resolveDocumentRowKey?: (id: string | number) => string | null;
resolveFolderRowKey?: (id: string | number) => string | null;
onSelectEntry?: (entry: WorkspaceEntry, event?: PointerEventLike | null, metadata?: EntryPointerMetadata) => void;
onDocumentActivate?: (id: string | number, metadata?: EntryPointerMetadata) => void;
}
@@ -41,8 +40,6 @@ export interface EntryPointerMetadata {
}
export const useEntryPointer = ({
resolveDocumentRowKey,
resolveFolderRowKey,
onSelectEntry,
onDocumentActivate,
}: UseEntryPointerOptions) =>
@@ -58,7 +55,7 @@ export const useEntryPointer = ({
}
const rowKey = entry.key
|| (type === 'document' ? resolveDocumentRowKey?.(id) : resolveFolderRowKey?.(id));
|| (type === 'document' ? createDocumentEntryKey(id) : createFolderEntryKey(id));
if (!rowKey) {
return;
}
@@ -73,7 +70,7 @@ export const useEntryPointer = ({
onDocumentActivate?.(id, metadata);
}
},
[resolveDocumentRowKey, resolveFolderRowKey, onSelectEntry, onDocumentActivate],
[onSelectEntry, onDocumentActivate],
);
export default useEntryPointer;