批量添加不存在的Gremlin顶点:fold/coalesce步骤失效问题
问题
我注入了一个值数组,想要批量添加不存在的顶点。用了fold和coalesce步骤,但批量场景下失效:因为已有一个顶点存在,fold无法得到空值,coalesce里的unfold会返回这个已有顶点,导致其他不存在的顶点没法添加。
当前遍历代码:
const traversal = await g ?.inject([ { twitterPostId: 'kay', like: true, retweet: false }, { twitterPostId: 'fay', like: true, retweet: false }, { twitterPostId: 'nay', like: true, retweet: false }, ]) .unfold() .as('a') .aggregate('ta') .V() .as('b') .where('b', p.eq('a')) .by(__.id()) .by('twitterPostId') .fold() .coalesce(__.unfold(), __.addV().property(t.id, __.select('ta').unfold().select('twitterPostId'))) .toList();
返回结果:
[Bn { id: 'kay', label: 'vertex', properties: undefined }]
解决方案
问题出在你当前的逻辑是把所有待处理对象聚合到ta后,全局查询匹配顶点再fold——只要有一个顶点存在,fold结果就非空,coalesce只会走unfold返回已有顶点,不会处理其他不存在的条目。
正确的做法是对每个待处理对象单独检查是否存在,修正后的代码如下:
const traversal = await g ?.inject([ { twitterPostId: 'kay', like: true, retweet: false }, { twitterPostId: 'fay', like: true, retweet: false }, { twitterPostId: 'nay', like: true, retweet: false }, ]) .unfold() .as('a') // 对每个对象单独查询匹配顶点 .V() .hasId(__.select('a').select('twitterPostId')) .fold() .coalesce( __.unfold(), // 存在则返回已有顶点 // 不存在则添加新顶点并设置所有属性 __.addV() .property(t.id, __.select('a').select('twitterPostId')) .property('like', __.select('a').select('like')) .property('retweet', __.select('a').select('retweet')) ) .toList();
逻辑说明
unfold拆分数组,让每个待处理对象单独走后续流程;- 对每个对象单独执行
V().hasId(...)检查顶点是否存在,再用fold包装结果; coalesce做分支判断:fold结果非空则返回已有顶点,为空则创建新顶点并绑定对应属性;- 每个对象独立处理,不受其他顶点存在状态影响,不存在的顶点都会被正确添加。
内容的提问来源于stack exchange,提问作者Kyano
相关产品推荐
相关产品推荐

