perf(web): pause dashboard refresh when inactive
This commit is contained in:
parent
b0b09eb8ad
commit
74d9aaf2b4
3 changed files with 257 additions and 31 deletions
90
apps/web/src/lib/client/dashboard-refresh.ts
Normal file
90
apps/web/src/lib/client/dashboard-refresh.ts
Normal file
|
|
@ -0,0 +1,90 @@
|
|||
export interface DashboardRefreshPauseState {
|
||||
visibilityState: DocumentVisibilityState;
|
||||
online: boolean;
|
||||
}
|
||||
|
||||
export function shouldPauseDashboardRefresh(
|
||||
state: DashboardRefreshPauseState,
|
||||
): boolean {
|
||||
return state.visibilityState !== "visible" || !state.online;
|
||||
}
|
||||
|
||||
export function createDashboardRequestAborter() {
|
||||
let shellController: AbortController | undefined;
|
||||
let tileController: AbortController | undefined;
|
||||
|
||||
function abortController(controller: AbortController | undefined) {
|
||||
if (controller && !controller.signal.aborted) {
|
||||
controller.abort();
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
beginShellRun(): AbortSignal {
|
||||
abortController(shellController);
|
||||
abortController(tileController);
|
||||
shellController = new AbortController();
|
||||
tileController = undefined;
|
||||
return shellController.signal;
|
||||
},
|
||||
beginTileRun(): AbortSignal {
|
||||
abortController(tileController);
|
||||
tileController = new AbortController();
|
||||
return tileController.signal;
|
||||
},
|
||||
abortActiveRequests(): void {
|
||||
abortController(shellController);
|
||||
abortController(tileController);
|
||||
shellController = undefined;
|
||||
tileController = undefined;
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
type DashboardRefreshEventTarget = Pick<
|
||||
EventTarget,
|
||||
"addEventListener" | "removeEventListener"
|
||||
>;
|
||||
|
||||
export interface DashboardRefreshLifecycleOptions {
|
||||
documentTarget: DashboardRefreshEventTarget;
|
||||
windowTarget: DashboardRefreshEventTarget;
|
||||
loadDashboard: () => void | Promise<void>;
|
||||
pauseRefreshes: () => void;
|
||||
refreshPaused: () => boolean;
|
||||
}
|
||||
|
||||
export function attachDashboardRefreshLifecycle(
|
||||
options: DashboardRefreshLifecycleOptions,
|
||||
): () => void {
|
||||
function handleRefreshLifecycleChange() {
|
||||
if (options.refreshPaused()) {
|
||||
options.pauseRefreshes();
|
||||
return;
|
||||
}
|
||||
|
||||
void options.loadDashboard();
|
||||
}
|
||||
|
||||
function handlePageHide() {
|
||||
options.pauseRefreshes();
|
||||
}
|
||||
|
||||
options.documentTarget.addEventListener(
|
||||
"visibilitychange",
|
||||
handleRefreshLifecycleChange,
|
||||
);
|
||||
options.windowTarget.addEventListener("online", handleRefreshLifecycleChange);
|
||||
options.windowTarget.addEventListener("offline", handleRefreshLifecycleChange);
|
||||
options.windowTarget.addEventListener("pagehide", handlePageHide);
|
||||
|
||||
return () => {
|
||||
options.documentTarget.removeEventListener(
|
||||
"visibilitychange",
|
||||
handleRefreshLifecycleChange,
|
||||
);
|
||||
options.windowTarget.removeEventListener("online", handleRefreshLifecycleChange);
|
||||
options.windowTarget.removeEventListener("offline", handleRefreshLifecycleChange);
|
||||
options.windowTarget.removeEventListener("pagehide", handlePageHide);
|
||||
};
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue