fridays / next-routes

Universal dynamic routes for Next.js
MIT License
2.47k stars 230 forks source link

404 when using Router.replace() to custom route #56

Closed jesstelford closed 7 years ago

jesstelford commented 7 years ago

Reproduction case: https://github.com/jesstelford/next-routes-issue-56

next: 3.0.0-beta16 next-routes: 1.0.27

git clone https://github.com/jesstelford/next-routes-issue-56.git next-routes-issue-56
cd next-routes-issue-56
yarn
yarn dev
  1. Open http://localhost:3000/abc123
    • Note: The /abc123 page loads fine
  2. Click the link to /about
    • Will redirect you back to /abc123
  3. Note: Incorrectly receiving a 404
  4. Refresh the page (or wait for next 'ping')
  5. /abc123 works as expected

Investigation

It looks like under the hood, next.js's client-side routing is requesting the url http://localhost:3000/_next/1498079290131/page/abc123 instead of http://localhost:3000/abc123. This wont match any routes I've setup, so it falls through to next.js, which throws the 404.

Server side rendering appears to work fine, because it's just a regular HTTP request being handled by express, which correctly matches one of the routes setup.

I tried adding some hacks such as path.replace(/^_next\/\d+\/page/, ''), but that didn't appear to improve anything.

This happens in both development and production mode (initially I was led astray by Webpack HMR call stacks, but they don't appear in production mode, while the error persists)

Workaround

Replacing Router.replace('/abc123'); with window.location = '/abc123'; in pages/about.js will get it working client side again (by forcing a hard server refresh).

Related

Kinda sorta maybe related(?): https://github.com/zeit/next.js/issues/257

fridays commented 7 years ago

Router.replace is provided by next.js, if you want to use it with routes, use Router.replaceRoute:

Router.replaceRoute('user', {userId: 'abc123'})

Now with the latest version you can also do:

Router.replaceRoute('/abc123')
jesstelford commented 7 years ago

You're a champion - Router.replaceRoute() works great in 1.0.40 :tada:

ahmadalfy commented 6 years ago

Router.replaceRoute is no longer provided by Router. It will return undefined.

Was it removed from next/router?