Add a Base URL to an App Using Redux and React Router
In this guide, you will learn how to set up a base URL in React Router and how to combine Redux seamlessly.
Nov 1, 2020 • 5 Minute Read
Introduction
A primary ingredient in any traditional or single-page app is routing. Routing is the ability to navigate from one page to another. In a typical single-page app, you can use React Router to do the routing for you. But as the app grows and the global state gets complicated, you may need to use a state management library like Redux.
The app may also be running on a different path (https://example.com/app) and not on the root domain, adding additional complexity. In this guide, you will learn how to set up a base URL in React Router and how to combine Redux seamlessly.
React-Router Example
This section covers how to add a base URL in a simple React app using React Router.
Install React-Router
The first step is to install the react-router-dom dependency in your app.
npm i react-router-dom
Configure the Routes
Next, add the page components as routes in the app.
const HomePage = () => {
return (
<div>
<h2>Home</h2>
</div>
);
};
const ContactPage = () => {
return (
<div>
<h2>Contact</h2>
</div>
);
};
const ProfilePage = () => {
return (
<div>
<h2>Profile</h2>
</div>
);
};
Pass the above page components as children to the Route component and wrap with the Switch component from react-router-dom.
import { Route, Switch } from "react-router-dom";
// ...
const Main = () => {
return (
<div className="app">
<Navbar />
<div className="content">
<Switch>
<Route exact path="/">
<HomePage />
</Route>
<Route path="/contact">
<ContactPage />
</Route>
<Route path="/profile">
<ProfilePage />
</Route>
</Switch>
</div>
</div>
);
};
Adding a Base URL
Import the BrowserRouter component from react-router-dom. The BrowserRouter component has a basename prop, which accepts a string as its value in case the React app is hosted from a sub-directory.
import { BrowserRouter } from "react-router-dom";
const App = () => {
return (
<BrowserRouter basename="/app">
<Main />
</BrowserRouter>
);
};
Adding basename in the BrowserRouter component ensures that all the links in the routes are prefixed with the base URL. For example, <Link to='/contact' /> will be rendered as <a href='/app/contact'>.
Integrating Redux
In this section, you will integrate Redux with the above React Router set up.
The connected-react-router package is recommended by the maintainers of React Router for deeper Redux integration. To install connected-react-router, run the following command.
npm i connected-react-router
Creating the history Object
The history object can be used to change the browser's history session programmatically. To create a history object, import the createBrowserHistory function from the history package and create the object as shown below.
import { createBrowserHistory } from "history";
const history = createBrowserHistory();
The history package is a dependency of react-router-dom, so you don't have to install it again.
Create Router Connected Store
Next, connect the history object to the store. To do that, import the connectRouter helper function from connected-react-router package and provide the created history object.
import { connectRouter } from "connected-react-router";
import { createStore } from "redux";
const reducer = (initialState, action) => {
// ...
};
const store = createStore(connectRouter(history)(reducer));
Adding routerMiddleware to Redux
routerMiddleware will dispatch the history actions to the Redux store. Use the applyMiddleware helper function from redux to include routerMiddleware in the app.
import { connectRouter, routerMiddleware } from "connected-react-router";
import { createStore, applyMiddleware } from "redux";
const store = createStore(
connectRouter(history)(reducer),
applyMiddleware(routerMiddleware(history))
);
Using ConnectedRouter Component
You're almost done. The last step is to use the ConnectedRouter component and pass the history object as a prop. Make sure you wrap the ConnectedRouter component with the Provider component from react-redux.
import { ConnectedRouter } from "connected-react-router";
import { Provider } from "react-redux";
const App = () => {
return (
<Provider store={store}>
<ConnectedRouter history={history}>
<BrowserRouter basename="/app">
<Main />
</BrowserRouter>
</ConnectedRouter>
</Provider>
);
};
Conclusion
Redux is a vital component of the React ecosystem, so you need to understand how to integrate React-Router and Redux and how they work together. React Router has an excellent section on deep Redux integration that you may want to read for a better understanding of how things work under the hood.