0

如果仅传递“第一个”参数,graphql 如何生成 hasNextPage?我在用

return relay.connectionFromPromisedArray( global.app.get('model__user').getUsers(args), args );

和查询:

query RootQueryType { viewer { user(id: 1){ id,email,friends(first: 5) {edges {cursor, node { id, email } }, pageInfo { hasNextPage } } } } }

那么我怎样才能传递给 graphql / 中继好友计数,以便正确生成 hasNextPage?

4

2 回答 2

1

您可以在此处找到有关中继分页算法的详细信息:https ://facebook.github.io/relay/graphql/connections.htm#sec-Pagination-algorithm 。

要回答您关于 hasNextPage 的具体问题,算法如下:

function hasNextPage(allEdges, before, after, first, last) {

    // If first was not set, return false.
    if (first === null) { return false; }

    // Apply the before & after cursor arguments to the set of edges.
    // i.e. edges is the set of edges between the before and after cursors
    const edges = ApplyCursorsToEdges(allEdges, before, after)

    // If more edges exist between the before & after cursors than
    // you are asking for then there is a next page.
    if (edges.length > first) { return true; }
    return false
}

关于光标与基于页面的分页的快速说明。使用固定页面大小进行分页通常是个坏主意。一个典型的例子是在 SQL 中使用 OFFSET 关键字来抓取下一页。这种方法有很多问题。例如,如果在对集合进行分页时插入了一个新对象,会发生什么情况?如果新对象是在您当前抓取的页面之前插入的,并且您使用固定偏移量,您将抓取一个您已经抓取的对象,这会导致表示层中的数据重复。使用游标进行分页通过允许您跟踪对象本身而不是对象的计数来解决此问题。

曾经是最后一件事,特别是中继分页。我建议在任何给定时间只使用 (first & after) OR (last & before)。在同一个查询中同时使用两者可能会导致合乎逻辑但出乎意料的结果。

祝你好运!

于 2016-06-28T20:17:53.553 回答
1

中继分页不是基于页面,而是cursor基于。因此,您通过说“我想要 Y 项之后的 X 项”来进行分页。项目 Y 不是作为页码或偏移量指向,而是作为指向该确切对象的指针,即所谓的光标。这种分页模型非常适合,例如无限滚动。“页面”在添加或删除项目后也很稳定,因为它们不依赖于项目的数量。

hasNextPage在 Relay GraphQL 规范中,仅指示在检索到的最后一个元素之后是否还有更多项目。所以在你的情况下,这意味着总共有超过 5 个元素,如果你这样做,你会得到更多的元素

friends(first: 5, after: "CURSOR_TO_THE_LAST_ELEMENT")

您可以从edges列表中检索光标,它是旁边的元素之一node

于 2016-04-06T09:00:58.090 回答