react-fetch-cache-patterns
React data-fetching patterns at scale — recommender carousels, infinite feeds, pages with many parallel fetches, dashboards. Covers request orchestration (parallelism, batching, deduplication), cache strategy (keys, normalization, staleTime, SWR), backend protection (concurrency caps, debounce/throttle, jittered retries, circuit breakers), prefetching (route loaders, hover/intent, idle, server hydration), failure resilience (AbortController, timeouts, error boundaries, stale fallback, idempotent mutations), and feed/carousel patterns (virtualization, cursor pagination, summary/detail split). Includes 5 ready-to-use scaffolding templates (resource query hook, carousel data loader, infinite feed, hover-prefetch link, request collapser). Trigger when building, reviewing, or refactoring React components that fetch data — even if the user doesn't explicitly mention "performance" or "scale".
Works with
Agent Skills format with YAML frontmatter. Claude Code reads it as-is.
--- name: "react-fetch-cache-patterns" description: "React data-fetching patterns at scale — recommender carousels, infinite feeds, pages with many parallel fetches, dashboards. Covers request orchestration (parallelism, batching, deduplication), cache strategy (keys, normalization, staleTime, SWR), backend protection (concurrency caps, debounce/throttle, jittered retries, circuit breakers), prefetching (route loaders, hover/intent, idle, server hydration), failure resilience (AbortController, timeouts, error boundaries, stale fallback, idempotent mutations), and feed/carousel patterns (virtualization, cursor pagination, summary/detail split). Includes 5 ready-to-use scaffolding templates (resource query hook, carousel data loader, infinite feed, hover-prefetch link, request collapser). Trigger when building, reviewing, or refactoring React components that fetch data — even if the user doesn't explicitly mention \"performance\" or \"scale\"." license: "MIT" --- # Experimental React Data Fetching & Caching Best Practices Implementation patterns for React applications that fetch and cache many API requests without overwhelming the backend. **48 rules across 8 categories**, ordered by execution lifecycle impact — earlier categories cascade through everything downstream. Templates show both library-based (TanStack Query, SWR) **and library-free** (pure React + AbortController) implementations so the patterns are usable regardless of stack constraints. ## When to Apply - Writing or reviewing a React component that calls `fetch`, `useQuery`, `useSWR`, or any data-fetching hook - Designing a list, feed, or carousel that displays many items each requiring data - Investigating "the backend is getting hammered" or "the page loads slowly" symptoms - Choosing between client-side fetching, route loaders, server components, or SSR - Implementing prefetch, retry, optimistic updates, or any failure-handling logic - Refactoring code that already does data fetching but with waterfalls, no cache strategy, or no concurrency limits ## Rule Categories by Priority | # | Category | Impact | Prefix | Rules | |---|----------|--------|--------|-------| | 1 | Request Orchestration | CRITICAL | `orch-` | 7 | | 2 | Cache Strategy | CRITICAL | `cache-` | 7 | | 3 | Backend Protection | CRITICAL | `protect-` | 7 | | 4 | Prefetch & Hydration | HIGH | `prefetch-` | 6 | | 5 | Failure Resilience | HIGH | `resilience-` | 6 | | 6 | Feed & Carousel Patterns | MEDIUM-HIGH | `feed-` | 7 | | 7 | Mutation & Invalidation | MEDIUM | `mutate-` | 4 | | 8 | Component Patterns | MEDIUM | `render-` | 4 | ## Quick Reference ### 1. Request Orchestration (CRITICAL) - [`orch-parallelize-independent-fetches`](references/orch-parallelize-independent-fetches.md) — Use `Promise.all` for independent requests; never serial `await` - [`orch-batch-n-plus-one-fanout`](references/orch-batch-n-plus-one-fanout.md) — Collapse per-row fetches via DataLoader-style batching - [`orch-dedupe-in-flight-requests`](references/orch-dedupe-in-flight-requests.md) — One in-flight request per key, shared across subscribers - [`orch-lift-fetch-to-route-loader`](references/orch-lift-fetch-to-route-loader.md) — Fetch in parallel with route chunk download - [`orch-avoid-effect-chains`](references/orch-avoid-effect-chains.md) — Flatten the dependency graph; only true dependencies wait - [`orch-server-fetch-when-possible`](references/orch-server-fetch-when-possible.md) — Move fetches to RSC/server when they don't depend on client state - [`orch-prefer-bulk-endpoint-for-fanout`](references/orch-prefer-bulk-endpoint-for-fanout.md) — One bulk request beats N parallel requests ### 2. Cache Strategy (CRITICAL) - [`cache-deterministic-keys`](references/cache-deterministic-keys.md) — Canonicalize cache keys; strip undefined, sort arrays - [`cache-normalize-shared-entities`](references/cache-normalize-shared-entities.md) — Store each entity once; views hold references - [`cache-set-stale-time`](references/cache-set-stale-time.md) — Tune `staleTime` to data volatility, not refresh frequency - [`cache-stale-while-revalidate`](references/cache-stale-while-revalidate.md) — Render stale instantly; revalidate in background - [`cache-select-subscribed-fields`](references/cache-select-subscribed-fields.md) — Subscribe to slices, not whole objects - [`cache-shared-key-factory`](references/cache-shared-key-factory.md) — One typed source of truth for keys; prevents read/write drift - [`cache-tiered-stale-fresh`](references/cache-tiered-stale-fresh.md) — Different `staleTime` per data class (realtime, fresh, warm, cold, static) ### 3. Backend Protection (CRITICAL) - [`protect-concurrency-limit-fanout`](references/protect-concurrency-limit-fanout.md) — Cap simultaneous requests with `p-limit`/semaphore - [`protect-collapse-identical-requests`](references/protect-collapse-identical-requests.md) — In-flight dedup at the fetch layer - [`protect-debounce-user-driven-fetches`](references/protect-debounce-user-driven-fetches.md) — Wait for user pause before firing search/filter requests - [`protect-throttle-scroll-triggered`](references/protect-throttle-scroll-triggered.md) — Use IntersectionObserver for viewport-triggered fetches - [`protect-jittered-retry-backoff`](references/protect-jittered-retry-backoff.md) — Add random jitter to prevent thundering-herd retries - [`protect-circuit-breaker`](references/protect-circuit-breaker.md) — Stop calling persistently failing endpoints for a cooldown window - [`protect-rate-limit-aware-client`](references/protect-rate-limit-aware-client.md) — Honor `Retry-After` and `X-RateLimit-*` headers ### 4. Prefetch & Hydration (HIGH) - [`prefetch-hover-intent-links`](references/prefetch-hover-intent-links.md) — Prefetch on hover/pointerdown for instant navigation - [`prefetch-parallel-loader-queries`](references/prefetch-parallel-loader-queries.md) — Parallelize independent queries inside loaders - [`prefetch-hydrate-server-cache`](references/prefetch-hydrate-server-cache.md) — Ship server-fetched data via `HydrationBoundary` / RSC - [`prefetch-idle-likely-next`](references/prefetch-idle-likely-next.md) — Use `requestIdleCallback` for likely-next data - [`prefetch-viewport-triggered-next-page`](references/prefetch-viewport-triggered-next-page.md) — Fire next-page prefetch via `rootMargin` - [`prefetch-budget-and-priority`](references/prefetch-budget-and-priority.md) — Tier prefetches by priority; respect `Save-Data` ### 5. Failure Resilience (HIGH) - [`resilience-abort-on-unmount`](references/resilience-abort-on-unmount.md) — Forward `AbortSignal` to cancel stale fetches - [`resilience-bounded-timeouts`](references/resilience-bounded-timeouts.md) — Set per-endpoint timeouts via `AbortSignal.timeout()` - [`resilience-scoped-error-boundaries`](references/resilience-scoped-error-boundaries.md) — One boundary per data section, not per page - [`resilience-stale-fallback`](references/resilience-stale-fallback.md) — Render stale cache when fresh fetch fails - [`resilience-no-auto-retry-mutations`](references/resilience-no-auto-retry-mutations.md) — Use idempotency keys or don't auto-retry - [`resilience-graceful-degradation`](references/resilience-graceful-degradation.md) — Critical/important/decorative tiers with different failure modes ### 6. Feed & Carousel Patterns (MEDIUM-HIGH) - [`feed-virtualize-long-lists`](references/feed-virtualize-long-lists.md) — Use TanStack Virtual for lists > 50 items - [`feed-cursor-pagination`](references/feed-cursor-pagination.md) — Cursors beat offset for inserts and large offsets - [`feed-split-summary-from-detail`](references/feed-split-summary-from-detail.md) — Carousel summaries lightweight; detail on demand - [`feed-multi-carousel-isolation`](references/feed-multi-carousel-isolation.md) — Per-carousel error/Suspense boundaries + tiered fallbacks for homepage feeds - [`feed-stable-keys-across-pages`](references/feed-stable-keys-across-pages.md) — Use entity IDs as keys; never index - [`feed-image-lazy-and-sized`](references/feed-image-lazy-and-sized.md) — `loading="lazy"` + explicit dimensions - [`feed-bounded-working-set`](references/feed-bounded-working-set.md) — `maxPages` + entity LRU eviction for unbounded feeds ### 7. Mutation & Invalidation (MEDIUM) - [`mutate-optimistic-updates-with-rollback`](references/mutate-optimistic-updates-with-rollback.md) — Snapshot, optimistic write, rollback on error - [`mutate-surgical-invalidation`](references/mutate-surgical-invalidation.md) — Invalidate specific keys, not entire trees - [`mutate-set-data-over-invalidate`](references/mutate-set-data-over-invalidate.md) — Write mutation responses directly into the cache - [`mutate-cancel-queries-on-mutate`](references/mutate-cancel-queries-on-mutate.md) — Cancel in-flight queries before optimistic writes ### 8. Component Patterns (MEDIUM) - [`render-stable-query-keys`](references/render-stable-query-keys.md) — `useMemo` object keys to keep references stable - [`render-cap-fanout-in-lists`](references/render-cap-fanout-in-lists.md) — Lift fetches; batch via DataLoader; virtualize - [`render-suspense-per-section`](references/render-suspense-per-section.md) — One Suspense boundary per data section - [`render-colocate-fetch-with-consumer`](references/render-colocate-fetch-with-consumer.md) — Put `useQuery` next to its consumer, not at the root ## How to Use 1. Open [references/_sections.md](references/_sections.md) for category definitions and impact rationale 2. Read individual rule files for incorrect-vs-correct code examples 3. For ready-to-use scaffolds, see [scaffolding templates](assets/templates/) 4. The [AGENTS.md](AGENTS.md) navigation document (auto-generated) provides a TOC for browsing ## Scaffolding Templates Six ready-to-adapt code templates under `assets/templates/`: | Template | Library deps | Purpose | |----------|-------------|---------| | `use-resource-query.template.tsx` | TanStack Query | Standard query hook with key factory, retry, abort, optional suspense | | `use-resource-query-no-deps.template.tsx` | **None** (pure React + AbortController) | Same patterns as above, library-free: hand-rolled cache, dedup, retry with jitter, staleTime/gcTime, concurrency limit | | `carousel-data-loader.template.tsx` | TanStack Query + react-error-boundary | Single carousel (summary + viewport-triggered detail) *and* multi-carousel feed with per-carousel failure isolation | | `infinite-feed.template.tsx` | TanStack Query + TanStack Virtual | Cursor-paginated infinite feed with virtualization and bounded working set | | `prefetch-link.template.tsx` | None | Hover/intent prefetch link wrapper | | `request-collapser.template.ts` | None | In-flight deduplication + concurrency limit utility | **Library-free path:** if you can't add TanStack Query / SWR / DataLoader to your bundle (size constraints, host-app conflicts, dependency bans), start with `use-resource-query-no-deps.template.tsx` — it implements the core cache/dedup/retry/abort patterns in ~250 lines using only React and the web platform. The other templates that depend on TanStack can be adapted on top of it; only the `request-collapser` and `prefetch-link` templates are zero-dep out of the box. ## Reference Files | File | Description | |------|-------------| | [references/_sections.md](references/_sections.md) | Category definitions, ordering, impact rationale | | [assets/templates/_template.md](assets/templates/_template.md) | Template for authoring new rules | | [metadata.json](metadata.json) | Version, references, abstract | ## Related Skills - `react-optimise` — General React render performance (this skill is data-fetching-specific) - `nextjs-bundle-optimizer` — Bundle/payload optimization for Next.js - `inngest-nextjs-patterns` — Server-side workflow patterns (complements server-fetch guidance)
More Refactoring skills
vercel-react-best-practices
vercel-labs/agent-skills
React and Next.js performance optimization guidelines from Vercel Engineering. This skill should be used when writing, reviewing, or refactoring React/Next.js code to ensure optimal performance patterns. Triggers on tasks involving React components, Next.js pages, data fetching, bundle optimization, or performance improvements.
analyze-project
lllllllama/rigorpilot-skills
Rigor Analyze / Rigor Audit read-only skill for deep learning research repositories. Use when the user wants to read and understand a repository, inspect model structure and training or inference entrypoints, review configs and insertion points, or flag suspicious implementation patterns without modifying code or running heavy jobs. Do not use for active command execution, broad refactoring, speculative code adaptation, or automatic bug fixing.
request-refactor-plan
mattpocock/skills
Create a detailed refactor plan with tiny commits via user interview, then file it as a GitHub issue. Use when user wants to plan a refactor, create a refactoring RFC, or break a refactor into safe incremental steps.

