首页 > 解决方案 > 如何将 _app.js 中获取的数据传递给组件

问题描述

在我的 nextjs 项目中,我有需要 api 调用的 Layout 组件。我不想在每个页面(./pages/*)中调用 api 调用,而是将逻辑放在一些全局空间中。我进行了一些研究,看起来覆盖 _app.js 是 nextjs 文档(https://nextjs.org/docs/advanced-features/custom-app)中指示的方式。

我已经列出了如下代码。但这似乎不起作用。

./pages/_app.js

function MyApp({ Component, appProps, results }) {

  return (
    <Layout {...results}>
      <Component {...appProps} />
    </Layout>
  )
}

MyApp.getInitialProps = async (appContext) => {
  const appProps = await App.getInitialProps(appContext)
  const results = await getResults()  //api call

  return { appProps, results }
}

./components/Layout.js

const Layout = ({ children, results }) => {

  return (
    <React.Fragment>
      <Header/>
      <div className='row col-md-8 offset-md-2'>
        {JSON.stringify(results)} //results is nothing here
        <div className='col-md-9'>
          {children}
        </div>
      </div>
    </React.Fragment>
  )
}

./pages/index.js

...
return (
    <>
      {head()}
      <Layout>
        <div className='row col-md-12'>
          {showContents()}
        </div>
      </Layout>
    </>
  )

我确定我遗漏了一些明显的东西。任何帮助,将不胜感激。

标签: javascriptreactjsnext.js

解决方案


除非您打算让该页面每次都返回类似的结果,否则您应该在客户端迁移您的 api 调用。Next.JS 已经从 getInitialProps 转移到了 getStaticProps(获取静态数据)、getStaticPaths(预渲染一组静态页面)和 getServerSideProps(这可能最接近 getInitialProps,在服务器端获取数据)。在此处获取有关 next.js 数据的更多信息:https ://nextjs.org/docs/basic-features/data-fetching

现在根据您提供的代码回答您的问题

// index.js
<Layout> <- you're not passing any props here.

它应该像这样支撑结果:

// index.js
function Page({ results }){
  return <Layout results={results}>Hello</Layout>
}

使用客户端示例,您可以执行以下操作

import { useState } from 'react'

function useCats(){
  const [cats, setCats] = useState()
  useEffect(() => {
    fetch('https://test.api/cats')
      .then(response => response.json())
      .then(_cats => setCats(_cats));
  }, [])

  return cats
}

// then in another component

function CatsList(){
  const cats = useCats();
  if(!cats){
    return <p>Loading</p>
  }

  return <div>
    {cats.map(cat => <p key={cat.id}>Cat: {cat.name}</p>)}
  </div>
}


推荐阅读