GatsbyJS从Restful API获取数据

时间:2018-03-15 12:18:34

标签: gatsby

我是React和GatsbyJS的新手。我很困惑,无法以一种简单的方式从第三方Restful API加载数据。

例如:我想从randomuser.me/API获取数据,然后能够使用页面中的数据。

我们这样说:

  import React from 'react'
  import Link from 'gatsby-link'

  class User extends React.Component {
    constructor(){
      super();
      this.state = {
        pictures:[],
      };

    }

    componentDidMount(){
      fetch('https://randomuser.me/api/?results=500')
      .then(results=>{
        return results.json();
      })
      .then(data=>{
        let pictures = data.results.map((pic,i)=>{
            return(
              <div key={i} >
                <img key={i} src={pic.picture.medium}/>
              </div>
            )
        })
        this.setState({pictures:pictures})
      })
    }

    render() {
      return (<div>{this.state.pictures}</div>)
    }
  }

  export default User;

但是我想得到GraphQL的帮助以便过滤&amp;排序用户等...... ..

您能否帮我找一些示例,了解如何获取数据并将其插入gatsby-node.js

中的GraphQL

5 个答案:

答案 0 :(得分:46)

如果要使用GraphQL获取数据,则必须创建sourceNode。关于creating a source plugin的文档可以帮助您。

按照以下步骤,您可以在Gatsby项目中使用graphQL查询随机用户数据。

1)在gatsby-node.js

中创建节点

在根项目文件夹中,将此代码添加到gatsby-node.js

const axios = require('axios');
const crypto = require('crypto');

exports.sourceNodes = async ({ boundActionCreators }) => {
  const { createNode } = boundActionCreators;

  // fetch raw data from the randomuser api
  const fetchRandomUser = () => axios.get(`https://randomuser.me/api/?results=500`);
  // await for results
  const res = await fetchRandomUser();

  // map into these results and create nodes
  res.data.results.map((user, i) => {
    // Create your node object
    const userNode = {
      // Required fields
      id: `${i}`,
      parent: `__SOURCE__`,
      internal: {
        type: `RandomUser`, // name of the graphQL query --> allRandomUser {}
        // contentDigest will be added just after
        // but it is required
      },
      children: [],

      // Other fields that you want to query with graphQl
      gender: user.gender,
      name: {
        title: user.name.title,
        first: user.name.first,
        last: user.name.last,
      },
      picture: {
        large: user.picture.large,
        medium: user.picture.medium,
        thumbnail: user.picture.thumbnail,
      }
      // etc...
    }

    // Get content digest of node. (Required field)
    const contentDigest = crypto
      .createHash(`md5`)
      .update(JSON.stringify(userNode))
      .digest(`hex`);
    // add it to userNode
    userNode.internal.contentDigest = contentDigest;

    // Create node with the gatsby createNode() API
    createNode(userNode);
  });

  return;
}
  

我使用axios来获取数据,因此您需要安装它:npm install --save axios

解释

目标是为您想要使用的每个数据创建每个节点。 根据{{​​3}},您必须提供一个包含少量必填字段的对象(id,parent,internal,children)。

从randomuser API获取结果数据后,您只需创建此节点对象并将其传递给createNode()函数。

我们在此处映射到您希望获得500个随机用户https://randomuser.me/api/?results=500的结果。

使用必填字段和所需字段创建userNode对象。 您可以根据要在应用中使用的数据添加更多字段。

只需使用Gatsby API的createNode()功能创建节点。

2)使用GraphiQL

查询您的数据

完成后,请运行gatsby develop并转到createNode documentation

您可以使用graphiQL来创建完美的查询。当我们命名节点对象internal.type的{​​{1}}时,我们可以查询'RandomUser'来获取我们的数据。

allRandomUser

3)在您的gatsby页面中使用此查询

在您的页面中,例如{ allRandomUser { edges { node { gender name { title first last } picture { large medium thumbnail } } } } } ,使用查询并显示您的数据:

src/pages/index.js

就是这样!

答案 1 :(得分:4)

非常感谢,这对我来说很好,我只更改gastbyjs-node.js的一小部分,因为它在使用sync&amp; amp时会出错。等待,我想我需要更改构建过程的某些部分以使用babel来允许我使用sync或await。

这是适合我的代码。

 const axios = require('axios');
 const crypto = require('crypto');

 // exports.sourceNodes = async ({ boundActionCreators }) => {
 exports.sourceNodes = ({boundActionCreators}) => {
const {createNode} = boundActionCreators;
return new Promise((resolve, reject) => {

// fetch raw data from the randomuser api
// const fetchRandomUser = () => axios.get(`https://randomuser.me/api/?results=500`);
// await for results
// const res = await fetchRandomUser();

axios.get(`https://randomuser.me/api/?results=500`).then(res => {

  // map into these results and create nodes
  res.data.results.map((user, i) => {

    // Create your node object
    const userNode = {
      // Required fields
      id: `${i}`,
      parent: `__SOURCE__`,
      internal: {
        type: `RandomUser`, // name of the graphQL query --> allRandomUser {}
        // contentDigest will be added just after
        // but it is required
      },
      children: [],

      // Other fields that you want to query with graphQl
      gender: user.gender,
      name: {
        title: user.name.title,
        first: user.name.first,
        last: user.name.last
      },
      picture: {
        large: user.picture.large,
        medium: user.picture.medium,
        thumbnail: user.picture.thumbnail
      }
      // etc...
    }

    // Get content digest of node. (Required field)
    const contentDigest = crypto.createHash(`md5`).update(JSON.stringify(userNode)).digest(`hex`);
    // add it to userNode
    userNode.internal.contentDigest = contentDigest;

    // Create node with the gatsby createNode() API
    createNode(userNode);
  });
  resolve();
});

});

}

答案 2 :(得分:1)

以上给出的答案有效,除了步骤2中的查询似乎只为我返回一个节点。我可以通过将totalCount作为边的同级添加来返回所有节点。即

{ allRandomUser { totalCount edges { node { id gender name { first last } } } } }

答案 3 :(得分:1)

可接受的答案非常有用,只是要注意,如果您使用boundActionCreators,则会有弃用警告。为了避免出现此警告,必须将其重命名为actions

答案 4 :(得分:1)

您可以使用 react useEffect 在前端从 API 获取数据。它运行良好,您将不再在 buildime 中看到任何错误

 const [starsCount, setStarsCount] = useState(0)
  useEffect(() => {
    // get data from GitHub api
    fetch(`https://api.github.com/repos/gatsbyjs/gatsby`)
      .then(response => response.json()) // parse JSON from request
      .then(resultData => {
        setStarsCount(resultData.stargazers_count)
      }) // set data for the number of stars
  }, [])