Back to blog

Next.js Blog Post 404 After Publishing? Find the Cause

Check the published URL and deployment, then distinguish missing post data from a Next.js App Router route that excludes the new slug.

Branded cover showing a blog post URL and two possible causes of a Next.js 404

If a newly published blog post returns 404, first check whether you are opening the right URL on a production deployment that contains the post. If both are correct, inspect the route: its content lookup may not find the slug, or its build-time route configuration may exclude it. Fix the branch you can confirm, then open the exact production URL again. A draft, a successful build, and a working preview are not substitutes for that live check.

Confirm the URL and what reached production

Start with the address readers are actually using, including the domain, blog prefix, slug, and any trailing slash. Compare it with the post’s intended public URL rather than reconstructing a link from its title. Open it directly in a fresh browser tab. If a different slug works, that tells you the blog route exists, but not that the new post reached it.

Next, check the publication state and production release. Was the article approved or published, rather than left as a draft? Did the change containing its content reach the production branch or content source, and did the intended production deployment finish? If the content is only in a draft, preview, or unreleased change, publish or deploy it before changing route configuration.

This distinction matters with assisted publishing too. Ranks supports automatic setup and publishing for Next.js App Router sites using TypeScript, but its product reference says generated drafts are not proof of a live deployment and advises checking the live article URL after publication. Treat delivery of an article and availability of its public page as separate observations.

Separate a missing post from an excluded slug

Once the correct content and deployment are confirmed, follow the requested slug through the App Router page. A route such as app/blog/[slug]/page.tsx captures the URL’s slug value. Check that the deployed page is under the intended blog path and that its content lookup uses the same slug stored for the article.

If the lookup returns no post, inspect the production content source and any published-state filter. A page that invokes notFound() when it cannot find a record renders a not-found fallback; changing which slugs the route permits will not create the missing record. Correct the article’s stored slug, publication state, or deployed content, as appropriate, and test again.

If the post is present but its URL still fails, inspect generateStaticParams and the route’s configuration in the version and rendering mode your site uses. generateStaticParams supplies parameter values during the build; it does not run again during ISR revalidation. Where dynamicParams = false applies, paths omitted from those generated parameters return 404. That is a different failure from a lookup that cannot find post data.

Do not copy a route-config change into an unfamiliar project without checking its Next.js setup. Next.js notes that dynamicParams is removed when Cache Components is enabled. In that setup, investigate the applicable routing and rendering behavior rather than assuming the legacy setting controls the 404.

Worked example: the post exists, but the build excluded it

Consider a fictional site at https://example.com. Its team intends to publish https://example.com/blog/new-guide. The article data is present in the production release under the slug new-guide, and other blog posts load. The deployed app/blog/[slug]/page.tsx uses dynamicParams = false, but its build-time generateStaticParams output contains only old-guide and pricing-guide. The new URL returns 404 because new-guide is not among the permitted paths, even though its article data exists.

The fix for this fictional configuration is to make generateStaticParams include { slug: 'new-guide' } alongside the existing entries, build against the content source that contains the post, and deploy the resulting release. If the function derives its list from published posts, instead check why that post was absent from the list at build time and ensure the next build includes it. Merely waiting for ISR revalidation will not rerun generateStaticParams.

If your actual requirement is for new slugs to work without a rebuild, evaluate request-time or on-demand routing for your Next.js configuration and confirm that the post data will also be available when a visitor requests it. In configurations that support it, Next.js lists dynamicParams = true as the default; allowing an omitted path to be generated does not fix a missing content record.

Verify the repaired page on the public site

After the correction is released, open the exact production URL—not its preview—and confirm that the intended article renders with its title and body. Check the address after any redirect so you know which URL readers reach. If it still fails, repeat the diagnosis against the newly deployed release: confirm the post data first, then compare the requested slug with the route’s generated parameters and content lookup.

For future releases, the Next.js App Router blog publishing checklist covers preflight route and invalid-slug checks. If the page now loads but is absent from Google, that is a different problem; use the blog post indexing guide rather than treating search visibility as another production 404.

Sources

  1. Ranks: Public product referenceranks.so
  2. Next.js: Dynamic Route Segmentsnextjs.org
  3. Next.js: notFoundnextjs.org
  4. Next.js: generateStaticParamsnextjs.org
  5. Next.js: Route Segment Confignextjs.org

Grow your SaaS traffic on autopilot

One vetted backlink submission and one targeted blog article per day, on autopilot. Track your growth, all in one dashboard.

Try Ranks