rsnext/docs/basic-features/data-fetching.md
2020-01-11 21:53:58 -05:00

97 lines
3.4 KiB
Markdown

---
description: Next.js can handle data fetching in multiple ways for server-rendered and static pages. Learn how it works here.
---
# Data fetching
Next.js has 2 pre-rendering modes built-in:
- [Static Generation](#static-generation)
- [Server-side rendering](#server-side-rendering)
You can learn more about the differences in the [pages section](/docs/basic-features/pages.md#pre-rendering).
These rendering modes are tightly coupled to the way that you do data fetching.
In Next.js data fetching generally happens at the page level. There are multiple reasons for this:
- Avoid data fetching waterfalls, having to render then wait then render etc.
- When pre-rendering React needs to have all data available before rendering.
## Static Generation
By default Next.js pages that don't use [`getInitialProps`](/docs/api-reference/data-fetching/getInitialProps.md) get rendered to static HTML at `next build` time.
This is useful for, as an example, dashboards that have a lot of dynamic data that depends on a specific user.
You might not want to server-render that content but instead load the data client-side.
For this particular use case [ZEIT](https://zeit.co) has created a data-fetching library called [SWR](https://github.com/zeit/swr).
```jsx
// This page doesn't define `getInitialProps`.
// Next.js will export the page to HTML at build time with the loading state
// When the page is loaded in the browser SWR will fetch the data
// Using the defined fetcher function
import fetch from 'unfetch'
import useSWR from 'swr'
const API_URL = 'https://api.github.com'
async function fetcher(path) {
const res = await fetch(API_URL + path)
const json = await res.json()
return json
}
function HomePage() {
const { data, error } = useSWR('/repos/zeit/next.js', fetcher)
if (error) return <div>failed to load</div>
if (!data) return <div>loading...</div>
return <div>Next stars: {data.stargazers_count}</div>
}
export default HomePage
```
## Server-side rendering
Pages might have to wait on some data before pre-rendering, for example, if you want the page to be indexed with the data by search engines.
Next.js comes with [`getInitialProps`](/docs/api-reference/data-fetching/getInitialProps.md), which is an [`async`](https://zeit.co/blog/async-and-await) function that can be added to any page as a [`static method`](https://javascript.info/static-properties-methods).
`getInitialProps` allows the page to wait for data before rendering starts.
Using `getInitialProps` will make the page opt-in to on-demand [server-side rendering](/docs/basic-features/pages.md#server-side-rendering).
```jsx
// This page has defined `getInitialProps` to do data fetching.
// Next.js will execute `getInitialProps`
// It will wait for the result of `getInitialProps`
// When the results comes back Next.js will render the page.
// Next.js will do this for every request that comes in.
import fetch from 'isomorphic-unfetch'
function HomePage({ stars }) {
return <div>Next stars: {stars}</div>
}
HomePage.getInitialProps = async () => {
const res = await fetch('https://api.github.com/repos/zeit/next.js')
const json = await res.json()
return { stars: json.stargazers_count }
}
export default HomePage
```
## Related
For more information on what to do next, we recommend the following sections:
<div class="card">
<a href="/docs/api-reference/data-fetching/getInitialProps.md">
<b>getInitialProps:</b>
<small>Learn more about the API for `getInitialProps`.</small>
</a>
</div>