如何在反应查询中重新获取集合的单个项目

How to re-fetch single items of a collection in react-query

假设我有一个获取电影集合的查询:

useQuery(['movies'], getMovies)

现在,如果我只想重新获取一部电影而不是全部,我可以这样写:

useQuery(['movies', movieId], () => getMovie(movieId))

问题是我使用了不同的查询键,它会复制数据。我会在我的缓存中存储这部电影两次。

那么,更新获取的集合中的单个项目的反应查询方式是什么?所有使用 useQuery(['movies']) 的组件都应在获取单个项目时自动更新。

我觉得有两种方式:

  1. 就像您用新密钥描述的那样。是的,数据将在缓存中“两次”,但“列表”数据通常与“详细信息”数据具有不同的结构。 movies-list 可能只有 id 和 name,而 details 也有描述等。如果这样做,请确保为它们提供相同的前缀 ('movies'),以便您可以在无效时使用模糊匹配:queryClient.invalidateQueries(['movies']) 将使列表和所有详细信息无效,这很好.

  2. 您可以使用 select 选项构建详细查询:

const useMovies = (select) => useQuery(['movies'], getMovies, { select })
const useMovie = (id) => useMovies(movies => movies.find(movie => movie.id === id))

有了它,你可以做 useMovie(5),因此只会订阅 ID 为 5 的电影。这非常好,而且渲染优化 - 如果 ID 为 4 的电影更新,订阅的组件ID 为 5 的电影将不会重新渲染。

“缺点”当然是从数据/网络角度来说,只有一个查询——列表查询,所以每次后台refetch的时候,都会从后台查询整个列表。但它仍然是避免缓存中数据重复的好方法,它也使乐观更新更容易,因为您只需写入更新一个缓存条目。