angularrbacauth-guard

How to dynamically add authguard based on a role in Angular?


In my Angular app , Admin user creates other users and roles.

While creating the roles , Admin can add permissions to it . i.e what menu items can this type of user role can access ?

The challenging part is that , I need to specify auth guard to the routes .

For example ,

Supervisor role type can access - Menu item 1 Menu Item 2 , Menu item 4, Menu item 5

Engineer role type can access - Menu Item 3 , Menu Item 6

All the menu items are separate modules .

When an Engineer tries to access menu item 1 via URL , he should be redirected .

Please help me on this . Any high level approach is fine for me . Thanks in advance

enter image description here

enter image description here


Solution

  • If you want a clean way to manage permissions based on roles, i suggest that you use ngx-permissions

    npm i ngx-permissions
    

    NgxPermissionsGuard implements CanLoad interface, and you can use it like this

     {
      path: 'lazy',
      data: {
       permissions: {
         only: 'SUPERVISOR',
       }
      },
      canLoad: [NgxPermissionsGuard],
      loadChildren: 'app/lazy-module/lazy-module.module#LazyModule'
    },
    

    if you want to grant access to something except Supervisor you can use except

    data: {
       permissions: {
         except: 'SUPERVISOR',
       }
    },
    

    Both possibilities is possible too

     data: {
      permissions: {
        only: ['ADMIN', 'MODERATOR'],
        except: ['SUPERVISOR']
      }
    }
    

    More details here

    if you don't want to use ngx-permission you can create a service

    @Injectable()
    export class AuthGuardService implements CanLoad {
     constructor(private router: Router) {}
    
     canLoad(route: Route): boolean {
    
     let url = route.path; //get url here, example menu1
     // get permissions array here from a service or localstorage
     if(permissions.indexOf(url) !== -1 ) { //means it exist
       return true
     }
     return false; 
     }
    } 
    

    and add it in your 3 routes

     {path: "menu1", loadChildren:'./main/menu.module#Menu1Module', canLoad:[AuthGuardService]}
     ...