如何在GraphQL中建模递归数据结构 [英] How to model recursive data structures in GraphQL

查看:104
本文介绍了如何在GraphQL中建模递归数据结构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个树形数据结构,我想通过GraphQL API返回.

I have a tree data structure that I would like to return via a GraphQL API.

结构不是特别大(足够小,不会在一次调用中将其返回).

The structure is not particularly large (small enough not to be a problem to return it in one call).

未设置结构的最大深度.

The maximum depth of the structure is not set.

我已经将结构建模为:

type Tag{
    id: String!
    children: [Tag]
}

当人们想要使标签达到任意深度时,就会出现问题.

The problem appears when one wants to get the tags to an arbitrary depth.

要使所有子级都达到(例如)3级,可以编写如下查询:

To get all the children to (for example) level 3 one would write a query like:

<代码>{标签{ID孩子们 {ID孩子们 {ID}}}}

是否可以编写查询以将所有标签返回到任意深度?

Is there a way to write a query to return all the tags to an arbitrary depth?

如果不是,建议使用哪种方法在GraphQL API中对类似于上述结构的结构进行建模.

If not what is the recommended way to model a structure like the one above in a GraphQL API.

推荐答案

前段时间,我想出了另一种解决方案,它与@WuDo建议的方法相同.

Some time ago I came up with another solution, which is the same approach like @WuDo suggested.

想法是使用ID引用树(每个有其父级的子级)并在ID上平整树,并标记树的根,然后在客户端再次递归地构建树.​​

The idea is to flatten the tree on data level using IDs to reference them (each child with it's parent) and marking the roots of the tree, then on client side build up the tree again recursively.

这样,您不必担心像@samcorcos的答案那样限制查询的深度.

This way you should not worry about limiting the depth of your query like in @samcorcos's answer.

模式:

type Query {
    tags: [Tag]
}

type Tag {
    id: ID!
    children: [ID]
    root: Boolean
}

响应:

{ 
    "tags": [
        {"id": "1", "children": ["2"], "root": true}, 
        {"id": "2", "children": [], "root": false}
    ] 
}

客户端树构建:

import find from 'lodash/find';
import isArray from 'lodash/isArray';

const rootTags = [...tags.map(obj => {...obj)}.filter(tag => tag.root === true)];
const mapChildren = childId => {
    const tag = find(tags, tag => tag.id === childId) || null;

    if (isArray(tag.children) && tag.children.length > 0) {
        tag.children = tag.children.map(mapChildren).filter(tag => tag !== null);
    }
}
const tagTree = rootTags.map(tag => {
    tag.children = tag.children.map(mapChildren).filter(tag => tag !== null);
    return tag;
});

这篇关于如何在GraphQL中建模递归数据结构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆