更新后 Mutation 组件与商店不同步
Mutation component becomes out of sync with the store after updates
这段看似很长,其实很简单;它创建一个节点并呈现其数据,然后更新节点并呈现更新的数据,但是创建的数据不会更新,即使直接检查商店显示 createFoo
查询的商店有已更新。我想了解如何确保依赖于 Apollo 客户端存储的数据的组件是最新的,最好是自动更新。
const CREATE_FOO = gql`
mutation {
createFoo(data: {}) {
id
bar
}
}
`;
const UPDATE_FOO = gql`
mutation($id: ID!) {
updateFoo(where: { id: $id }, data: { bar: "baz" }) {
id
bar
}
}
`;
<Mutation mutation={CREATE_FOO}>
{(createFoo, { data: createData }) => {
if (createData) {
return (
<div>
<p>{JSON.stringify(createData.createFoo)}</p>
<Mutation
mutation={UPDATE_FOO}
variables={{ id: createData.createFoo.id }}
>
{(updateFoo, { data: updateData }) => {
if (updateData) {
return <p>{JSON.stringify(updateData.updateFoo)}</p>;
}
return (
<button onClick={updateFoo} type="button">
updateFoo
</button>
);
}}
</Mutation>
</div>
);
}
return (
<button onClick={createFoo} type="button">
createFoo
</button>
);
}}
</Mutation>
数据模型:
type Foo {
id: ID! @unique
bar: String
}
存储数据:
{
"ROOT_QUERY": {
"userSidebarWidth": 200
},
"Foo:cjqd2cd41zi140a98ugrjpz2m": {
"id": "cjqd2cd41zi140a98ugrjpz2m",
"bar": "baz",
"__typename": "Foo"
},
"ROOT_MUTATION": {
"createFoo({\"data\":{}})": {
"type": "id",
"generated": false,
"id": "Foo:cjqd2cd41zi140a98ugrjpz2m",
"typename": "Foo"
},
"updateFoo({\"data\":{\"bar\":\"baz\"},\"where\":{\"id\":\"cjqd2cd41zi140a98ugrjpz2m\"}})": {
"type": "id",
"generated": false,
"id": "Foo:cjqd2cd41zi140a98ugrjpz2m",
"typename": "Foo"
}
}
}
假设您有一个这样的 Query
组件:
const GET_FOO = gql`
query SomeQuery {
getFoo {
id
bar
}
}
`;
<Query query={GET_FOO}>
{({ loading, error, data }) => (
<SomeComponent/>
)}
</Query>
挂载组件时,Apollo 从服务器或缓存中获取数据(取决于数据是否被缓存以及您的获取策略是什么)。但是,它也订阅 缓存中的更改。因此,如果您获取了一个 ID 为 1
的 Foo
,并且它通过另一个操作在缓存中进行了更新,组件将收到通知并相应地进行更新。具体来说,传递给 render prop 函数的 data
值将被更改以反映缓存中的更改。
Mutation
组件具有类似于 Query
组件的渲染属性函数签名,包括 data
属性。但是,这个属性只反映调用mutate
函数时返回的数据。虽然突变的结果存储在缓存中,但通过 Mutation
组件公开的 data
不是订阅缓存的结果——相反,它只是一种对mutate
调用的结果。 Mutation
组件中的 data
唯一可能发生变化的情况是再次调用 mutate
函数。
如果我们修改您的示例并将组件包装在 Query
组件中,我们可以在您的组件内显示来自查询的数据,并可能忽略来自两个 [=] 之一的 data
15=] 组件。假设 Query
和 Mutations
引用缓存中的相同项目,来自 Query
组件的数据将在任何一个突变解决时更新。
这段看似很长,其实很简单;它创建一个节点并呈现其数据,然后更新节点并呈现更新的数据,但是创建的数据不会更新,即使直接检查商店显示 createFoo
查询的商店有已更新。我想了解如何确保依赖于 Apollo 客户端存储的数据的组件是最新的,最好是自动更新。
const CREATE_FOO = gql`
mutation {
createFoo(data: {}) {
id
bar
}
}
`;
const UPDATE_FOO = gql`
mutation($id: ID!) {
updateFoo(where: { id: $id }, data: { bar: "baz" }) {
id
bar
}
}
`;
<Mutation mutation={CREATE_FOO}>
{(createFoo, { data: createData }) => {
if (createData) {
return (
<div>
<p>{JSON.stringify(createData.createFoo)}</p>
<Mutation
mutation={UPDATE_FOO}
variables={{ id: createData.createFoo.id }}
>
{(updateFoo, { data: updateData }) => {
if (updateData) {
return <p>{JSON.stringify(updateData.updateFoo)}</p>;
}
return (
<button onClick={updateFoo} type="button">
updateFoo
</button>
);
}}
</Mutation>
</div>
);
}
return (
<button onClick={createFoo} type="button">
createFoo
</button>
);
}}
</Mutation>
数据模型:
type Foo {
id: ID! @unique
bar: String
}
存储数据:
{
"ROOT_QUERY": {
"userSidebarWidth": 200
},
"Foo:cjqd2cd41zi140a98ugrjpz2m": {
"id": "cjqd2cd41zi140a98ugrjpz2m",
"bar": "baz",
"__typename": "Foo"
},
"ROOT_MUTATION": {
"createFoo({\"data\":{}})": {
"type": "id",
"generated": false,
"id": "Foo:cjqd2cd41zi140a98ugrjpz2m",
"typename": "Foo"
},
"updateFoo({\"data\":{\"bar\":\"baz\"},\"where\":{\"id\":\"cjqd2cd41zi140a98ugrjpz2m\"}})": {
"type": "id",
"generated": false,
"id": "Foo:cjqd2cd41zi140a98ugrjpz2m",
"typename": "Foo"
}
}
}
假设您有一个这样的 Query
组件:
const GET_FOO = gql`
query SomeQuery {
getFoo {
id
bar
}
}
`;
<Query query={GET_FOO}>
{({ loading, error, data }) => (
<SomeComponent/>
)}
</Query>
挂载组件时,Apollo 从服务器或缓存中获取数据(取决于数据是否被缓存以及您的获取策略是什么)。但是,它也订阅 缓存中的更改。因此,如果您获取了一个 ID 为 1
的 Foo
,并且它通过另一个操作在缓存中进行了更新,组件将收到通知并相应地进行更新。具体来说,传递给 render prop 函数的 data
值将被更改以反映缓存中的更改。
Mutation
组件具有类似于 Query
组件的渲染属性函数签名,包括 data
属性。但是,这个属性只反映调用mutate
函数时返回的数据。虽然突变的结果存储在缓存中,但通过 Mutation
组件公开的 data
不是订阅缓存的结果——相反,它只是一种对mutate
调用的结果。 Mutation
组件中的 data
唯一可能发生变化的情况是再次调用 mutate
函数。
如果我们修改您的示例并将组件包装在 Query
组件中,我们可以在您的组件内显示来自查询的数据,并可能忽略来自两个 [=] 之一的 data
15=] 组件。假设 Query
和 Mutations
引用缓存中的相同项目,来自 Query
组件的数据将在任何一个突变解决时更新。