如何为Gatsby提供GraphQL架构

Ash*_*ury 13 javascript reactjs graphql gatsby

我们从Wordpress后端引入一些帖子,有些有图片(在ACF字段中),有些则没有.问题是盖茨比根据它收到的第一个节点推断出架构.如果它收到没有图片的节点,那么架构是错误的.

Gatsby的GraphQL架构来自哪里? 使用Gatsby,我们使用从不同来源获取数据的插件.然后,我们使用该数据自动推断GraphQL架构.

我们怎样才能为GraphQL/Gatsby指定一个总是包含图片的模式,如果它是空白的话,将'null'作为默认值?

{
  allWordpressWpTestimonial {
    edges {
      node {
        id
        title
        acf {
          photo_fields {
            photo {
              id
              localFile {
                childImageSharp {
                  sizes {
                    src
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}
Run Code Online (Sandbox Code Playgroud)

在上面的例子中,有时候"照片"不存在,它会破坏一切......

盖茨比配置:

const innertext = require('innertext')
const url = require('url')

module.exports = {
  siteMetadata: {
    title: 'Test',
    googleMapsAPIKey: 'xxxxxx',
    adminBaseUrl: '123.123.123',
    adminProtocol: 'http',
  },
  pathPrefix: '/web/beta',
  plugins: [
    'gatsby-plugin-react-next',
    'gatsby-plugin-react-helmet',
    'gatsby-plugin-sharp',
    'gatsby-plugin-svgr',
    {
      resolve: 'gatsby-plugin-google-analytics',
      options: {
        trackingId: 'GOOGLE_ANALYTICS_TRACKING_ID',
      },
    },
    {
      resolve: 'gatsby-plugin-bugherd',
      options: {
        key: 'xxxxxx',
        showInProduction: true,
      },
    },
    {
      resolve: '@andrew-codes/gatsby-plugin-elasticlunr-search',
      options: {
        fields: ['title', 'url', 'textContent', 'urlSearchable'],
        resolvers: {
          wordpress__PAGE: {
            title: node => node.title,
            textContent: node => innertext(node.content),
            url: node => url.parse(node.link).path,
            urlSearchable: node =>
              url
                .parse(node.link)
                .path.split('/')
                .join(' '),
          },
          wordpress__POST: {
            title: node => node.title,
            textContent: node => innertext(node.content),
            url: node => `/news/${node.slug}`,
            urlSearchable: node =>
              url
                .parse(node.link)
                .path.split('/')
                .join(' '),
          },
          wordpress__wp_industry: {
            title: node => node.title,
            textContent: node => innertext(node.content),
            url: node => `/business/industries/${node.slug}`,
            urlSearchable: node =>
              url
                .parse(node.link)
                .path.split('/')
                .join(' '),
          },
        },
      },
    },
    {
      resolve: 'gatsby-source-wordpress',
      options: {
        baseUrl: 'xxxxxx',
        protocol: 'http',
        hostingWPCOM: false,
        useACF: true,
        auth: {
          htaccess_user: 'admin',
          htaccess_pass: 'xxxxxx',
          htaccess_sendImmediately: false,
        },
        verboseOutput: false,
      },
    },
    'gatsby-transformer-sharp',
  ],
}
Run Code Online (Sandbox Code Playgroud)

Der*_*yen 8

自从这篇文章以来已经有一段时间了,但是自从2.2版Gatsby以来,添加了一个新的API,它将使自定义架构更加容易。这不是wordpress的示例,而是gatsby的示例gatsby-transformer-remark,但我确定它是适用的。

我有一堆.md与frontmatter看起来像这样:

---
title: "Screen title"
image: "./hero-image.png"  <--- sometimes it's an empty string, ""
category: "Cat"
---

...content...
Run Code Online (Sandbox Code Playgroud)

如果Gatsby .md首先使用空白图片进入,则String即使该字段应为,它也会错误地将该字段推断为File。使用新的API,我可以通过以下方式向Gatsby谈谈图像字段gatsby-node.js

exports.sourceNodes = ({ actions, schema }) => {
  const { createTypes } = actions
  createTypes(`
    type MarkdownRemarkFrontmatter {
      image: File
    }

    type MarkdownRemark implements Node {
      frontmatter: MarkdownRemarkFrontmatter
    }
  `)
}
Run Code Online (Sandbox Code Playgroud)

这样可以确保该image字段始终为File类型,否则为null

一些注意事项:

  • 像这样的根节点MarkdownRemark必须实现Node
  • 一个节点可以实现多个接口
  • 您必须“努力”到相关领域。在此示例中,我必须声明MarkdownRemarkFrontmatter类型,然后将其传递给node中的frontmatter字段MarkdownRemark
  • 如果未指定,盖茨比将推断其余字段。在上面的示例中,由于我没有在中指定category字段MarkdownRemarkFrontmatter,因此Gatsby会像以前一样推断出该字段。
  • 找到这些类型的(最有用的方法MarkdownRemarkMarkdownRemarkFrontmatter)是看他们在graphiql(在默认情况下localhost:8000/___graphql