vercel / next.js

The React Framework
https://nextjs.org
MIT License
127.12k stars 27.01k forks source link

`dynamicParams=false` show 404 page in dev, but not show 404 page after build in prod #52765

Open leozhao0709 opened 1 year ago

leozhao0709 commented 1 year ago

Verify canary release

Provide environment information

Operating System:
      Platform: linux
      Arch: x64
      Version: #22 SMP Tue Jan 10 18:39:00 UTC 2023
    Binaries:
      Node: 16.17.0
      npm: 8.15.0
      Yarn: 1.22.19
      pnpm: 7.1.0
    Relevant Packages:
      next: 13.4.10-canary.8
      eslint-config-next: N/A
      react: 18.2.0
      react-dom: 18.2.0
      typescript: 4.9.5
    Next.js Config:
      output: N/A

Which area(s) of Next.js are affected? (leave empty if unsure)

App Router

Link to the code that reproduces this issue or a replay of the bug

https://codesandbox.io/p/sandbox/wandering-forest-3tmmtz

To Reproduce

Run yarn dev, then access https://3tmmtz-3000.csb.app/post/404, it shows 404 page which is expected. Run yarn build, then yarn start in prod mode, access the same url as above, it shows the rendering page, not 404 page.

Describe the Bug

Leaving dynamicParams=false and accessing an entry point that does not exist in generateStaticParams does not return a 404 page in prod. (dev works fine)

The generateStaticParams only returns id 1,2,3 which means all the other param with id should return 404. Seems dev works as expected but prod is not.

Expected Behavior

when access a param that not returned by generateStaticParams function, it should return 404 page in both dev and prod.

Which browser are you using? (if relevant)

No response

How are you deploying your application? (if relevant)

No response

romainbenard commented 1 year ago

Hello @leozhao0709 did you found a solution?

I have the same issue with next 13.5.2

leozhao0709 commented 1 year ago

@romainbenard No, the app router approach seems never resolve this issues in production side. I feel the approuter approach is too buggy, so if the app is for production, I used the old way to create next js app.

JoiGud commented 1 year ago

We are also experiencing this issue. We tried reproducing it locally by setting NODE_ENV to production but that still gave us the 404 response; while on our live page we get some weird soup of a

  1. 404 top part / <header> and
  2. the main body of the layout is our frontpage

Say, for instance, we request awesomesite.com/foo and /foo is not a route that is valid, then we get the 404 page. But if we go on deeper; awesomesite.com/foo/bar (which also doesn't exist) then we get this weird mixture of layouts and no 404.

We are using Prismic for our CMS, and use their client to generate the static paths.

jahirfiquitiva commented 10 months ago

I'm facing the same issue using Next.js 14.0.5-canary.56

azizoid commented 10 months ago

Facing the same problem

Next.js 14.0.4
   - Environments: .env.local, .env

 ✓ Creating an optimized production build
 ✓ Compiled successfully
 ✓ Linting and checking validity of types
 ✓ Collecting page data
 ✓ Generating static pages (121/121)
 ✓ Collecting build traces
 ✓ Finalizing page optimization
leozhao0709 commented 9 months ago

This is still a problem today.

I found something interesting more today:

So I believe the problem is because the nextjs fetch cache. If you encounter the similar problem, you can either remove revalidate prop(default revalidate is false) or use other http client to fetch data.

One thing to remember is based on document here: https://nextjs.org/docs/app/api-reference/functions/fetch#revalidate, when using fetch, if we are not setting the revalidate, the default value is false which means there is a force cache happen.

jacekkuczynski commented 9 months ago

I've implemented a workaround, and it works just fine.

 export async function generateStaticParams() {
  const allCategoriesData = await getAllCategoriesData();
  return allCategoriesData.map((category) => ({
    slug: category.slug,
  }));
}

export default async function Home({ params }: { params: { slug: string } }) {
  const { slug } = params;

  // own implementation of dynamicParams = false
  const allCategoriesData = await getAllCategoriesData();
  const allParams = allCategoriesData.map((category) => category.slug);
  if (!allParams.includes(slug)) notFound();

  const { content } = await getCategoryData(slug);
  return (
    <div className="container flex flex-col items-center justify-center w-full min-h-screen">
      <CategoryContent content={content} />
    </div>
  );
}
joselinki25 commented 7 months ago

Also facing the same problem as of today.

▲ Next.js 14.1.0
   - Environments: .env.local

   Creating an optimized production build ...
Compiler edge-server unexpectedly exited with code: null and signal: SIGTERM
 ✓ Compiled successfully
 ✓ Linting and checking validity of types    
 ⚠ Using edge runtime on a page currently disables static generation for that page
 ✓ Collecting page data
 ✓ Generating static pages (15/15)
 ✓ Collecting build traces    
 ✓ Finalizing page optimization
matthewca commented 6 months ago

Also facing the same problem with 14.2.3. I'm trying to limit our website to specific languages (example.com/en and example.com/fr), but I can't get it to consistently throw a 404 for random values.

dkottas-nelios commented 5 months ago

This is still a problem today.

I found something interesting more today:

  • when using axios instead of fetch to fetch data, then both dev and prod can work correctly. ✅
  • When using fetch with {next: { revalidate: 0 },}, then dev is working, but prod it not work ❌
  • When using fetch without {next: { revalidate: 0 },}, then both dev and prod can work correctly. ✅

So I believe the problem is because the nextjs fetch cache. If you encounter the similar problem, you can either remove revalidate prop(default revalidate is false) or use other http client to fetch data.

One thing to remember is based on document here: https://nextjs.org/docs/app/api-reference/functions/fetch#revalidate, when using fetch, if we are not setting the revalidate, the default value is false which means there is a force cache happen.

I am using fetch without {next: { revalidate: 0 },} and still have the same issue in Next 14.2.3.

dkottas-nelios commented 5 months ago

For me the problem is with Vercel. I have the exact same project on Vercel and Netlify. Netlify returns 404 as expected, Vercel doesn't. The same code on Vercel: https://keytours-test.vercel.app/en/meteora/shoud-not-work and Netlify: https://keytours-test.netlify.app/en/meteora/shoud-not-work

atakanuludag commented 4 months ago

Isn't this problem fixed?

Edit by maintainer bot: Comment was automatically minimized because it was considered unhelpful. (If you think this was by mistake, let us know). Please only comment if it adds context to the issue. If you want to express that you have the same problem, use the upvote 👍 on the issue description or subscribe to the issue for updates. Thanks!

hulh122 commented 3 months ago

Same with mine, hope to fix the problem. I have to do like thie in my project, it seems bad

export async function generateStaticParams() {
    return await getPaths()
}

export async function generateMetadata({ params }: { params: { id: string } }): Promise<Metadata> {
   const paths = await getBlogPaths()

    if (paths.every(({ id }) => id !== params.id)) {
        return notFound()
    }
}

export default async function Page({ params }: { params: { id: string } }) {
    const paths = await getBlogPaths()

    if (paths.every(({ id }) => id !== params.id)) {
        return notFound()
    }
}