使所有查询失效,但仅重新获取活动查询。

huangapple go评论63阅读模式
英文:

Invalidate all queries but refetch only active

问题

我想要实现这样的行为:在成功进行突变之后,所有具有依赖数据的查询应标记为无效,但只有活动的查询应立即重新获取,而非活动的查询应只在它们变为活动时重新获取。

据我了解,使用 react-query API 可以实现这种行为:

queryClient.invalidateQueries(['query-key'], { refetchType: 'active' })

它会使所有匹配的查询无效,但只会重新获取活动的查询,但当无效的非活动数据变为活动时,它不会重新获取。这可能不仅与无效调用的方式有关,还可能与一些默认查询选项有关。

目前,我只是重新获取所有无效的查询,无论它们是否活动,但这并不是正确的方法。

// 查询客户端默认设置
const queryClient = new QueryClient({
  defaultOptions: {
    queries: {
      retry: false,
      refetchOnMount: false,
      refetchOnReconnect: false,
      refetchOnWindowFocus: false,
    },
  },
})

// 带有查询无效的突变
const useCreateExample = () => {
  const queryClient = useQueryClient()

  return useMutation({
    mutationFn: createExample,
    onSuccess: () => {
      queryClient.invalidateQueries(['example'], { refetchType: 'all' })
    },
  })
}
英文:

I want to achieve the behavior where after successful mutation, all queries with dependent data should be marked as invalid but only active should be refetched right away, and inactive should be refetched only whether they would become active.

As I understand the react-query API, this behavior can be achieved using

queryClient.invalidateQueries(['query-key'], { refetchType: 'active' })

as it invalidates all queries that match but refetch only active ones, but this is not refetch invalid inactive data when it becomes active. Maybe it can be a problem not only in the way invalidation is called but also in some default query options.

Currently, I'm simply refetch all invalid queries, whether they are active or not, but this is quite not the right approach.

// query client defaults
const queryClient = new QueryClient({
  defaultOptions: {
    queries: {
      retry: false,
      refetchOnMount: false,
      refetchOnReconnect: false,
      refetchOnWindowFocus: false,
    },
  },
})

// mutation with query invalidation
const useCreateExample = () => {
  const queryClient = useQueryClient()

  return useMutation({
    mutationFn: createExample,
    onSuccess: () => {
      queryClient.invalidateQueries(['example'], { refetchType: 'all' })
    },
  })
}

答案1

得分: 0

TLDR:检查你的默认查询选项,它们可以防止重新获取陈旧数据。


正如我所预测的那样,问题并不是无效,而是在默认查询选项中。如重要的默认值中所指出的,根据默认情况,会在某些触发事件(挂载、重新聚焦、重新连接)后重新获取陈旧数据,但你可以阻止这种行为。我的默认设置在任何情况下都会阻止数据的重新获取,因为没有必要定期更新界面。

但不清楚的是,即使你从非活动查询中使数据无效并且设置refetchOnMount: false,无效的数据也不会被重新获取。感谢@tkdodo的这个评论提供的帮助。

英文:

TLDR: Check your default query options, they can prevent refetching stale data.


As I predicted, the problem was not in invalidation, but in default query options. As pointed out in Important defaults, stale data will be refetching after some triggers (mounting, refocus, reconnect) by default, but you can prevent this behavior. My defaults prevent data refetching in any case because there was no need for the UI to be updated regularly.

But it was unclear that even if you invalidate the data from an inactive query and have refetchOnMount: false - the invalid data won't be refetched anyway. Thanks this comment by @tkdodo for the help.

huangapple
  • 本文由 发表于 2023年7月12日 20:29:29
  • 转载请务必保留本文链接:https://go.coder-hub.com/76670546.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定