fix(pwa): fix pull-to-refresh's at-top check and extend coverage

The authenticated shell's actual scroll container is <main
id="main-content"> (AuthShell sets it overflow-y-auto inside a
height-locked layout); document.scrollingElement never moves there, so
the gesture's "only arm at the top of the page" check was permanently
true regardless of how far a user had scrolled a long list. Point it
at the real scroll container instead, with the old document-root check
kept as a fallback for the few body-scrolled surfaces outside the
shell.

Extend pull-to-refresh from 4 pages (labs/checkups/mood/measurements)
to the dashboard, /insights, /medications, and the documents vault —
the sharpest PWA-resume-staleness surfaces, per the audit: a
background-refreshed dose or a cross-device write otherwise sits
stale until a full remount or the staleTime window lapses.
This commit is contained in:
Marc-André Bombeck committed 2026-07-18 03:52:32 +02:00
1 parent c1c3aa9754
commit b00450aec8
5 files changed
+90 -8

No files matched your search

@@ -38,6 +38,8 @@ import { PageHeader } from "@/components/ui/page-header";
import { QueryErrorCard } from "@/components/ui/query-error-card";
import { Skeleton } from "@/components/ui/skeleton";
import { useAuth } from "@/hooks/use-auth";
import { usePullToRefresh } from "@/hooks/use-pull-to-refresh";
import { PullToRefreshIndicator } from "@/components/ui/pull-to-refresh-indicator";
import { apiGet, apiPost } from "@/lib/api/api-fetch";
import { useTranslations } from "@/lib/i18n/context";
import { invalidateKeys, queryKeys } from "@/lib/query-keys";
@@ -233,6 +235,18 @@ export function DocumentsView() {
[list.data],
);
// v1.30.1 M12 — pull-to-refresh parity with labs/checkups/mood/
// measurements/medications. The vault is one of the sharpest PWA-resume-
// staleness surfaces named in the audit: a document indexed server-side
// while the tab was backgrounded (auto-index / AI summary) otherwise
// stays invisible until the bounded processing poll above happens to
// catch it or the user navigates away and back.
const refreshDocuments = useCallback(
() => Promise.all([list.refetch(), usage.refetch()]),
[list, usage],
);
const pull = usePullToRefresh({ onRefresh: refreshDocuments });
const upload = useDocumentUpload(
usage.data ? { maxFileBytes: usage.data.maxFileBytes } : undefined,
);
@@ -595,6 +609,7 @@ export function DocumentsView() {
return (
<div className="space-y-6">
<PullToRefreshIndicator {...pull} />
<PageHeader
title={t("documents.title")}
description={t("documents.subtitle")}