diff --git a/src/components/messageStream/hooks/usePostStream.ts b/src/components/messageStream/hooks/usePostStream.ts index 5a12617..491e963 100644 --- a/src/components/messageStream/hooks/usePostStream.ts +++ b/src/components/messageStream/hooks/usePostStream.ts @@ -112,6 +112,17 @@ function streamKey(params: PostStreamParams): string { return buildRealUrl(params); } +function cacheFirstPage( + params: PostStreamParams, + page: PostListResponse, +): void { + streamCache.set(streamKey(params), { + items: itemsOrEmpty(page.items), + cursor: page.nextCursor, + hasMore: !!page.nextCursor, + }); +} + /** * Warm the cache for a stream view before the user navigates to it, so opening * the page shows content immediately instead of starting to load on arrival. @@ -119,20 +130,31 @@ function streamKey(params: PostStreamParams): string { */ export function prefetchPostStream(params: PostStreamParams): void { if (USE_MOCK) return; + const key = streamKey(params); + if (streamCache.has(key)) return; + const url = buildRealUrl(params); - if (readJSONCache(url)) return; - getJSON(url).catch(() => {}); + const cachedPage = readJSONCache(url); + if (cachedPage) { + cacheFirstPage(params, cachedPage); + return; + } + + getJSON(url) + .then((page) => cacheFirstPage(params, page)) + .catch(() => {}); } export function usePostStream(params: PostStreamParams): PostStreamResult { - const [items, setItems] = useState([]); - const [hasMore, setHasMore] = useState(true); - const [isLoading, setIsLoading] = useState(false); + const initialCached = streamCache.get(streamKey(params)); + const [items, setItems] = useState(() => initialCached?.items ?? []); + const [hasMore, setHasMore] = useState(() => initialCached?.hasMore ?? true); + const [isLoading, setIsLoading] = useState(() => !initialCached); const [error, setError] = useState(null); const reqIdRef = useRef(0); - const cursorRef = useRef(undefined); - const hasMoreRef = useRef(true); + const cursorRef = useRef(initialCached?.cursor); + const hasMoreRef = useRef(initialCached?.hasMore ?? true); const loadingRef = useRef(false); const fetchPage = useCallback( diff --git a/src/layouts/PublicLayout.tsx b/src/layouts/PublicLayout.tsx index eb7424f..e3210d2 100644 --- a/src/layouts/PublicLayout.tsx +++ b/src/layouts/PublicLayout.tsx @@ -764,9 +764,8 @@ function BottomNavIcon({ icon: "home" | "document" | "bookmark" | "update"; active: boolean; }) { - const src = active - ? `${NAVBAR_ICON_BASE}/${icon}-active.svg` - : `${NAVBAR_ICON_BASE}/${icon}-inactive.svg`; + const activeSrc = `${NAVBAR_ICON_BASE}/${icon}-active.svg`; + const inactiveSrc = `${NAVBAR_ICON_BASE}/${icon}-inactive.svg`; return ( - + + + + {label} );