Skip to content

Commit 7d4978c

Browse files
committed
add cleanup and debouncing for workspace editor updates
Cancel debounced functions on unmount to prevent stale callbacks. Debounce WorkspaceService.UpdateWorkspace calls to avoid excessive backend updates during typing.
1 parent 265fe0f commit 7d4978c

File tree

1 file changed

+32
-11
lines changed

1 file changed

+32
-11
lines changed

frontend/app/tab/workspaceswitcher.tsx

Lines changed: 32 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -141,11 +141,17 @@ const WorkspaceSwitcher = forwardRef<HTMLDivElement>((_, ref) => {
141141
);
142142
});
143143

144+
/**
145+
* A ViewModel that has access to its block's ID and atom.
146+
*/
144147
interface BlockAwareViewModel extends ViewModel {
145148
blockId: string;
146149
blockAtom: Atom<Block>;
147150
}
148151

152+
/**
153+
* A preview ViewModel with directory navigation capabilities.
154+
*/
149155
interface PreviewViewModel extends BlockAwareViewModel {
150156
goHistory: (path: string) => Promise<void>;
151157
}
@@ -268,6 +274,24 @@ const WorkspaceSwitcherItem = ({
268274
[]
269275
);
270276

277+
const debouncedWorkspaceUpdate = useMemo(
278+
() =>
279+
debounce(300, (oid: string, name: string, icon: string, color: string, directory: string) => {
280+
fireAndForget(async () => {
281+
await WorkspaceService.UpdateWorkspace(oid, name, icon, color, directory, false);
282+
});
283+
}),
284+
[]
285+
);
286+
287+
useEffect(() => {
288+
return () => {
289+
debouncedBlockUpdate.cancel();
290+
debouncedWorkspaceUpdate.cancel();
291+
pendingDirectoryRef.current = null;
292+
};
293+
}, [debouncedBlockUpdate, debouncedWorkspaceUpdate]);
294+
271295
const setWorkspace = useCallback(
272296
(newWorkspace: Workspace) => {
273297
setWorkspaceEntry((prev) => {
@@ -276,16 +300,13 @@ const WorkspaceSwitcherItem = ({
276300
const directoryChanged = newDirectory !== oldDirectory;
277301

278302
if (newWorkspace.name !== "") {
279-
fireAndForget(async () => {
280-
await WorkspaceService.UpdateWorkspace(
281-
prev.workspace.oid,
282-
newWorkspace.name,
283-
newWorkspace.icon,
284-
newWorkspace.color,
285-
newWorkspace.directory ?? "",
286-
false
287-
);
288-
});
303+
debouncedWorkspaceUpdate(
304+
prev.workspace.oid,
305+
newWorkspace.name,
306+
newWorkspace.icon,
307+
newWorkspace.color,
308+
newWorkspace.directory ?? ""
309+
);
289310
if (directoryChanged && isCurrentWorkspace && newDirectory) {
290311
pendingDirectoryRef.current = newDirectory;
291312
debouncedBlockUpdate(newDirectory);
@@ -294,7 +315,7 @@ const WorkspaceSwitcherItem = ({
294315
return { ...prev, workspace: newWorkspace };
295316
});
296317
},
297-
[debouncedBlockUpdate, isCurrentWorkspace, setWorkspaceEntry]
318+
[debouncedBlockUpdate, debouncedWorkspaceUpdate, isCurrentWorkspace, setWorkspaceEntry]
298319
);
299320

300321
const isActive = !!workspaceEntry.windowId;

0 commit comments

Comments
 (0)