因此,我一直尝试在 React 应用程序中使用 apollo-boost 来使用缓存来管理我的客户端状态,在查询中使用 @client 指令,但我遇到了一些问题。
基本上,我使用 writeQuery() 将 bool 值写入组件(我们称之为组件 A)中的本地应用程序状态,并希望使用 readQuery() 在另一个组件(我们称之为组件 B)中获取该值在 componentDidUpdate 方法内。问题是,组件 B 中的 readQuery() 在组件 A 中的 writeQuery 设置缓存/本地状态中的值之前运行,因此组件 B 读取的值是错误的。
我已经通过使用 setTimeout 延迟 readQuery() 来确认这一点,并且确实在使用超时后,该值是正确的,但是这个解决方案不可信,我可能不知道 Apollo 客户端中的某些内容,因为这个功能对于本地状态管理来说是非常基本的。有什么建议吗?
我相信在 Redux 中这个问题已经解决了,因为状态被注入(inject)到 props 中,这使得组件更新,因此组件 A 是改变状态的组件,组件 B 甚至不必使用 componentDidUpdate 来获取新值,因为状态将被注入(inject)并且组件 B 将使用正确的值进行更新。
任何帮助将不胜感激,抱歉,如果我没有说清楚!
编辑: writeQuery() 正在 Mutation 解析器内部使用。
最佳答案
诸如 readQuery
和 writeQuery
之类的方法旨在用于读取和修改突变内部的缓存。一般来说,它们不应该直接在组件内部使用。通过调用readQuery
,您只需从缓存中获取数据一次。相反,您应该使用查询
组件。
const TODO_QUERY = gql`
query GetTodos {
todos @client {
id
text
completed
}
}
`
<Query query={TODO_QUERY}>
{({ data }) => {
if (data.todos) return <ToDoListComponent todos={data.todos}/>
return null
}}
</Query>
Query
组件订阅缓存的相关更改,因此 data
的值将在缓存更新时更新。
同样,您应该为要对缓存进行的任何更改创建适当的突变,然后利用 Mutation
组件来实际突变缓存。
const client = new ApolloClient({
clientState: {
defaults: {
todos: []
},
resolvers: {
Mutation: {
addTodo: (_, { text }, { cache }) => {
const previous = cache.readQuery({ query: TODO_QUERY })
const newTodo = { id: nextTodoId++, text, completed: false, __typename: 'TodoItem' }
const data = {
todos: previous.todos.concat([newTodo]),
}
cache.writeQuery({ query, data })
return newTodo
},
},
}
}
})
<Mutation mutation={ADD_TODO}>
{(addTodo) => (
// use addTodo to mutate the cache asynchronously
)}
</Mutation>
请查看the docs了解更多详情。
关于javascript - Apollo 客户端本地状态缓存竞争条件?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54349855/