mirror of
https://github.com/hanzoai/next.js.git
synced 2026-09-24 17:00:51 +00:00
## Summary Add `bash filename="Terminal"` to improve readability. ### Improving Documentation - [x] Run `pnpm prettier-fix` to fix formatting issues before opening the PR. - [x] Read the Docs Contribution Guide to ensure your contribution follows the docs guidelines: https://nextjs.org/docs/community/contribution-guide Co-authored-by: Delba de Oliveira <[email protected]>
96 lines
3.7 KiB
Plaintext
96 lines
3.7 KiB
Plaintext
---
|
|
title: Dynamic APIs are Asynchronous
|
|
description: Learn more about why accessing certain APIs synchronously now warns.
|
|
---
|
|
|
|
## Why This Warning Occurred
|
|
|
|
Somewhere in your code you used an API that opts into [dynamic rendering](/docs/app/building-your-application/rendering/server-components#dynamic-apis).
|
|
|
|
Dynamic APIs are:
|
|
|
|
- The `params` and `searchParams` props that get provided to pages, layouts, metadata APIs, and route handlers.
|
|
- `cookies()`, `draftMode()`, and `headers()` from `next/headers`
|
|
|
|
In Next 15, these APIs have been made asynchronous. You can read more about this in the Next.js 15 [Upgrade Guide](/docs/app/building-your-application/upgrading/version-15).
|
|
|
|
For example, the following code will issue a warning:
|
|
|
|
```js filename="app/[id]/page.js"
|
|
function Page({ params }) {
|
|
// direct access of `params.id`.
|
|
return <p>ID: {params.id}</p>
|
|
}
|
|
```
|
|
|
|
This also includes enumerating (e.g. `{...params}`, or `Object.keys(params)`) or iterating over the return
|
|
value of these APIs (e.g. `[...headers()]` or `for (const cookie of cookies())`, or explicitly with `cookies()[Symbol.iterator]()`).
|
|
|
|
In the version of Next.js that issued this warning, access to these properties is still possible directly but will warn.
|
|
In future versions, these APIs will be async and direct access will not work as expected.
|
|
|
|
## Possible Ways to Fix It
|
|
|
|
The [`next-async-request-api` codemod](/docs/app/building-your-application/upgrading/codemods#next-async-request-api) can fix many of these cases automatically:
|
|
|
|
```bash filename="Terminal"
|
|
$ npx @next/codemod@canary next-async-request-api .
|
|
```
|
|
|
|
The codemod cannot cover all cases, so you may need to manually adjust some code.
|
|
|
|
If the warning occured on the Server (e.g. a route handler, or a Server Component),
|
|
you must `await` the dynamic API to access its properties:
|
|
|
|
```js filename="app/[id]/page.js"
|
|
async function Page({ params }) {
|
|
// asynchronous access of `params.id`.
|
|
const { id } = await params
|
|
return <p>ID: {id}</p>
|
|
}
|
|
```
|
|
|
|
If the warning occured in a synchronous component (e.g. a Client component),
|
|
you must use `React.use()` to unwrap the Promise first:
|
|
|
|
```js filename="app/[id]/page.js"
|
|
'use client'
|
|
import * as React from 'react'
|
|
|
|
function Page({ params }) {
|
|
// asynchronous access of `params.id`.
|
|
const { id } = React.use(params)
|
|
return <p>ID: {id}</p>
|
|
}
|
|
```
|
|
|
|
### Unmigratable Cases
|
|
|
|
If Next.js codemod found anything that is not able to be migrated by the codemod, it will leave a comment with `@next-codemod-error` prefix and the suggested action, for example:
|
|
In this case, you need to manually await the call to `cookies()`, and change the function to async. Then refactor the usages of the function to be properly awaited:
|
|
|
|
```ts
|
|
export function MyCookiesComponent() {
|
|
const c =
|
|
/* @next-codemod-error Manually await this call and refactor the function to be async */
|
|
cookies()
|
|
return c.get('name')
|
|
}
|
|
```
|
|
|
|
### Enforced Migration with Linter
|
|
|
|
If you didn't address the comments that starting with `@next-codemod-error` left by the codemod, Next.js will error in both dev and build to enforce you to address the issues.
|
|
You can review the changes and follow the suggestion in the comments. You can either make the necessary changes and remove the comment, or replace the comment prefix `@next-codemod-error` with `@next-codemod-ignore`
|
|
If there's no action to be taken, the comment prefix `@next-codemod-ignore` will bypass the build error.
|
|
|
|
```diff
|
|
- /* @next-codemod-error <suggested message> */
|
|
+ /* @next-codemod-ignore */
|
|
```
|
|
|
|
> **Good to know**:
|
|
>
|
|
> You can delay unwrapping the Promise (either with `await` or `React.use`) until you actually need to consume the value.
|
|
> This will allow Next.js to statically render more of your page.
|