Re-do of https://github.com/vercel/next.js/pull/40251
Edge SSR'd routes cold boot performances are proportional to the
executed code size.
In order to improve it, we are trying to optimize for the bundle size of
a packed Edge SSR route.
This PR adds ESM compilation targets for all Next.js dist packages and
use them to bundle Edge SSR'd route.
This allows us to leverage the better tree shaking/DCE for ESM modules
in webpack in order to decrease the overall bundle size.
This PR also enables minifying Edge SSR routes. Since we don't control
which minifier might be used later (if any), it's best if we provide an
already optimised bundle.
<img width="903" alt="image"
src="https://user-images.githubusercontent.com/11064311/190005211-b7cb2c58-a56a-44b0-8ee4-fd3f603e41bd.png">
This is a 10ms cold boot win per my benchmarking script, which I'll put
in a subsequent PR.
Not done yet:
- ~~swap exported requires in `next/link` (and others) etc to point them
to the esm modules version~~
<!--
Thanks for opening a PR! Your contribution is much appreciated. In order
to make sure your PR is handled as smoothly as possible we request that
you follow the checklist sections below. Choose the right checklist for
the change that you're making: -->
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have helpful link attached, see `contributing.md`
- [x] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have helpful link attached, see `contributing.md`
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The examples guidelines are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing.md#adding-examples)
Co-authored-by: JJ Kasper <jj@jjsweb.site>
Co-authored-by: Shu Ding <g@shud.in>
<!--
Thanks for opening a PR! Your contribution is much appreciated.
To make sure your PR is handled as smoothly as possible we request that
you follow the checklist sections below.
Choose the right checklist for the change that you're making:
-->
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Co-authored-by: JJ Kasper <jj@jjsweb.site>
Co-authored-by: Shu Ding <g@shud.in>
This seems to be the cause for the failure of https://github.com/vercel/next.js/actions/runs/3133433920/jobs/5087331787 that caused[ the revert](https://github.com/vercel/next.js/pull/40967) of my [commit ](11deaaa82b) that changed the edge bundle to SSR.
After investigating, I realised this was the culprit: this forces the test app code to run with this on, somehow, when built on Vercel.
Removing it should fix it. Let's merge if all tests still pass?
Open questions:
- I'm not sure why this is/was needed, since this variable should always be inlined by webpack
- furthermore, this was causing client code to run as-if on the edge?
- but also, this still shouldn't happen because webpack should get rid of it
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the feature request has been accepted for implementation before opening a PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
When fetching the middleware rewrite information via `_next/data` for a static page that is not a `fallback` we can use a `HEAD` request instead of a `GET` request which provides the necessary header information and saves some bandwidth by avoiding sending back the data that is already present in the page.
x-ref: [slack thread](https://vercel.slack.com/archives/C03S8ED1DKM/p1664229966495469)
## Bug
- [x] Related issues linked using `fixes #number`
- [x] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
This reverts commit 11deaaa82b.
Temporarily reverts the above commit due to breaking middleware/edge
functions once deployed.
Fixes:
https://github.com/vercel/next.js/actions/runs/3133433920/jobs/5087331787
cc @shuding @feedthejim
```sh
[GET] /blog/first
13:56:56:61
2022-09-27T20:56:56.671Z 61d43a6a-34a1-40c0-b71f-4ae5d1918431 ERROR /var/task/node_modules/next/dist/esm/client/router.js:1
/* global window */ import React from 'react';
^^^^^^
SyntaxError: Cannot use import statement outside a module
at Object.compileFunction (node:vm:352:18)
at wrapSafe (node:internal/modules/cjs/loader:1033:15)
at Module._compile (node:internal/modules/cjs/loader:1069:27)
at Object.Module._extensions..js (node:internal/modules/cjs/loader:1159:10)
at Module.load (node:internal/modules/cjs/loader:981:32)
at Function.Module._load (node:internal/modules/cjs/loader:822:12)
at Module.require (node:internal/modules/cjs/loader:1005:19)
at require (node:internal/modules/cjs/helpers:102:18)
at Object.<anonymous> (/var/task/node_modules/next/router.js:3:7)
at Module._compile (node:internal/modules/cjs/loader:1105:14)
```
This PR adds a new `experimental.enableUndici` option to let the
developer switch from `next-fetch` to `undici` as the underlying
polyfill for `fetch` in Node.js.
In the current implementation, Next.js makes sure that `fetch` is always
available by using `node-fetch`. However, we do not polyfill in Node.js
18+, since those versions come with their own `fetch` implementation
already, built-in.
Node.js 18+ uses `undici` under the hood, so letting the developer use
`undici` earlier could make the migration easier later on.
Eventually, we hope to be able to stop polyfilling `fetch` in an
upcoming major version of Next.js, shipping less code.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The examples guidelines are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing.md#adding-examples)
Co-authored-by: Balázs Orbán <info@balazsorban.com>
Co-authored-by: Sukka <isukkaw@gmail.com>
Co-authored-by: JJ Kasper <jj@jjsweb.site>
Co-authored-by: Steven <steven@ceriously.com>
It makes copy-pasting the code easier since the person will be aware of
the import
<!--
Thanks for opening a PR! Your contribution is much appreciated.
To make sure your PR is handled as smoothly as possible we request that
you follow the checklist sections below.
Choose the right checklist for the change that you're making:
-->
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Co-authored-by: JJ Kasper <jj@jjsweb.site>
<!--
Thanks for opening a PR! Your contribution is much appreciated.
To make sure your PR is handled as smoothly as possible we request that
you follow the checklist sections below.
Choose the right checklist for the change that you're making:
-->
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Co-authored-by: JJ Kasper <jj@jjsweb.site>
Makes sure font loader CSS ends up correctly in the Flight Manifest and Flight Client Entries.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the feature request has been accepted for implementation before opening a PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
This PR serializes `regions` into `middleware-manifest.json`,
allowing to extend Edge Functions and Middleware for deployment
providers.
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Co-authored-by: Seiya Nuta <nuta@seiya.me>
Co-authored-by: JJ Kasper <jj@jjsweb.site>
This reducer takes a good chunk of the bundle but is never run on the server so we can eliminate it. 5-10ms wins from my manual benchmark runs.
![image](https://user-images.githubusercontent.com/11064311/192577550-4b2c3fa1-1ce9-456a-a635-d708e8200f2d.png)
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the feature request has been accepted for implementation before opening a PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
This PR adds the benchmarking script I've been using for #40251 to
measure the performance improvements that we make to the Edge SSR
runtime.
This tool:
- uploads two version of the benchmarking project to Vercel, one with
the latest canary and the one with your current local changes in dist
(don't forget to build!)
- runs some tests against the published url to measure TTFB
- displays a nice chart and table
What this doesn't do (yet):
- allow you to choose which URL to compare
- allow you to change the measured metric
- run a battery of differnet test
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
https://user-images.githubusercontent.com/11064311/191270204-04447e20-5a40-43a9-bcda-b7eaeb3d270a.mov
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Co-authored-by: kodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
As per #40926 we commit all node_modules inside test so we can test external packages. It will be much more convenient to not hide them in VS Code. With this configuration, all node_modules folders will be excluded except for these under the test directory.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the feature request has been accepted for implementation before opening a PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
As discussed with @sebmarkbage, the handling is more about showing a not found component than it is about a specific status code as these can come in late with streaming.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the feature request has been accepted for implementation before opening a PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Merge e2e tests customized `node_modules` with installed `node_modules`,
to let you debug easily locally without moving folder between
`node_modules` and `node_modules_bak`
Also add `optoutServerComponentsBundle` to config schema.
Clean up some utils, global variables and RegExp usages from the places
I touched recently.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Specific logic to handle the file transpilation on the server layer is
implemented in SWC (#40603). When Babel is enabled, that SWC transform
is ignored at the moment. In this PR we add an additional SWC pass after
Babel to handle that.
## Bug
- [ ] Related issues linked using `fixes #number`
- [x] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Co-authored-by: kodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
Since React 18 returning `undefined` from components is allowed which renders to `undefined` in the RSC response so we need a separate prop to know if the loading boundary was provided.
Thanks to @finn-orsini who reported this problem.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the feature request has been accepted for implementation before opening a PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
We currently resolve the `react-server` condition correctly inside
`externals` for the server layer, however that will cause the resolved
path to be external (as it is called "externals").
So we need a way to hook into the module resolution process to force it
to use the `react-server` condition **when it's on the server layer**.
The `resolve` option doesn't give us that ability, and the solution in
this PR is to leverage `normalModuleFactory`'s resolve hook to override
the resolve options before actually resolving it. And there we can have
the `contextInfo`.
One thing left out is bundling for the edge server, we need to add tests
and sort that out carefully.
## Bug
- [ ] Related issues linked using `fixes #number`
- [x] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
Fixes: https://github.com/vercel/next.js/issues/40927
## Bug
- [x] Related issues linked using `fixes #number`
- [x] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
Currently, a developer building a website using Next.js could write this
code with no type errors:
```tsx
<Image
width="kangaroo"
height="100px"
quality="medium"
{...rest}
/>
```
This PR adds stricter type checking, which will catch this type of error
earlier.
Similarly, this PR adds stricter types for the `responseLimit`, to
ensure the types align to:
https://nextjs.org/docs/messages/api-routes-response-size-limit
Co-authored-by: Steven <steven@ceriously.com>
Co-authored-by: JJ Kasper <jj@jjsweb.site>
# Context
Edge SSR'd routes cold boot performances are proportional to the
executed code size.
In order to improve it, we are trying to optimize for the bundle size of
a packed Edge SSR route.
This PR adds ESM compilation targets for all Next.js dist packages and
use them to bundle Edge SSR'd route.
This allows us to leverage the better tree shaking/DCE for ESM modules
in webpack in order to decrease the overall bundle size.
This PR also enables minifying Edge SSR routes. Since we don't control
which minifier might be used later (if any), it's best if we provide an
already optimised bundle.
<img width="903" alt="image"
src="https://user-images.githubusercontent.com/11064311/190005211-b7cb2c58-a56a-44b0-8ee4-fd3f603e41bd.png">
This is a 10ms cold boot win per my benchmarking script, which I'll put
in a subsequent PR.
Not done yet:
- ~~swap exported requires in `next/link` (and others) etc to point them
to the esm modules version~~
<!--
Thanks for opening a PR! Your contribution is much appreciated.
In order to make sure your PR is handled as smoothly as possible we
request that you follow the checklist sections below.
Choose the right checklist for the change that you're making:
-->
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have helpful link attached, see `contributing.md`
## Feature
- [x] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The examples guidelines are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing.md#adding-examples)
Co-authored-by: JJ Kasper <jj@jjsweb.site>
Co-authored-by: Shu Ding <g@shud.in>
### Issue
When import an esm package in client component, and use it in server
component page, it will fail to SSR but render successfully on client.
It's because the import to esm package will make the client chunk become
an **async module** since esm module will be treated as **async**.
```
page (serve component) -> local module (client) -> external dependency (esm)
```
Then in react SSR layer, it need the module type information of that
chunk, async or not for react so that react could unwrap the async
module from `Promise` properly when SSR.
### Solution
We need to mark the client entries which are effected by async/esm
modules that becoming **async** as `async: true` in SSR manifest.
Since flight manifest plugin is only running against client compiler,
which doesn't have those module information from server compiler. So we
collect the async modules from the **server** compiler **client** layer
from flight entry client plugin, then leverage the collection to detect
if a module is async in flight manifest plugin for react.
## Bug
- [ ] Related issues linked using `fixes #number`
- [x] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
Updates the output path so it's the same as when font files are imported
in CSS: `url(./font.woff2)`
Also adds missing font types to next package.
## Bug
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have a helpful link attached, see `contributing.md`
## Feature
- [ ] Implements an existing feature request or RFC. Make sure the
feature request has been accepted for implementation before opening a
PR.
- [ ] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Documentation added
- [ ] Telemetry added. In case of a feature if it's used or not.
- [ ] Errors have a helpful link attached, see `contributing.md`
## Documentation / Examples
- [ ] Make sure the linting passes by running `pnpm lint`
- [ ] The "examples guidelines" are followed from [our contributing
doc](https://github.com/vercel/next.js/blob/canary/contributing/examples/adding-examples.md)
The old link was cloning the "with-chakra-ui-typescript" repo which has
been deprecated.
<!--
Thanks for opening a PR! Your contribution is much appreciated.
To make sure your PR is handled as smoothly as possible we request that
you follow the checklist sections below.
Choose the right checklist for the change that you're making:
-->
## Bug
- [x] Fixed issue with link in README.md
<!--
Thanks for opening a PR! Your contribution is much appreciated.
To make sure your PR is handled as smoothly as possible we request that
you follow the checklist sections below.
Choose the right checklist for the change that you're making:
-->
For context, making a test change to allow testing CI changes in
https://github.com/vercel/next.js/pull/40910 without approval each run.
@ijjk How's this? The string's not being snapshotted so it shouldn't
break any tests.