在功能组件之前添加异步会导致它 return 一个对象?

Adding async before functional component causes it to return an object?

我有一个 App 组件和 BookList 组件,它们在 App 中呈现。当我将异步添加到我的 BookList 组件时,出现以下错误:

Error: Objects are not valid as a React child (found: [object Promise]). If you meant to render a collection of children, use an array instead.
    in BookList (at App.js:18)
    in div (at App.js:16)
    in ApolloProvider (at App.js:15)
    in App (at src/index.js:16)
    in StrictMode (at src/index.js:14) 

应用程序:

import React from 'react';
import styled from 'styled-components';
import BookList from './components/BookList';
import ApolloClient from 'apollo-boost';
import { ApolloProvider } from '@apollo/react-hooks';

export const client = new ApolloClient({
  uri: 'http://localhost:4001/graphql',
})

const App = () => {
  return (
    <ApolloProvider client={client}>
      <div id='main'>
        <h1>Javed's Reading List</h1>
        <BookList />
      </div>
    </ApolloProvider>
  );
}

export default App;

图书清单:

const BookList = async () => {

  const query = gql`
    query {
      books {
        name
        id
      }
    }
  `;

  const { data } = await client.query({ query })
  return (
    <div id='main'>
      <ul id='book-list'>
        <li>Book Name</li>
      </ul>
    </div>
  );
};

export default BookList;

我知道添加异步会导致 return 值成为一个承诺,但我过去这样做没有任何问题。我不确定我错过了什么。为什么我无法呈现 BookList?

编辑:

我听从了@MorKadosh 的建议,页面加载时 useEffect 挂钩没有触发

const BookList = () => {
  const [data, setData] = useState(null)

  useEffect(() => {
    const fetch = async () => {
      const response = await client.query({ query });
      console.log(response.data);
      console.log('hello')
      setData(response.data);
    }
    fetch();
  }, [])

  return (
    <div id='main'>
      <ul id='book-list'>
        <li>Book Name</li>
      </ul>
    </div>
  );
};

export default BookList;

你不应该那样做。 相反,使用 useEffectuseState 钩子来获取数据:

  const [data, setData] = useState(null);

  useEffect(() => {
    const query = ...
    const fetch = async () => {
       const response = await client.query({ query });
       setData(response.data);
    };
    fetch();
  }, []);

这只是示例,请根据自己的需要进行调整。

为什么你不应该那样做?因为正如您所说的那样,使用 async 将始终 return 一个 Promise,这不是有效的反应组件。

我认为 promise 与 React 界面不匹配

为什么不将 API 调用包装在异步函数中或使用 useEffect 挂钩?

const apiCall = async () => await client.query(...)