Replies: 2 comments 5 replies
-
In the meantime, I applied the following diff to my local versions to make it behave the way I need. I can hide this behavior behind a flag and make a proper PR if @TkDodo would be interesting in it! diff --git a/packages/query-core/src/query.ts b/packages/query-core/src/query.ts
index 22dadd37..08dda01f 100644
--- a/packages/query-core/src/query.ts
+++ b/packages/query-core/src/query.ts
@@ -254,8 +254,11 @@ export class Query<
isStaleByTime(staleTime = 0): boolean {
return (
this.state.isInvalidated ||
- !this.state.dataUpdatedAt ||
- !timeUntilStale(this.state.dataUpdatedAt, staleTime)
+ (!this.state.dataUpdatedAt && !this.state.errorUpdatedAt) ||
+ !timeUntilStale(
+ Math.max(this.state.errorUpdatedAt ?? 0, this.state.dataUpdatedAt ?? 0),
+ staleTime,
:...skipping...
diff --git a/packages/query-core/src/query.ts b/packages/query-core/src/query.ts
index 22dadd37..08dda01f 100644
--- a/packages/query-core/src/query.ts
+++ b/packages/query-core/src/query.ts
@@ -254,8 +254,11 @@ export class Query<
isStaleByTime(staleTime = 0): boolean {
return (
this.state.isInvalidated ||
- !this.state.dataUpdatedAt ||
- !timeUntilStale(this.state.dataUpdatedAt, staleTime)
+ (!this.state.dataUpdatedAt && !this.state.errorUpdatedAt) ||
+ !timeUntilStale(
+ Math.max(this.state.errorUpdatedAt ?? 0, this.state.dataUpdatedAt ?? 0),
+ staleTime,
+ )
)
}
@@ -559,6 +562,7 @@ export class Query<
fetchFailureReason: error as TError,
fetchStatus: 'idle',
status: 'error',
+ isInvalidated: false,
}
case 'invalidate':
return {
diff --git a/packages/query-core/src/queryObserver.ts b/packages/query-core/src/queryObserver.ts
index d23850bc..376d1ed2 100644
--- a/packages/query-core/src/queryObserver.ts
+++ b/packages/query-core/src/queryObserver.ts
@@ -714,6 +714,7 @@ function shouldLoadOnMount(
return (
options.enabled !== false &&
!query.state.dataUpdatedAt &&
+ !query.state.errorUpdatedAt &&
!(query.state.status === 'error' && options.retryOnMount === false)
)
}
@@ -753,7 +754,7 @@ function shouldFetchOptionally(
return (
options.enabled !== false &&
(query !== prevQuery || prevOptions.enabled === false) &&
- (!options.suspense || query.state.status !== 'error') &&
+ !options.suspense &&
isStale(query, options)
)
} |
Beta Was this translation helpful? Give feedback.
-
|
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
I posted it on SO but it got auto-deleted before I could add the codesandbox.
Codesandbox: https://codesandbox.io/s/react-query-failed-prefetch-mi96w1?file=/src/App.tsx
Despite staletime being set to
10_000
, error queries are retried on every call. This is bad because it overwhelms my API with network calls when there are errors.Original SO post
It seems that whenever a query throws an error, it's staleTime is forcibly set to
0
and made to be refetched in the next usage. Is it possible to make staleTime for failed queries consistent with succeeded queries?My issue is that I prefetch a list of queries in a component
and failed queries get "re-prefetched" on every render because all failed queries seem to be immediately marked stale. I thought about a checking to ignore failed queries:
However this causes a new issue where I can't make the failed queries re-fetch when their error might have gone away (after the staletime).
I guess I could do some math comparing the time of the error with the current time, and deciding whether pre-fetch based on that, but while it would solve the prefetch issue, the same sort of problem happens with components that call
useQuery
instead which would require me to do funny things withenabled
. In short, it would force me to take up a lot of undue complexity to make failed queries behave consistently with succeeding queries.Beta Was this translation helpful? Give feedback.
All reactions