【发布时间】:2020-09-13 17:36:46
【问题描述】:
我的情况是这样的:我的视图中有多个组件最终依赖于相同的数据,但在某些情况下,视图状态是从数据派生的。当基础数据发生变化时,如何确保我的整个视图保持同步?我将使用大家最喜欢的Star Wars API 举例说明。
首先,我显示一个所有电影的列表,查询如下:
# ALL_FILMS
query {
allFilms {
id
title
releaseDate
}
}
接下来,我想在 UI 中使用一个单独的组件来突出显示最近的电影。没有查询,所以我将使用客户端解析器来实现它。查询将是:
# MOST_RECENT_FILM
query {
mostRecentFilm @client {
id
title
}
}
以及解析器:
function mostRecentFilmResolver(parent, variables, context) {
return context.client.query({ query: ALL_FILMS }).then(result => {
// Omitting the implementation here since it's not relevant
return deriveMostRecentFilm(result.data);
})
}
现在,有趣的是 SWAPI 开始将 The Last Jedi 和 The Rise of Skywalker 添加到其电影列表中。我们可以假设我是列表中的polling,以便定期重新获取它。太好了,现在我的列表 UI 是最新的。但是我的“最近的电影”用户界面并没有意识到有什么变化——它仍然停留在 2015 年显示原力觉醒,尽管用户可以清楚地看到有更新的电影。
也许我被宠坏了;我来自MobX 的世界,像 Just Works™ 这样的东西。但这并不像一个不常见的问题。在 Apollo/GraphQL 领域是否有保持同步的最佳实践?我是否以完全错误的方式处理这个问题?
我的一些想法:
- 我的“最新电影”查询也可以定期轮询。但是您不想经常轮询;毕竟,星球大战电影每隔一年左右才会上映。 (谢谢,迪士尼!)根据轮询间隔的重叠方式,仍然会有一个很大的窗口让事情不同步。
- 而不是将
deriveMostRecentFilm逻辑放在解析器中,只需将其放在组件中并在组件之间共享ALL_FILMS查询。那会起作用,但这基本上是在回答“我如何让它在阿波罗工作?”与“不要使用 Apollo”。 - 一些复杂的系统,用于跟踪查询之间的依赖关系并在此基础上链接刷新。 (如果可以避免的话,我不想发明这个!)
【问题讨论】:
标签: graphql apollo apollo-client