Chapter 5: Comparison — vs SWR, Apollo, RTK Query, React Router
Core Idea
Among mainstream data-fetching/cache libraries, TanStack Query is the one with the broadest feature set out of the box (offline support, structural-sharing memoization, full-featured infinite queries, cache manipulation API) at the cost of not doing normalized caching, which GraphQL-native Apollo does support.
Key Concepts
- Caching strategy: TanStack Query uses hierarchical key → value caching (array
queryKeys with partial matching); SWR uses a flatter unique-key cache; Apollo normalizes by GraphQL schema/entity; RTK Query uses key → value like SWR but with referential-equality change detection instead of deep comparison.
- Partial query matching: because query keys serialize deterministically, you can invalidate/refetch every query whose key starts with
['todos'] without enumerating each variant — a capability SWR only partially supports and RTK Query/Apollo handle differently.
- Data memoization: TanStack Query does full structural sharing (only new object references for parts of the data that actually changed), reducing re-renders; most alternatives use referential-identity checks instead.
- What none of the "no" alternatives share with it: offline mutation support, general cache dehydration/rehydration for SSR, and an abstracted/agnostic core usable outside React.
- What it deliberately doesn't do: normalized caching (storing entities in a flat, deduplicated graph) — Apollo is the one built around this because GraphQL's schema gives it the structure to normalize against.
Reference Tables
| Capability | TanStack Query | SWR | Apollo Client | RTK Query |
|---|
| Caching model | Hierarchical key → value, partial match | Unique key → value | Normalized by GraphQL schema | Unique key → value, referential equality |
| Data query syntax | Promise/REST/GraphQL (agnostic) | Promise/REST/GraphQL | GraphQL-native | Promise/REST/GraphQL |
| Normalized caching | No | No | Yes | No |
| Offline mutation support | Yes | No | Partial (3rd-party) | No |
| Framework-agnostic core | Yes | No | Partial | No (tied to Redux) |
| React Suspense support | Yes | Yes | Yes | No |
Key Takeaways
- Pick Apollo specifically when normalized caching against a GraphQL schema is the actual requirement — it's the one structural advantage the others don't replicate.
- Pick TanStack Query as the framework-agnostic, protocol-agnostic default when you're not committed to GraphQL or Redux and want the widest feature set (offline, structural sharing, dehydration/hydration) with the least lock-in.
- RTK Query is the natural fit only if the app is already built on Redux Toolkit — its caching model is otherwise a strict subset of TanStack Query's.
Connects To
- GraphQL: how to still use GraphQL as the transport with TanStack Query (via
graphql-request + codegen), without normalized caching.
- Server Rendering & Hydration: the dehydration/rehydration capability referenced here.