Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Next.js router.isReady never set to true on custom 404 page #35990

Closed
1 task done
iiroj opened this issue Apr 8, 2022 · 8 comments · Fixed by #43836
Closed
1 task done

Next.js router.isReady never set to true on custom 404 page #35990

iiroj opened this issue Apr 8, 2022 · 8 comments · Fixed by #43836
Labels
bug Issue was opened via the bug report template.

Comments

@iiroj
Copy link

iiroj commented Apr 8, 2022

Verify canary release

  • I verified that the issue exists in Next.js canary release

Provide environment information

Operating System:
      Platform: darwin
      Arch: arm64
      Version: Darwin Kernel Version 21.4.0: Fri Mar 18 00:46:32 PDT 2022; root:xnu-8020.101.4~15/RELEASE_ARM64_T6000
    Binaries:
      Node: 17.7.2
      npm: 8.5.5
      Yarn: 1.22.17
      pnpm: N/A
    Relevant packages:
      next: 12.1.5-canary.4
      react: 17.0.2
      react-dom: 17.0.2

What browser are you using? (if relevant)

Safari 15.4 (17613.1.17.1.13)

How are you deploying your application? (if relevant)

next dev

Describe the Bug

The Next.js router object contains a boolean value router.isReady, which according to docs indicates:

Whether the router fields are updated client-side and ready for use. Should only be used inside of useEffect methods and not for conditionally rendering on the server. See related docs for use case with automatically statically optimized pages

We are using this in a withSSRLoadingIndicator HoC that checks inside an useEffect hook that if the router is ready, render page component, and else render a full-screen loading indicator. This allows us to deploy certain pages as small static files, which only load client-side, while other pages can use the full getServerSideProps method and render what they need directly. With the HoC, we don't have to check if the router.query object is populated, because the page component will receive the data on its first render (because then router.isReady = true).

This HoC works nicely on all other pages expect our custom 404 page, and after a bit of debugging it seems that the Router instance simply never sets router.isReady = true.

Expected Behavior

I would expect the custom 404 to also receive router.isReady = true on the client-side.

To Reproduce

Create a Next.js page src/pages/index.js with code like this:

import { useRouter } from 'next/router'
import React, { useEffect, useState } from 'react'

export default () => {
  const router = useRouter()
  const [state, setState] = useState(false)

  useEffect(() => {
    setState(router.isReady)
  }, [router.isReady])

  return <p>{state === true ? 'Router is ready' : 'Router is not ready'}</p>
}

When opening the page in your browser, http://localhost:3000/, you will see:

  1. Router is not ready on the first render
  2. Router is ready on the second render

Copy the same page component as src/pages/404.js, open http://localhost:3000/404, and you will instead see:

  1. Router is not ready on the first render
  2. ...there will not be a second render at all
@iiroj iiroj added the bug Issue was opened via the bug report template. label Apr 8, 2022
@bryanrsmith
Copy link
Contributor

Additionally, after landing on a 404 page the isReady value remains false for the lifetime of the router. If you land on a custom 404 page that doesn't use router.isReady but then use the site nav to navigate to a different page that does, the page following that client side navigation will break.

@cvolant
Copy link
Contributor

cvolant commented Jun 21, 2022

I had the same issue because router.replace (shallow) was executed during the first render. I moved it inside a useEffect and it fixed my problem. If it can be of any help to debug...

@mykyta-hryn
Copy link

I am able to reproduce this bug the way @iiroj described.
Do we have any progress on this bug? It hardly breaks my website's functionality

@vixeven
Copy link

vixeven commented Sep 1, 2022

I found out that router.isReady works as expected when reusing the built-in error by creating custom _error page.

@Saturate
Copy link

Saturate commented Oct 4, 2022

I found out that router.isReady works as expected when reusing the built-in error by creating custom _error page.

I can confirm this works, I needed access to router.query and had troubles doing this on a 404 page.

@qiweiii
Copy link

qiweiii commented Oct 26, 2022

@vixeven @Saturate, I also facing this problem, could you share or explain how to reuse the built-in error page to solve this? Thanks!

@Saturate
Copy link

Saturate commented Oct 27, 2022

ijjk added a commit that referenced this issue Dec 13, 2022
Previously, query parameters were not available on 404 pages because
calling the router methods would change the pathname in the browser.
This change adds support for the query to update for those pages without
updating the path to include the basePath.

This additionally narrows some Typescript types that were previous set
to `any` which highlighted some type errors that were corrected.

Fixes: #35990

Co-authored-by: JJ Kasper <jj@jjsweb.site>
timneutkens pushed a commit that referenced this issue Dec 13, 2022
Previously, query parameters were not available on 404 pages because
calling the router methods would change the pathname in the browser.
This change adds support for the query to update for those pages without
updating the path to include the basePath.

This additionally narrows some Typescript types that were previous set
to `any` which highlighted some type errors that were corrected.

Fixes: #35990

Co-authored-by: JJ Kasper <jj@jjsweb.site>
@github-actions
Copy link
Contributor

This closed issue has been automatically locked because it had no new activity for a month. If you are running into a similar issue, please create a new issue with the steps to reproduce. Thank you.

@github-actions github-actions bot locked as resolved and limited conversation to collaborators Jan 12, 2023
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
bug Issue was opened via the bug report template.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

7 participants