使用 Apollo 的 writeFragment 更新嵌套列表

Eri*_*tvl 8 javascript reactjs graphql react-apollo

我正在开发一个应用程序,在该应用程序中可以使用方向舵和其他东西配置一艘船。数据库结构有点嵌套,到目前为止,我一直将 GraphQL 查询与数据库保持一致。

这意味着:我可以使用一些查询 ship(projectId, shipId) 获取一艘船,但我使用的是嵌套查询:

query {
    project(id:1) {
        id
        title
        ship(id:1) {
            id
            name
            rudders {
                id
                position
            }
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

这样的结构当然会导致很多嵌套数组。例如,如果我刚刚添加了一个新方向舵,则必须使用 cache.readQuery 进行检索,它为我提供项目对象而不是方向舵列表。要将方向舵添加到缓存中,我会得到一条带有嵌套的、解构的对象的长行,这使得代码难以阅读。

所以我想到了使用 GraphQL 片段。在 Internet 上,我看到它们被大量使用以防止必须在大量对象上重新键入多个字段(我个人认为这也非常有用!)。然而,片段用于数组的例子并不多。

当将一些数据附加到嵌套在某些缓存查询中的数组时,数组的片段可以保存所有对象解构。使用 Apollo 的 readFragment 和 writeFragment,我设法让一些东西工作起来。

片段:

export const FRAGMENT_RUDDER_ARRAY = gql`
    fragment rudderArray on ShipObject {
        rudders {
            id
            position
        }
    }
`
Run Code Online (Sandbox Code Playgroud)

用于主船查询:

query {
    project(id: ...) {
        id
        title
        ship(id: ...) {
            id
            name
            ...rudderArray
        }
    }
}
${RUDDER_FRAGMENT_ARRAY}
Run Code Online (Sandbox Code Playgroud)

使用这个,我可以编写一个更清晰的 update() 函数来在突变后更新 Apollo 的缓存。见下文:

const [ createRudder ] = useMutation(CREATE_RUDDER_MUTATION, {
    onError: (error) => { console.log(JSON.stringify(error))},
    update(cache, {data: {createRudder}}) {
        const {rudders} = cache.readFragment({
            id: `ShipObject:${shipId}`,
            fragment: FRAGMENT_RUDDER_ARRAY,
            fragmentName: 'rudderArray'
        });

        cache.writeFragment({
            id: `ShipObject:${shipId}`,
            fragment: FRAGMENT_RUDDER_ARRAY,
            fragmentName: 'rudderArray',
            data: {rudders: rudders.concat(createRudder.rudder)}
        });
    }
});

Run Code Online (Sandbox Code Playgroud)

现在我的问题是什么?好吧,因为我几乎从未看到片段用于此目的,所以我发现它运行良好,但我想知道这是否有任何缺点。

另一方面,我也决定分享这个,因为我找不到任何例子。因此,如果这是一个好主意,请随意使用该模式!