ReactJS roles and permissions in depth tutorial

    By: Thad Mertz
    6 months ago
    Category: ReactViews: 153

    User authentication and authorization are critical aspects of modern web applications. You need to ensure that users can only access the parts of your application that they are authorized to see. React, a popular JavaScript library for building user interfaces, provides an excellent solution for handling user roles and permissions. When combined with React Router, you can create a powerful system for controlling access to different parts of your application. In this blog post, we will explore how to implement role-based permissions in a React application using React Router, with practical examples.


    Understanding Roles and Permissions


    Before diving into the code, let's clarify some concepts:


    - **Roles**: Roles are labels or groups assigned to users, defining their access privileges. Common roles include "admin," "user," and "guest." Users can have one or more roles, and each role has a set of associated permissions.


    - **Permissions**: Permissions are rules or settings that determine what actions users with specific roles can perform. These actions could include viewing, creating, updating, or deleting data, among others.


    Setting Up a React Application


    If you don't already have a React application, start by creating one. You can use Create React App or your preferred method to set up a basic project structure. Once you have a project ready, you can begin implementing role-based permissions.


    Implementing Role-Based Routing


    Step 1: Create a RoleContext


    The first step is to create a `RoleContext` that will store the user's roles. This context should be available throughout your application, so you can access the user's roles from any component.



    // RoleContext.js
    import React, { createContext, useContext, useState } from 'react';
    
    const RoleContext = createContext();
    
    export const RoleProvider = ({ children }) => {
     const [roles, setRoles] = useState([]);
    
     return (
      <RoleContext.Provider value={ roles, setRoles }>
       {children}
      </RoleContext.Provider>
     );
    };
    
    export const useRoles = () => {
     const context = useContext(RoleContext);
     if (!context) {
      throw new Error('useRoles must be used within a RoleProvider');
     }
     return context;
    };
    



    Step 2: Set User Roles


    In your application, when a user logs in, set their roles using the `setRoles` function provided by the `RoleContext`.


    // Login.js
    import React from 'react';
    import { useRoles } from './RoleContext';
    
    const Login = () => {
     const { setRoles } = useRoles();
    
     const handleLogin = () => {
      // Simulate a login request, and once the user is authenticated, set their roles.
      const userRoles = ['user'];
      setRoles(userRoles);
     };
    
     return (
      <div>
       <button onClick={handleLogin}>Login</button>
      </div>
     );
    };
    



    Step 3: Create Protected Routes


    Now, you can create protected routes that are only accessible by users with specific roles. Use React Router for this purpose.


    // ProtectedRoute.js
    import React from 'react';
    import { Route, Redirect } from 'react-router-dom';
    import { useRoles } from './RoleContext';
    
    const ProtectedRoute = ({ component: Component, allowedRoles, ...rest }) => {
     const { roles } = useRoles();
    
     return (
      <Route
       {...rest}
       render={(props) => {
        if (allowedRoles.some((role) => roles.includes(role))) {
         return <Component {...props} />;
        } else {
         return <Redirect to="/unauthorized" />;
        }
       }
      />
     );
    };
    
    export default ProtectedRoute;
    


    Step 4: Implement Role-Based Routing


    Now, you can use the `ProtectedRoute` component to create role-based routes.


    // App.js
    import React from 'react';
    import { BrowserRouter, Route, Switch } from 'react-router-dom';
    import { RoleProvider } from './RoleContext';
    import ProtectedRoute from './ProtectedRoute';
    import Home from './Home';
    import AdminDashboard from './AdminDashboard';
    import UserDashboard from './UserDashboard';
    import Unauthorized from './Unauthorized';
    
    function App() {
     return (
      <RoleProvider>
       <BrowserRouter>
        <Switch>
         <Route path="/" component={Home} exact />
         <ProtectedRoute path="/admin" component={AdminDashboard} allowedRoles={['admin']} />
         <ProtectedRoute path="/user" component={UserDashboard} allowedRoles={['user']} />
         <Route path="/unauthorized" component={Unauthorized} />
        </Switch>
       </BrowserRouter>
      </RoleProvider>
     );
    }
    
    export default App;
    



    In this blog post, we've explored how to implement role-based permissions in a React application using React Router. By creating a `RoleContext` to manage user roles and leveraging the `ProtectedRoute` component to control access, you can ensure that users only see what they are authorized to access. This approach provides a secure and user-friendly way to manage permissions in your React application.


    Remember that this is a simplified example, and in a real-world application, you would likely integrate with an authentication system or API to fetch and manage user roles. Implementing role-based permissions can help you build more secure and tailored experiences for your users.


    Check our video guide for better in depth understanding


    Our U).