Aller au contenu principal

39-2 Décoder le jeton pour utiliser son contenu

Dans l'en-tête du site, les informations de connexion proviennent de la propriété pseudo du localstorage et non des informations contenues dans le jeton.

Pour obtenir ces informations, il faut décoder le jeton.

Modifier le modèle utilisateur

Modifions le modèle utilisateur pour qu'il contienne les informations nécessaires en provenance du jeton. Dans mon cas, je ne retourne que l'identifiant, le courriel et le nom d'utilisateur.

src/app/models/utilisateur.model.ts
export interface Utilisateur {
id: number;
courriel: string;
nomUtilisateur: string;
}

Installer jwt-decode

La librairie jwt-decode peut nous aider à gérer tout ce qui a trait au traitement du jeton côté client. Entre autres, décoder le jeton et obtenir les informations qu'il contient. Sans cette librairie, il faudrait manuellement décortiquer les trois sections du jeton, convertir de base64 au format texte, extraire l'objet JSON du contenu, etc.

  1. Installez la librairie via npm
npm install jwt-decode

Décoder le jeton dans AuthService

La dernière étape consiste à décoder le jeton afin d'en récupérer son contenu. AuthService est déjà responsable de retourner un utilisateur via sa fonction obtenirUtilisateur(), alors modifions cette dernière pour qu'elle retourne l'utilisateur contenu dans le jeton.

  1. Créer un modèle idem à celui retourné du serveur, soit JwtPayload pour représenter le contenu du jeton.

    src/app/core/models/jwt-payload.ts
    export interface JwtPayload {
    sub: number;
    courriel: string;
    nomUtilisateur: string;
    }
  2. Décoder le jeton et retourner un utilisateur

    src/app/core/services/auth-service.ts
    obtenirUtilisateur(): Utilisateur | null {
    const token = localStorage.getItem('access_token');
    if(token){
    const jwtPayload = jwtDecode<JwtPayload>(token);
    if(jwtPayload){
    let utilisateur: Utilisateur = {
    id: jwtPayload.sub,
    courriel: jwtPayload.courriel,
    nomUtilisateur: jwtPayload.nomUtilisateur,
    }
    return utilisateur
    }
    }

    return null;
    }
    info

    jwtDecode<JwtPayload>(token) décode le jeton dans le localstorage et retourne son contenu sous la forme de notre modèle JwtPayload.

  3. Vérifier si le jeton est expiré. Il faut en effet vérifier si le jeton n'est plus valide. Pour cela, créer une fonction tokenIsExpired.

    src/app/core/services/auth-service.ts
      private tokenIsExpired(token: string) {
    try {
    const decoded: any = jwtDecode(token);

    if (!decoded.exp) {
    return false; // Pas de date d'expiration, donc pas expiré
    }

    // exp est en secondes, Date.now() en millisecondes
    const currentTime = Date.now() / 1000;

    return decoded.exp < currentTime;
    } catch (error) {
    return false; // Si le jeton est invalide, le traiter comme expiré
    }
    }
  4. Tenir compte de la date d'expiration dans obtenirUtilisateur()

    obtenirUtilisateur(): Utilisateur | null {
    const token = localStorage.getItem('access_token');
    if(token && !this.tokenIsExpired(token)) {
    try {

    //...
  5. On peut en profiter d'ailleurs pour modifier la fonction estConnecte() permettant de vérifier si un utilisateur est connecté à l'application ou non.

    src/app/services/auth.service.ts
    estConnecte() {
    return this.obtenirUtilisateur() !== null
    }
    info

    La fonction obtenir utilisateur vérifie l'expiration du jeton, donc nous avons seulement à vérifier si la fonction ne retourne PAS null.

Afficher le nom d'utilisateur ou autre info pertinente

Cela nous permet maintenant d'utiliser le même principe que précédemment afin de récupérer les informations de l'utilisateur et les afficher.

Par exemple, pour afficher le nom d'utilisateur plutôt que le pseudo dans la barre de navigation:

src/app/components/navbar.component.ts
<ul *ngIf="utilisateur" class="navbar-nav">
<li>Allô, {{utilisateur.nomUtilisateur}}!</li>
</ul>

Imgur