A Journey through React Routing using React Router V4

- 7 mins

Index


Introduction

You might have a one-page SPA only one content to show. But on the rise of Frontend technologies such as React, Vue, Svelte; nowadays you might need more than a content to show within a SPA. So how do you do that? Well obviously with a Routing. Using routing in SPAs we can load and show different content. The good thing is it will change your URL and content without reloading at all. 

In this article, I will write up about react-router and its implementation.


React router

The Official react page has a list of routing packages you can use. But most commonly used routing package is react router, which I am using in this article. Feel free to check others too. 

React router router has two different versions for native apps and web apps. They both share the core react-router components. If it is native apps which require routing use react-router-native, else if it a web app then the package is react-router-dom  I will demonstrate here routing for web apps, which is technically react-router-dom. I will write another article on react-router-native in future.


Route types

First of all, we need a wrapper Router for routes. There are few different types of routers-

We can use any of them by importing like this-

	import { MemoryRouter as Router } from 'react-router-dom';
	import { BrowserRouter as Router } from 'react-router-dom'
	import { HashRouter as Router } from 'react-router-dom'
	import { StaticRouter as Router } from 'react-router-dom'

MemoryRouter

MemoryRouter keeps URL changing history in memory. So one drawback is you can’t go back or forward using browser history. It is useful if you are testing or using a non-browser environment (like React Native).

HashRouter

The biggest difference of HashRouter is, it uses hash in the URL, like /#/home. It is only for client-side routing and not looks that professional, also officially recommended to avoid using. HashRouter only exists to support legacy browsers which doesn’t support HTML pushState API.

BrowserRouter

BrowserRouter is the most popular and recommended router to use. It supports HTML5 pushState API.

StaticRouter

This router never changes location. That means client-side do not control the URL, only server does. StaticRouter is useful in Server Side Rendering.

Use one of them as Router, based on your requirement.


Implementation

So we have a base Router component imported. Declare a route about.
The Route, which takes two necessary props- path for URL path and a component name which will render on that path.

	import { Route } from "react-router-dom";
	<Router>
		/*Basic route*/
		<Route path='/about' component={About}/>
		/*Route with parameter user id*/
		<Route path='/:userid' component={SingleUser}/>
	</Router>

Here’s a catch, all declared routes match and render their components in sequence. In the above example, both of the component Home and SingleUser  will render. The reason is they match the declared routes pattern. We don’t want to render other components for a specific path.
So, in that case, we will use Switch. Using Switch the previous example will look like this-

	import { Route, Switch } from "react-router-dom";
	<Router>
		<Switch>
			/*Basic route*/
			<Route path='/about' component={About}/>
			/*Route with parameter user id*/
			<Route path='/:userid' component={SingleUser}/>
		</Switch>
	</Router>

Now in the router, if it matches path with /home, it will stop looking further down.


Nested Route

We’ve understood how routing works. What about nested routes? Let’s look at an example.

	import { Route, Switch } from "react-router-dom";
	<Router>
		<Switch>
			/*All users*/
			<Route path='/user' component={User}/>
			/*Specific user with id*/
			<Route path='/user/:id' component={SingleUser}/>
		</Switch>
	</Router>

But a long list of routes could be overwhelming. Also, it doesn’t feel right to declare user every time in the path.
In react-router nested routing could be implemented like this-

	import { Route, Switch } from "react-router-dom";
	<Router>
		<Switch>
			<Route exact path="/" component={Home} />
			/*All users*/
			<Route path='/user' component={UserRoutes}/>
		</Switch>
	</Router>


	const UserRoutes = ({match}) => {
		return (
			<Route exact path={match.path} component={User} />
			<Route path={`${match.path}/:id`} component={SingleUser} />	      
		);
	}

I guess the above code is self-explanatory. We are using specific component for the route under user, which is matching URL using match props.


Connecting with Route

The basic of routing is covered. One last thing is remained, which is navigation

We can do that using Link which generates an anchor tag with a href.

	import { Link } from 'react-router-dom'

	<Link to="/">Home</Link>
	<Link to="/about">About</Link>

to props are the same as declared Route path. On clicking this link initiate react-router.

In the same way, we can redirect from one route to another using Redirect property.

	import { Route, Redirect } from 'react-router'

	<Redirect to="/about" />

Active Route

What to do if we want to detect active link? We can use NavLink instead of Link. It is a special version of Link that will add attributes when matches with the current URL.
The implementation is fairly simple.

	import { NavLink } from 'react-router-dom'

	/* previous one <Link to="/">Home</Link>*/
	<NavLink exact to="/" activeClassName="activeColor">Home</NavLink>
	
	/* previous one <Link to="/about">About</Link>*/
	<NavLink exact to="/about" activeStyle=>About</NavLink>

Conclusion

I’ve tried to cover almost everything you need every day for routing. There’s a lot of other options and feature available in the official website. Navigate through the doc if you need something specific.


comments powered by Disqus
rss facebook twitter github youtube mail spotify lastfm instagram linkedin google google-plus pinterest medium vimeo stackoverflow reddit quora quora