diff --git a/demos/default/pages/getStaticProps/with-revalidate-404.js b/demos/default/pages/getStaticProps/with-revalidate-404.js new file mode 100644 index 0000000000..c5658021b8 --- /dev/null +++ b/demos/default/pages/getStaticProps/with-revalidate-404.js @@ -0,0 +1,21 @@ +import Link from 'next/link' + +const Show = () => ( +
+

This page is ISR, but will return a 404 if the current time ends in 0-4.

+ + + Go back home + +
+) + +export async function getStaticProps(context) { + return { + props: {}, + notFound: new Date().getMinutes() % 10 < 5, + revalidate: 60, + } +} + +export default Show diff --git a/packages/runtime/src/templates/getHandler.ts b/packages/runtime/src/templates/getHandler.ts index c6fbff2bb5..6ecbd1c2b2 100644 --- a/packages/runtime/src/templates/getHandler.ts +++ b/packages/runtime/src/templates/getHandler.ts @@ -128,8 +128,15 @@ const makeHandler = (conf: NextConfig, app, pageRoot, staticManifest: Array<[str const ttl = getMaxAge(cacheHeader) // Long-expiry TTL is basically no TTL, so we'll skip it if (ttl > 0 && ttl < ONE_YEAR_IN_SECONDS) { - result.ttl = ttl - requestMode = `odb ttl=${ttl}` + // ODBs currently have a minimum TTL of 60 seconds + result.ttl = Math.max(ttl, 60) + } + // Only cache 404s ephemerally + if (ttl === ONE_YEAR_IN_SECONDS && result.statusCode === 404) { + result.ttl = 60 + } + if (result.ttl > 0) { + requestMode = `odb ttl=${result.ttl}` } } multiValueHeaders['cache-control'] = ['public, max-age=0, must-revalidate'] diff --git a/test/__snapshots__/index.js.snap b/test/__snapshots__/index.js.snap index bb77f6a9a4..5256ac3769 100644 --- a/test/__snapshots__/index.js.snap +++ b/test/__snapshots__/index.js.snap @@ -20,6 +20,7 @@ exports.resolvePages = () => { require.resolve('../../../.next/server/pages/getStaticProps/[id].js') require.resolve('../../../.next/server/pages/getStaticProps/env.js') require.resolve('../../../.next/server/pages/getStaticProps/static.js') + require.resolve('../../../.next/server/pages/getStaticProps/with-revalidate-404.js') require.resolve('../../../.next/server/pages/getStaticProps/with-revalidate.js') require.resolve('../../../.next/server/pages/getStaticProps/withFallback/[...slug].js') require.resolve('../../../.next/server/pages/getStaticProps/withFallback/[id].js') @@ -55,6 +56,7 @@ exports.resolvePages = () => { require.resolve('../../../.next/server/pages/getStaticProps/[id].js') require.resolve('../../../.next/server/pages/getStaticProps/env.js') require.resolve('../../../.next/server/pages/getStaticProps/static.js') + require.resolve('../../../.next/server/pages/getStaticProps/with-revalidate-404.js') require.resolve('../../../.next/server/pages/getStaticProps/with-revalidate.js') require.resolve('../../../.next/server/pages/getStaticProps/withFallback/[...slug].js') require.resolve('../../../.next/server/pages/getStaticProps/withFallback/[id].js') @@ -90,6 +92,7 @@ exports.resolvePages = () => { require.resolve('../../../web/.next/server/pages/getStaticProps/[id].js') require.resolve('../../../web/.next/server/pages/getStaticProps/env.js') require.resolve('../../../web/.next/server/pages/getStaticProps/static.js') + require.resolve('../../../web/.next/server/pages/getStaticProps/with-revalidate-404.js') require.resolve('../../../web/.next/server/pages/getStaticProps/with-revalidate.js') require.resolve('../../../web/.next/server/pages/getStaticProps/withFallback/[...slug].js') require.resolve('../../../web/.next/server/pages/getStaticProps/withFallback/[id].js') @@ -125,6 +128,7 @@ exports.resolvePages = () => { require.resolve('../../../web/.next/server/pages/getStaticProps/[id].js') require.resolve('../../../web/.next/server/pages/getStaticProps/env.js') require.resolve('../../../web/.next/server/pages/getStaticProps/static.js') + require.resolve('../../../web/.next/server/pages/getStaticProps/with-revalidate-404.js') require.resolve('../../../web/.next/server/pages/getStaticProps/with-revalidate.js') require.resolve('../../../web/.next/server/pages/getStaticProps/withFallback/[...slug].js') require.resolve('../../../web/.next/server/pages/getStaticProps/withFallback/[id].js') @@ -501,6 +505,12 @@ Array [ "status": 200, "to": "/.netlify/functions/___netlify-handler", }, + Object { + "force": true, + "from": "/_next/data/build-id/en/getStaticProps/with-revalidate-404.json", + "status": 200, + "to": "/.netlify/builders/___netlify-odb-handler", + }, Object { "force": true, "from": "/_next/data/build-id/en/getStaticProps/with-revalidate.json", @@ -723,6 +733,12 @@ Array [ "status": 200, "to": "/.netlify/functions/___netlify-handler", }, + Object { + "force": true, + "from": "/_next/data/build-id/es/getStaticProps/with-revalidate-404.json", + "status": 200, + "to": "/.netlify/builders/___netlify-odb-handler", + }, Object { "force": true, "from": "/_next/data/build-id/es/getStaticProps/with-revalidate.json", @@ -909,6 +925,12 @@ Array [ "status": 200, "to": "/.netlify/functions/___netlify-handler", }, + Object { + "force": true, + "from": "/_next/data/build-id/fr/getStaticProps/with-revalidate-404.json", + "status": 200, + "to": "/.netlify/builders/___netlify-odb-handler", + }, Object { "force": true, "from": "/_next/data/build-id/fr/getStaticProps/with-revalidate.json", @@ -1202,6 +1224,12 @@ Array [ "status": 200, "to": "/.netlify/builders/___netlify-odb-handler", }, + Object { + "force": true, + "from": "/es/getStaticProps/with-revalidate-404", + "status": 200, + "to": "/.netlify/builders/___netlify-odb-handler", + }, Object { "force": false, "from": "/es/getStaticProps/withFallback/:id", @@ -1394,6 +1422,12 @@ Array [ "status": 200, "to": "/.netlify/builders/___netlify-odb-handler", }, + Object { + "force": true, + "from": "/fr/getStaticProps/with-revalidate-404", + "status": 200, + "to": "/.netlify/builders/___netlify-odb-handler", + }, Object { "force": false, "from": "/fr/getStaticProps/withFallback/:id", @@ -1538,6 +1572,12 @@ Array [ "status": 200, "to": "/.netlify/builders/___netlify-odb-handler", }, + Object { + "force": true, + "from": "/getStaticProps/with-revalidate-404", + "status": 200, + "to": "/.netlify/builders/___netlify-odb-handler", + }, Object { "force": false, "from": "/getStaticProps/withFallback/:id",