Retrieve user roles from core in Angular prior to implementing a guard

Hey, I'm facing an issue with my app.module setup. I have implemented lazy loading to load the core module and store roles in the core component. Everything works fine when I navigate from one page to another with the role guard applied. However, when I directly type the URL of a page with the role guard, it fails to load the roles. I tried using skipWhile but it didn't solve the issue. Any suggestions on how to resolve this? Thanks!

AppRoutingModule

  {
    path: '',
    children: [{
      path: '', loadChildren: () => import('./core/core.module').then(m => m.CoreModule)
    }]
  },

CoreRoutingModule

{
    path: '',
    component: CoreComponent,
    children: [
      {
        path: "test,
        loadChildren: () => import('@modules/test/test.module').then(m => m.TestModule),
        canActivate: [MyGuard]
    ......

CoreComponent

  ngOnInit(): void {
    this.authFacade.initAll();
    this.authFacade.loginCheck();
  }  

AuthGuard - only for test

canActivate(
    route: ActivatedRouteSnapshot,
    state: RouterStateSnapshot): Observable<boolean> {
    return this.authFacade.user$.pipe(
      skipWhile(user => user === undefined),
      take(1),
      map(user => {
        console.log(user);
        if (!user)
          return false;

        return true;
      })
    )
  }

Answer №1

It is possible that the issue arises due to the roles being loaded asynchronously within your CoreComponent, causing the guard to be evaluated before the roles are retrieved and stored.

You can attempt the following solution:

//CoreComponent
ngOnInit(): void {
  this.authFacade.initAll();
  this.authFacade.loginCheck();

  this.authFacade.rolesLoaded$.pipe(
// wait until roles are loaded
    filter(loaded => loaded), 
// only happens once
take(1) 
  ).subscribe(() => {
    // roles loaded
  });
}

and

//AuthGuard
canActivate(
  route: ActivatedRouteSnapshot,
  state: RouterStateSnapshot
): Observable<boolean> {
  return combineLatest([
    this.authFacade.user$,
 // something to track roles loading
    this.authFacade.rolesLoaded$
  ]).pipe(
    skipWhile(([user, rolesLoaded]) => user === undefined || !rolesLoaded),
    take(1),
    map(([user, rolesLoaded]) => {
      if (!user) {
        return false;
      }

      // check user's roles against necessary roles for the route
      // add logic here to determine if the user possesses the required roles

      return true;
    })
  );
}

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Tips on selecting data from an array to populate a mat-selection-list

When I receive a string like this from the API: 55,118,122,126,116,58,125,119,132. These are the ids that I need to work with in my Angular mat-selection-list. My goal is to initially select these values and update existing data before sending it back thro ...

Obtain the dimensions (width and height) of a collection of images using Angular and TypeScript

Currently, I am facing an issue with my image upload functionality. My goal is to retrieve the width and height of each image before uploading them. However, I've encountered a problem where my function only provides the dimensions for the first image ...

What is the best way to display suggested words from a given list of options?

Looking for a way to provide suggestions to users based on a list of words they enter in TypeScript while maintaining performance. How can this be achieved efficiently? ...

Tips for troubleshooting Angular 4 unit testing using jasmine and karma with simulated HTTP post requests

I have a service that I need to unit test in Angular 4 using TypeScript and Jasmine. The problem is with the http where it needs to perform a post request and get an identity in return, but for some reason, no data is being sent through. My goal is to ac ...

Implementing a SetTimeout Function in HTML

Is there a way to delay calling the mouseHoverTableRow() function until after hovering on tr for 3 seconds? I only want to call this function if the hover duration is at least 3 seconds, as it triggers an API request. How can I achieve this? <tr *ngF ...

Oops! Angular2 couldn't find a provider for HttpHandler

I have been working on implementing HttpCache through an interceptor. Below is the code snippet for caching-interceptor.service.ts: import { HttpRequest, HttpResponse, HttpInterceptor, HttpHandler, HttpEvent } from '@angular/common/http' import ...

Personalize the Ag-Grid Status Bar to your liking

Currently utilizing Ag-Grid Enterprise, Version 19 ("ag-grid-angular": "19.0.0", "ag-grid-community": "19.0.0", "ag-grid-enterprise": "19.0.0") in conjunction with Angular 4. There is a specific need to customize the status bar of the grid and add an add ...

The functionality of Angular router is disrupted when guards yield an Observable as their return value

My goal is to redirect users who are not logged in when they try to access protected routes, but I am facing an issue with redirection. The function that checks if the user is logged in returns an Observable. Below is the code snippet from my PrivateGuard ...

Vertical and horizontal tabs not functioning properly in Mat tabs

I successfully created a vertical material tab with the code below, but now I am looking to incorporate a horizontal tab inside the vertical tab. Attempting to do so using the code provided results in both tabs being displayed vertically. Below is my code ...

Utilizing Angular 8's Reactive Form to Transform Checkbox Event Output into a String Format

My form is reactive and includes a field called Status, which can have the values 'A' or 'I': this.form = this.formBuilder.group({ result_info: this.formBuilder.array([ this.getResultcontrols()]), stat ...

Exploring the location of unit testing within async-await in Angular applications

I have been working with Angular 9+ along with karma test runner and jasmine test framework for my unit tests. My focus is on unit testing only the app component which includes dependency injection: app.component.ts import { Component, EmbeddedViewRef } ...

SQL Exception: The value for the first parameter is not defined

I'm encountering an issue with a SqlError while trying to retrieve data from my database. It seems like the problem is within my fetchData function where I might not be passing the two parameters (startDate and endDate) correctly. The specific SqlErr ...

Sending an array of dates from Angular to Java - A quick guide

I'm facing an issue where Java is interpreting date attributes as null objects when I send an array of objects with date attributes from Angular to a Spring REST API. How can I ensure that the values are passed correctly? While researching, I came ac ...

Switching a parameter from a string to an object will cause Elasticsearch to be unable to properly index the new data structure

I have a collection of items stored in a Firebase database that I am using in conjunction with ElasticSearch for advanced queries. Recently, I had to update the structure of one of the items from a simple string, organizer: "some name", to a more complex ...

Receiving an error in Typescript when passing an object dynamically to a React component

Encountering a typescript error while attempting to pass dynamic values to a React component: Error message: Property 'title' does not exist on type 'string'.ts(2339) import { useTranslation } from "react-i18next"; import ...

When another page is refreshed, Angular routing redirects back to the home page

Within my application, there is a homepage that appears after the user logs in, along with some other pages. However, I've encountered an issue where when I navigate to one of these other pages and then refresh the page, it redirects me back to the ho ...

Having trouble getting code hints to function properly with the official TypeScript plugin on Sublime Text 3

I am experiencing issues with getting code hinting to work using the official TypeScript plugin for Sublime Text 3 on Mac OSX 10.10.5 with Sublime 3. Despite installing it in the packages directory, I am unable to see any code hints. In accordance with th ...

Issues with Cross-Origin Resource Sharing (CORS) have been identified on the latest versions of Android in Ionic Cordova. However, this problem does not

I am encountering an issue with my TypeScript Ionic code. It works well in browsers and some older mobile devices, but it fails to function on newer Android versions like 8+. I need assistance in resolving this problem. import { Injectable } from '@an ...

Angular2 - Error: The view has been destroyed and cannot be updated: detectChanges

My application keeps encountering this persistent error: extensions::uncaught_exception_handler:8 Error in event handler for runtime.onMessage: Attempt to use a destroyed view: detectChanges at ViewDestroyedException.BaseException [as constructor] (chrome ...

The template is displaying the string as "[object Object]"

I've implemented code in my ngOnInit function to fetch the translation for a specific text. The following function is being called: async getEmailTranslation() { const email$ = this.translate.get('SUPPORT_TRANSLATE.EMAIL'); this.emai ...