在 GraphQL 中以最佳方式获取数据
Fetching the data optimally in GraphQL
如何编写解析器,以便我可以在每个解析器中生成数据库子查询并有效地组合所有这些查询并一次获取数据?
对于以下架构:
type Node {
index: Int!
color: String!
neighbors(first: Int = null): [Node!]!
}
type Query {
nodes(color: String!): [Node!]!
}
schema {
query: Query
}
执行以下查询:
{
nodes(color: "red") {
index
neighbors(first: 5) {
index
}
}
}
数据存储:
在我的数据存储中,节点和邻居存储在单独的表中。我想编写一个解析器,以便我们可以最佳地获取所需的数据。
If there are any similar examples, please share the details. (It would be helpful to get an answer in reference to graphql-java)
推荐和最常用的方法是使用 data loader
。
A data loader
收集关于从哪个 fields
加载哪个 table
以及要使用哪个 where
过滤器的信息。
我没有在 Java 中使用过 GraphQL,所以我只能给你指导如何自己实现它。
- 创建数据加载器实例并将其作为
context
参数传递给解析器。
- 您的解析器应将
table name
、field names
列表和 where conditions
列表传递给数据加载器和 return 承诺。
- 一旦所有解析器都已执行,您的数据加载器应该合并这些列表,这样您最终每个 table 只需要一个查询。
- 您应该
remove duplicate field
名称和 combine the where conditions
使用 or
关键字。
- 查询执行后,您可以 return 所有这些数据到您的解析器并让他们过滤数据(因为我们使用
or
关键字组合条件)
- 作为一项高级功能,您的数据加载器可以在 return 将数据发送到解析器之前应用 where 条件,这样他们就不必过滤它们。
DataFetchingEnvironment
通过 DataFetchingEnvironment#getSelectionSet
提供对子选择的访问。这意味着,在您的情况下,您可以从 nodes
解析器知道还需要 neighbors
,因此您可以适当地 JOIN
并准备结果。
getSelectionSet
当前实施的一个 限制 是它不提供有关 条件选择 的信息。因此,如果您要处理接口和联合,则必须手动收集从 DataFetchingEnvironment#getField
开始的子选择。这很可能会在 graphql-java.
的未来版本中得到改进
如何编写解析器,以便我可以在每个解析器中生成数据库子查询并有效地组合所有这些查询并一次获取数据?
对于以下架构:
type Node {
index: Int!
color: String!
neighbors(first: Int = null): [Node!]!
}
type Query {
nodes(color: String!): [Node!]!
}
schema {
query: Query
}
执行以下查询:
{
nodes(color: "red") {
index
neighbors(first: 5) {
index
}
}
}
数据存储:
在我的数据存储中,节点和邻居存储在单独的表中。我想编写一个解析器,以便我们可以最佳地获取所需的数据。
If there are any similar examples, please share the details. (It would be helpful to get an answer in reference to graphql-java)
推荐和最常用的方法是使用 data loader
。
A data loader
收集关于从哪个 fields
加载哪个 table
以及要使用哪个 where
过滤器的信息。
我没有在 Java 中使用过 GraphQL,所以我只能给你指导如何自己实现它。
- 创建数据加载器实例并将其作为
context
参数传递给解析器。 - 您的解析器应将
table name
、field names
列表和where conditions
列表传递给数据加载器和 return 承诺。 - 一旦所有解析器都已执行,您的数据加载器应该合并这些列表,这样您最终每个 table 只需要一个查询。
- 您应该
remove duplicate field
名称和combine the where conditions
使用or
关键字。 - 查询执行后,您可以 return 所有这些数据到您的解析器并让他们过滤数据(因为我们使用
or
关键字组合条件) - 作为一项高级功能,您的数据加载器可以在 return 将数据发送到解析器之前应用 where 条件,这样他们就不必过滤它们。
DataFetchingEnvironment
通过 DataFetchingEnvironment#getSelectionSet
提供对子选择的访问。这意味着,在您的情况下,您可以从 nodes
解析器知道还需要 neighbors
,因此您可以适当地 JOIN
并准备结果。
getSelectionSet
当前实施的一个 限制 是它不提供有关 条件选择 的信息。因此,如果您要处理接口和联合,则必须手动收集从 DataFetchingEnvironment#getField
开始的子选择。这很可能会在 graphql-java.