Stabilize swrDelta config (#66108)

Alternative to https://github.com/vercel/next.js/pull/65867 this
stabilizes our `swrDelta` config that allows customizing the
`stale-while-revalidate` period that is included in the `Cache-Control`
header for ISR enabled routes.

This is not a breaking change itself as no default value is provided as
is the case already.
This commit is contained in:
JJ Kasper 2024-05-23 08:46:57 -05:00 committed by GitHub
parent 93c861d67b
commit 0bf384bf02
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 39 additions and 8 deletions

View file

@ -0,0 +1,19 @@
---
title: swrDelta
description: Set a custom stale-while-revalidate period for ISR enabled pages.
---
{/* The content of this doc is shared between the app and pages router. You can use the `<PagesOnly>Content</PagesOnly>` component to add content that is specific to the Pages Router. Any shared content should not be wrapped in a component. */}
You can specify a custom stale-while-revalidate period for CDNs to consume in the `Cache-Control` header for ISR enabled pages.
Open `next.config.js` and add the `swrDelta` config:
```js filename="next.config.js"
module.exports = {
// one year in seconds
swrDelta: 31536000,
}
```
Now instead of an empty `stale-while-revalidate` period being provided in the `Cache-Control` header, the custom period will be included.

View file

@ -421,7 +421,7 @@ export async function exportAppImpl(
experimental: { experimental: {
isAppPPREnabled: checkIsAppPPREnabled(nextConfig.experimental.ppr), isAppPPREnabled: checkIsAppPPREnabled(nextConfig.experimental.ppr),
clientTraceMetadata: nextConfig.experimental.clientTraceMetadata, clientTraceMetadata: nextConfig.experimental.clientTraceMetadata,
swrDelta: nextConfig.experimental.swrDelta, swrDelta: nextConfig.swrDelta,
after: nextConfig.experimental.after ?? false, after: nextConfig.experimental.after ?? false,
}, },
} }

View file

@ -569,7 +569,7 @@ export default abstract class Server<
isExperimentalCompile: this.nextConfig.experimental.isExperimentalCompile, isExperimentalCompile: this.nextConfig.experimental.isExperimentalCompile,
experimental: { experimental: {
isAppPPREnabled, isAppPPREnabled,
swrDelta: this.nextConfig.experimental.swrDelta, swrDelta: this.nextConfig.swrDelta,
clientTraceMetadata: this.nextConfig.experimental.clientTraceMetadata, clientTraceMetadata: this.nextConfig.experimental.clientTraceMetadata,
after: this.nextConfig.experimental.after ?? false, after: this.nextConfig.experimental.after ?? false,
}, },
@ -1628,7 +1628,7 @@ export default abstract class Server<
generateEtags, generateEtags,
poweredByHeader, poweredByHeader,
revalidate, revalidate,
swrDelta: this.nextConfig.experimental.swrDelta, swrDelta: this.nextConfig.swrDelta,
}) })
res.statusCode = originalStatus res.statusCode = originalStatus
} }
@ -2913,7 +2913,7 @@ export default abstract class Server<
'Cache-Control', 'Cache-Control',
formatRevalidate({ formatRevalidate({
revalidate: cacheEntry.revalidate, revalidate: cacheEntry.revalidate,
swrDelta: this.nextConfig.experimental.swrDelta, swrDelta: this.nextConfig.swrDelta,
}) })
) )
} }
@ -2935,7 +2935,7 @@ export default abstract class Server<
'Cache-Control', 'Cache-Control',
formatRevalidate({ formatRevalidate({
revalidate: cacheEntry.revalidate, revalidate: cacheEntry.revalidate,
swrDelta: this.nextConfig.experimental.swrDelta, swrDelta: this.nextConfig.swrDelta,
}) })
) )
} }

View file

@ -290,7 +290,6 @@ export const configSchema: zod.ZodType<NextConfig> = z.lazy(() =>
externalMiddlewareRewritesResolve: z.boolean().optional(), externalMiddlewareRewritesResolve: z.boolean().optional(),
fallbackNodePolyfills: z.literal(false).optional(), fallbackNodePolyfills: z.literal(false).optional(),
fetchCacheKeyPrefix: z.string().optional(), fetchCacheKeyPrefix: z.string().optional(),
swrDelta: z.number().optional(),
flyingShuttle: z.boolean().optional(), flyingShuttle: z.boolean().optional(),
forceSwcTransforms: z.boolean().optional(), forceSwcTransforms: z.boolean().optional(),
fullySpecified: z.boolean().optional(), fullySpecified: z.boolean().optional(),
@ -589,6 +588,7 @@ export const configSchema: zod.ZodType<NextConfig> = z.lazy(() =>
skipMiddlewareUrlNormalize: z.boolean().optional(), skipMiddlewareUrlNormalize: z.boolean().optional(),
skipTrailingSlashRedirect: z.boolean().optional(), skipTrailingSlashRedirect: z.boolean().optional(),
staticPageGenerationTimeout: z.number().optional(), staticPageGenerationTimeout: z.number().optional(),
swrDelta: z.number().optional(),
target: z.string().optional(), target: z.string().optional(),
trailingSlash: z.boolean().optional(), trailingSlash: z.boolean().optional(),
transpilePackages: z.array(z.string()).optional(), transpilePackages: z.array(z.string()).optional(),

View file

@ -225,7 +225,7 @@ export interface ExperimentalConfig {
fetchCacheKeyPrefix?: string fetchCacheKeyPrefix?: string
optimisticClientCache?: boolean optimisticClientCache?: boolean
/** /**
* period (in seconds) where the server allow to serve stale cache * @deprecated use config.swrDelta instead
*/ */
swrDelta?: SwrDelta swrDelta?: SwrDelta
middlewarePrefetch?: 'strict' | 'flexible' middlewarePrefetch?: 'strict' | 'flexible'
@ -839,6 +839,11 @@ export interface NextConfig extends Record<string, any> {
} }
} }
/**
* period (in seconds) where the server allow to serve stale cache
*/
swrDelta?: SwrDelta
/** /**
* Enable experimental features. Note that all experimental features are subject to breaking changes in the future. * Enable experimental features. Note that all experimental features are subject to breaking changes in the future.
*/ */
@ -906,6 +911,7 @@ export const defaultConfig: NextConfig = {
httpAgentOptions: { httpAgentOptions: {
keepAlive: true, keepAlive: true,
}, },
swrDelta: undefined,
staticPageGenerationTimeout: 60, staticPageGenerationTimeout: 60,
output: !!process.env.NEXT_PRIVATE_STANDALONE ? 'standalone' : undefined, output: !!process.env.NEXT_PRIVATE_STANDALONE ? 'standalone' : undefined,
modularizeImports: undefined, modularizeImports: undefined,
@ -923,7 +929,6 @@ export const defaultConfig: NextConfig = {
fetchCacheKeyPrefix: '', fetchCacheKeyPrefix: '',
middlewarePrefetch: 'flexible', middlewarePrefetch: 'flexible',
optimisticClientCache: true, optimisticClientCache: true,
swrDelta: undefined,
manualClientBasePath: false, manualClientBasePath: false,
cpus: Math.max( cpus: Math.max(
1, 1,

View file

@ -503,6 +503,13 @@ function assignDefaults(
configFileName, configFileName,
silent silent
) )
warnOptionHasBeenMovedOutOfExperimental(
result,
'swrDelta',
'swrDelta',
configFileName,
silent
)
if ((result.experimental as any).outputStandalone) { if ((result.experimental as any).outputStandalone) {
if (!silent) { if (!silent) {