22

I'm using the default dynamic routing technique of nextjs in my project which is based on the folder structure. I have a route which is:

pages/[language]/location/[location_id]

Now I'm coming across a use case where I need the above route exactly the same except the last parameter of [location_id], I need [route_id] here.

When I created a file [route_id].js for this new route, I'm facing this error:

 throw new Error(`You cannot use different slug names for the same dynamic path ('${previousSlug}' !== '${nextSlug}').`);

I'm aware of the error and the problem about why it's showing me this after doing some research but I'm unable to understand how I can solve this problem. I just want a solution how I can implement these two routes in my app:

Route 1: pages/[language]/location/[location_id]
Route 2: pages/[language]/location/[route_id]

PS: I've already studied this: https://github.com/zeit/next.js/issues/9081

Rehan Sattar
  • 3,497
  • 4
  • 13
  • 21

3 Answers3

17

The two routes you have provided are exactly equivalent and are not at all different. Therefore, they will be handled by a single page. There is no example of two urls that will route to different nextjs pages for the above two routes.

Anything written in [] will handle any type of value e.g 1 or 2 or any other value for that matter.

You can not make two pages to handle same request because there is no way for next or anyone else for that matter to know whether you are using route_id or location_id because these are both variables that are representing any value.

If you want to differentitate between them, either create a new route with

/route/[route_id] instead of

/location/[location_id], or use queryparams e.g

pages/[language]/location?locationid=[location_id]

And

pages/[language]/location?routeid=[route_id]
Kevin Danikowski
  • 4,620
  • 6
  • 41
  • 75
Hassaan Tauqir
  • 2,464
  • 1
  • 13
  • 11
  • Thank you so much, I changed the routes. Now the root structure is same but I have one parameter for `route_id` for the new route. – Rehan Sattar Mar 09 '20 at 13:00
  • 1
    What if I don't want to create new route or use query parameters? I have a scenario where the URI can category, post or page, that's why I want to use different slugs as same path but seems to be not possible, why the href attribute of Link component can't distinguish for which slug the request is? – Vikas Khunteta Mar 08 '21 at 07:39
  • 1
    @VikasKhunteta have you ever find a solution for this. I have very similar routing needs and I am facing the same problem. Thank you! – Primoz Rome Aug 16 '21 at 08:58
  • I too need a solution where query params aren't an option. I opened a new question, will hopefully have luck. https://stackoverflow.com/questions/69457864/nextjs-how-to-dynamically-load-different-apps-with-dynamic-routes – Kevin Danikowski Oct 05 '21 at 22:23
4

From the official code of Next.js:

currently multiple dynamic params on the same segment level are not supported

                if (previousSlug !== null) {
                    // If the specific segment already has a slug but the slug is not `something`
                    // This prevents collisions like:
                    // pages/[post]/index.js
                    // pages/[id]/index.js
                    // Because currently multiple dynamic params on the same segment level are not supported
                    if (previousSlug !== nextSlug) {
                        // TODO: This error seems to be confusing for users, needs an error link, the description can be based on above comment.
                        throw new Error(`You cannot use different slug names for the same dynamic path ('${previousSlug}' !== '${nextSlug}').`);
                    }
                }
Alex K - JESUS first
  • 1,883
  • 14
  • 13
0

It would have been possible for Next.js to handle multiple dynamic routes under some circumstances. For instance, once a dynamic route is detected to have multiple files, if those files also included getStaticPaths, it could iterate through them. If the first file didn't have the path, it would attempt to find it on the second file. This however could have many edge cases in how its expected to function, so it's understandable that they didn't include it.

I resolved this issue by having a single dynamic route which acts as a union for both sets of data. During rendering, I check which data the page is and provide the appropriate component. Below is some code as an example.

const getStaticPaths = () => {
  const pathsA = [...]
  const pathsB = [...]
  return {paths: [...pathsA, ...pathsB]}
}

const getStaticProps = (context) => {
  const isDataA = ...
  const data = ...
  return {props: {isDataA, data}}
}

const Page = (props) => {
  if (props.isDataA) {
    return <DataAPage data={props.data} />
  } else {
    return <DataBPage data={props.data} />
  }
}

const DataAPage = (props) => {
  return <>{props.data}</>
}

const DataBPage = (props) => {
  return <>{props.data}</>
}
cnotethegr8
  • 7,342
  • 8
  • 68
  • 104