简体   繁体   中英

Angular and Laravel how to manage user permissions on the client side

The code snippet below is an Angular service to authenticate a user using Laravel Sanctum:

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Observable } from 'rxjs';
import { map } from 'rxjs/operators';
import { Router } from '@angular/router';

@Injectable({
  providedIn: 'root'
})
export class AuthService {

  private baseURL = "http://localhost:8000/api";

  constructor(private http: HttpClient,public router: Router) { }

  login(username: string, password: string): Observable<boolean> {
    return this.http.post<{token: string}>(this.baseURL+'/login', {email: username, password: password})
      .pipe(
        map(result => {
          localStorage.setItem('access_token', result.token);
          return true;
        })
      );
  }

  getToken() {
    return localStorage.getItem('access_token');
  }

  logout() {
    let removeToken = localStorage.removeItem('access_token');

    if (removeToken == null) {
      this.router.navigate(['login']);
    }
  }

  public get isLoggedIn(): boolean {
    //TODO: Check token expiry and other security checks
    return (localStorage.getItem('access_token') !== null);
  }
}

My question is, if am using spatie permissions or Laravel Gates for authorization how can I store them on the frontend so that I can be able to show or hide menus based on what user is allowed to access?

DISCLAIMER: I'm used to developing applications using blade templates. First time I'm switching to SPA.

After authentication (successful login) you can manage your authorization (access right) via:

If the component is accociated with a route, your need to protect the routes. In this case use:

  • Route Guards to protect accessing components under particular URL tree from unauthrized users.

If the component is embedded in the view (like a button or section of a view under open or protected route) then you can:

  • Use property binding with [hidden]="condition" html property if you want to just hide an element from the UI but not from the DOM.
  • Use built-in Angular directive *ngIf="condition" if you want to hide or show an element in the UI and the DOM based on certain condition.

Say you want to grant access to item A in menu only to Super_Admin users. You can do this:

<ng-container *ngIf="rolePropertyFromAPI === 'Super_Admin'">Item A</ng-container>  

This is a big topic where you can find so much on-line. Check medium and Angular In-depth blog posts to know how to implement such strategies. First step is of course the DOCS here

For storing access credits like the 'Super_Admin' above it is a pretty straightforward. You have three options here:

The optimal one from easy of access and durability is localStorage API. However it is not that safe. It does the job for you though.

The most advanced and tricky one is to store the credentials in the application state using Observables for example.

With localStorage:

1- you accesss your API endpoint response

2- set the property in the browser storage

localStorage.setItem('Super_Admin', JSON.stringify(valueFromBackendEnd))

3- get the value by the key stored with

localStorage.getItem('Super_Admin')

4- clear the storage.

localStorage.removeItem('Super_Admin')

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM