Comparison with other tools
While there are numerous tools for async state we could compare to, the libraries were chosen as the strongest representation of their general approach.
Rest Hooks' design is aimed at treating remote data like it is local. This means component logic should be no more complex than useState and setState. This design requires Rest Hooks to automatically ensures safety and performance, rather than requiring users to layer their own state manipulation logic.
From those adopting Rest Hooks we've seen
- Dramatic increase in developer velocity
- Elimination of networking related jank
- No more bug-whack-a-mole
- Improved learning curves - no need for expensive and time consuming courses
- Reduction in server load by overfetching improvements
- Navigational and interaction speed improvements
Platforms
Rest Hooks | SWR | RTK-Query | Apollo | Relay | |
---|---|---|---|---|---|
Fetch Protocols | REST, GraphQL, img+binary, user-defined1 | user-defined1 | REST, user-defined1 | GraphQL | GraphQL |
Push Protocols | Websockets, SSE, user-defined1 | 🛑 | Websockets, user-defined1 | GraphQL subscriptions | GraphQL subscriptions |
Polling (hybrid) | ✅ | 🟡 | ✅ | ✅ | ✅ |
Offline persistence | 🟡 user-defined1 | 🛑 | 🟡 user-defined1 | ✅ | 🛑 |
View Library | React web, React Native, NextJS, React SSR | React web | React web, Svelte | React web | React web, React native |
While the maintainers do check this from time to time, we encourage you to fix any inaccuracies on this table. Be sure to include relevant links to docs as well as PRS for newly added features in the PR description.
We focus on outcomes rather than how they are achieved, as that can be somewhat subjective. Such comparisons are useful but don't fit into a table of check boxes. For instance, a car missing a cassette tape player but having bluetooth and internet streaming isn't necessarily worse than a car with just a tape player.
Safety
Rest Hooks | SWR | RTK-Query | Apollo | Relay | |
---|---|---|---|---|---|
Data Integrity | |||||
Typed returns | ✅ | 🛑 | 🛑 | ||
Typed arguments | ✅ | 🛑 | 🛑 | ||
Typed mutations | ✅ | 🛑 | 🛑 | ||
Validation | ✅ | 🛑 | 🛑 | 🛑 | |
Global referential integrity | ✅ | 🛑 | 🛑 | 🛑 | |
Atomic mutations | ✅ | 🛑 | 🛑 | ✅ | |
Mutation isolation | ✅ | 🛑 | ✅ | ||
Data Consistency | |||||
No component tearing | ✅ | ✅ | |||
No mutation flashes | ✅ | 🛑 | 🛑 | ✅ | |
Across queries | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Fetch order protection | ✅ | 🛑 | 🛑 | ||
Entity ordering protection | ✅ | 🛑 | 🛑 | ||
Relationships | |||||
one-to-one | ✅ | 🛑 | 🛑 | ✅ | ✅ |
many-to-one | ✅ | 🛑 | 🛑 | ✅ | ✅ |
many-to-many | 🟡 | 🛑 | 🛑 | ✅ | |
Liveliness | |||||
Expiry policy | ✅ | 🛑 | ✅ |
Performance
Rest Hooks | SWR | RTK-Query | Apollo | Relay | |
---|---|---|---|---|---|
Global cache | ✅ | ✅ | ✅ | ✅ | ✅ |
Parallel fetches | ✅ | ✅ | ✅ | ✅ | ✅ |
Reuse data from other fetch | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
Immediate updates | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Immediate deletes | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Immediate creates | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Optimistic Updates | ✅ | 🛑 | 🟡 manual, race conditions, unsafe | 🟡 | ✅ |
Global referential integrity | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
Concurrent mode support | |||||
Suspense | ✅ | ✅ | 🛑 | 🛑 | ✅ |
useTransition | ✅ | 🛑 | 🛑 | ✅ | |
Deferred data | ✅ | 🛑 | 🛑 | ✅ | |
Fetch-while-render | ✅ | 🛑 | 🛑 | 🛑 | ✅ |
SSR | ✅ | 🛑 | ✅ | 🛑 | |
Streaming Server Rendering | ✅ | 🛑 | 🛑 | 🛑 | |
Selective Hydration | ✅ | 🛑 | 🛑 | 🛑 | |
SSR primes cache | ✅ | 🛑 | 🛑 | 🛑 | |
Bundle size | |||||
Auto code split | ✅ | ✅ | 🛑 | 🛑 | |
Entry Bundle (gzip) | 7.8kb | 4.1kb | 17kb | 27.9kb | 55.7kb |
Overfetch elimination | |||||
Auto fetch deduplication | ✅ | ✅ | ✅ | ✅ | |
Nested data support | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Client-side joins | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
No overfetch on delete | ✅ | 🛑 | 🛑 | ✅ | ✅ |
No overfetch on update | ✅ | 🛑 | 🟡 | ✅ | ✅ |
No overfetch on create | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Zero fetch on SSR | ✅ | 🛑 | 🛑 | 🛑 | |
No polling overfetch | ✅ | 🛑 | 🛑 |
Features
How quickly one can get started
Rest Hooks | SWR | RTK-Query | Apollo | Relay | |
---|---|---|---|---|---|
Can use with redux | ✅ | 🛑 | ✅ | 🛑 | 🛑 |
Infinite scrolling | ✅ | ✅ | 🛑 | ✅ | |
401 handling | ✅ | 🛑 | 🟡 | 🛑 | |
Aborts | ✅ | 🛑 | 🛑 | 🛑 | |
Arbitrary store queries | ✅ | 🛑 | ✅ | 🛑 | |
Debugging inspector | ✅ | 🛑 | ✅ | ✅ | ✅ |
Data mocking | ✅ | 🛑 | 🛑 | 🛑 | ✅ |
Storybook | ✅ | 🛑 | 🛑 | 🛑 | |
Retries | 🟡 user-defined1 | 🛑 | ✅ | 🟡 user-defined1 | 🛑 |
Declarative data transforms | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
Extensibility
How well it scales as code size and usage increases
Rest Hooks | SWR | RTK-Query | Apollo | Relay | |
---|---|---|---|---|---|
Middlewares | ✅ | 🛑 | ✅ | 🛑 | 🛑 |
Abstracted/Agnostic Core | ✅ | 🛑 | ✅ | 🛑 | 🛑 |
Composition | |||||
Hook+API disjoint | ✅ | 🛑 | 🟡 | 🟡 | 🟡 |
Fallback+dependency disjoint | ✅ | ✅ | 🛑 | 🛑 | ✅ |
Data+API disjoint | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
Actions+API disjoint | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
Data co-location | ✅ | ✅ | 🛑 | 🛑 | ✅ |
Code sharing | |||||
Protocol hierarchy | ✅ | 🛑 | 🛑 | ✅ | ✅ |
Data hierarchy | ✅ | 🛑 | 🛑 | 🟡 | 🟡 |
Resource | ✅ | 🛑 | 🛑 | 🛑 | 🛑 |
[1]: user-defined
means it has extensibility to support arbitrary user implementations, but does not ship with the library itself