21

If you have a route such as:

<Route path="/users/:userId" />

And then you export that route, and so it can be used across your app, such as:

export const MY_ROUTE = '/users/:userId/';

<Route path={MY_ROUTE} />

How do you set the param in a link dynamically? i.e. I would like to do this:

<Link to={MY_ROUTE} params={{userId: 1}} />

but params is totally ignored... and query just makes a query (?userId=) not a param... any ideas?

1
  • What do you mean by set the param dynamically? The route should be matched automatically when you hit /users/123 Commented Jun 28, 2016 at 20:43

4 Answers 4

15

Taken from React Router official docs:

From the upgrade guide from 1.x to 2.x:

<Link to>, onEnter, and isActive use location descriptors

<Link to> can now take a location descriptor in addition to strings. The query and state props are deprecated.

// v1.0.x

<Link to="/foo" query={{ the: 'query' }}/>

// v2.0.0

<Link to={{ pathname: '/foo', query: { the: 'query' } }}/>

Unfortunately, there's no support for passing in a param object, you yourself saw that.

In order to dynamically use the route you proposed, you would have to do something along the lines of:

<Link to={ MY_ROUTE.replace(':userId', '<someUserIdFromSomewhere>') }/>

Or you could further optimize by instead of exporting a string for MY_ROUTE, you could export a userLink function as such:

function userLink(userId) {
    return `/users/${userId}/`;
}

and then use that wherever you would want to use a Link to the route.

Below you can find supported parameters and API exposed on the Link component:

Router Link API

Sign up to request clarification or add additional context in comments.

1 Comment

You can try using url-pattern to construct your urls: path={new UrlPattern(MY_ROUTE).stringify({ userId: 1})}. It is not a perfect match but for simple routes it can work
7

I know this is an old question, but with React Router V4 you can use the path-to-regexp package, which is also being used by React Router V4.

Example:

import {Link} from 'react-router-dom';
import {compile} from 'path-to-regexp';

const MY_ROUTE = '/users/:userId/';
const toPath = compile(MY_ROUTE);

// Now you can use toPath to generate Links dynamically
// The following will log '/users/42' to the console
console.log( toPath({ userId: 42 }) );

Of course you can use the toPath method to create proper links as well, example:

<Link to={toPath({ userId: 42 })}>My Link</Link>

1 Comment

or, even simpler: <Link to={`users/${user.id}`}>My Link</Link>
6

You could create a function which interpolate the userId param to create the route, something like this:

export const MY_ROUTE = (userId) => `/users/${userId}/`;

<Route path={MY_ROUTE(':userId')} />

And so in your component

<Link to={MY_ROUTE(1)} params={{userId: 1}} />

Try this solution here: https://jsbin.com/pexikoyiwa/edit?js,console

1 Comment

This should be accepted answer, it allows to build both path required by router and actual path in the redirects in the clearest way
3

React Router v5 has a built in method to take in your url pattern and an object that maps to the params of the url called generatePath

https://v5.reactrouter.com/web/api/generatePath

import { generatePath } from "react-router";

generatePath("/user/:id/:entity(posts|comments)", {
  id: 1,
  entity: "posts"
});
// Will return /user/1/posts

So used in your example would be

<Link to={generatePath(MY_ROUTE, {userId: 1})} />

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.