Gatsby+GraphQL下过滤WordPress ACF Post Object字段的方案咨询
你之前关于Gatsby查询逻辑的结论是正确的,gatsby-source-wordpress插件会在构建阶段全量拉取WordPress节点存储到本地缓存,所有Gatsby侧的GraphQL查询都基于本地缓存执行,不会调用远程WPGraphQL接口,因此WPGraphQL端注册的自定义查询参数不会生效。以下是可落地的实现方案:
方案1:自定义Gatsby Schema启用关联字段过滤
通过gatsby-node.js的createSchemaCustomization API显式声明过滤规则,就能让genericPage出现在GraphiQL的过滤选项里:
exports.createSchemaCustomization = ({ actions }) => { const { createTypes } = actions const typeDefs = ` type WpPage implements Node { pagesGeo: WpPagePagesGeo } type WpPagePagesGeo { genericPage: WpPage @filterable } ` createTypes(typeDefs) }
配置后重启开发服务,就可以用如下查询实现多ID匹配,对应你WordPress端的OR查询逻辑:
query Test { allWpPage(filter: {pagesGeo: {genericPage: {id: {in: ["目标ID1", "目标ID2"]}}}}) { edges { node { pagesGeo { genericPage { ... on WpPage { id } } hreflangValue } } } } }
方案2:全量查询后手动过滤(适合小数据量场景)
如果你的页面总数不多,不需要改Schema,直接全量查询后在业务代码里过滤即可:
const result = await graphql(` query Test { allWpPage { edges { node { id pagesGeo { genericPage { ... on WpPage { id } } hreflangValue } } } } } `) const targetIds = ["要匹配的ID1", "要匹配的ID2"] const filteredPages = result.data.allWpPage.edges.filter(edge => { const genericPageId = edge.node.pagesGeo?.genericPage?.id return genericPageId && targetIds.includes(genericPageId) })
方案3:WordPress端暴露标量ID字段(最稳定方案)
因为关联对象的过滤规则可能受插件版本影响,最稳妥的方式是在WordPress端把generic_page存储的关联ID作为独立的元字段暴露给WPGraphQL,Gatsby拉取到这个数字类型的标量值后,默认就支持所有过滤操作,不需要额外配置Schema。
你可以在WordPress主题的functions.php里添加如下代码暴露字段:
add_action('graphql_register_types', function() { register_graphql_field('Page', 'genericPageId', [ 'type' => 'Int', 'description' => 'ACF generic_page字段存储的关联文章ID', 'resolve' => function($post) { return get_field('generic_page', $post->ID, false); // 第三个参数false直接返回原始存储的ID值 } ]); });
配置后重新同步Gatsby的WordPress数据,就可以直接用genericPageId字段过滤:
query Test { allWpPage(filter: {genericPageId: {in: [目标ID1, 目标ID2]}}) { edges { node { # 你需要的字段 } } } }
内容的提问来源于stack exchange,提问作者Borje
相关产品推荐
相关产品推荐

