如何使用gqlgen为GraphQL内部嵌套节点生成过滤用resolver
gqlgen嵌套节点resolver实现过滤的步骤
1. 调整Schema定义,为嵌套字段添加过滤参数
首先修改你的GraphQL schema,给需要过滤的嵌套字段新增对应的参数,示例如下:
type Region { id: ID! name: String! # 新增schoolId参数用于筛选学校,可按需扩展为多条件过滤的Input类型 schools(schoolId: ID): [School!]! } type School { id: ID! name: String! # 新增classId参数用于筛选班级 classes(classId: ID): [Class!]! } type Query { regions(id : ID!): [Region!]! }
如果需要支持多条件过滤,你可以自定义input类型替代单个ID参数,使用更灵活。
2. 修改gqlgen配置,指定嵌套字段需要生成resolver
默认gqlgen只会为顶层的Query、Mutation生成resolver,嵌套字段如果匹配到Go模型的属性会直接自动映射返回。你需要修改项目下的gqlgen.yml配置,标记需要自定义resolver的嵌套字段:
models: Region: fields: schools: resolver: true School: fields: classes: resolver: true
配置完成后执行go run github.com/99designs/gqlgen generate命令,gqlgen会自动在resolver文件中生成两个嵌套字段对应的resolver方法骨架。
3. 实现自定义resolver逻辑
在自动生成的resolver方法中编写过滤逻辑,入参中可以拿到父级节点的实例,结合传入的过滤参数做筛选即可,示例代码:
// Region下schools字段的resolver func (r *regionResolver) Schools(ctx context.Context, obj *model.Region, schoolId *string) ([]*model.School, error) { // obj为当前父级Region的实例,可获取Region的id等属性查询关联的学校数据 allSchools := 查询当前Region关联的所有学校的逻辑 if schoolId == nil { return allSchools, nil } // 按传入的schoolId过滤 var filteredSchools []*model.School for _, school := range allSchools { if school.ID == *schoolId { filteredSchools = append(filteredSchools, school) } } return filteredSchools, nil } // School下classes字段的resolver func (r *schoolResolver) Classes(ctx context.Context, obj *model.School, classId *string) ([]*model.Class, error) { // obj为当前父级School的实例 allClasses := 查询当前School关联的所有班级的逻辑 if classId == nil { return allClasses, nil } // 按传入的classId过滤 var filteredClasses []*model.Class for _, class := range allClasses { if class.ID == *classId { filteredClasses = append(filteredClasses, class) } } return filteredClasses, nil }
4. 同时过滤Schools和Classes的查询示例
完成上述配置后,就可以在单次查询中同时传入两个层级的过滤参数:
query getFilteredRegionData($regionId: ID!, $schoolFilterId: ID!, $classFilterId: ID!) { regions(id: $regionId) { id name schools(schoolId: $schoolFilterId) { id name classes(classId: $classFilterId) { id # 其他需要返回的班级字段 } } } }
内容的提问来源于stack exchange,提问作者Forkmohit
相关产品推荐
相关产品推荐

