npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@un-dev-suisse/nestjs-permissions

v1.1.2

Published

NestJS Permissions Service - A simple permissions service for NestJS applications

Downloads

44

Readme

@un-dev-suisse/nestjs-permissions

Un service de permissions robuste pour les applications NestJS avec gestion d'erreurs avancée.

Installation

npm install @un-dev-suisse/nestjs-permissions

or

pnpm install @un-dev-suisse/nestjs-permissions

Utilisation

1. Importer le module

import { Module } from '@nestjs/common';
import { PermissionsModule } from '@un-dev-suisse/nestjs-permissions';

@Module({
  imports: [PermissionsModule],
})
export class AppModule {}

2. Utiliser le service

import { Injectable } from '@nestjs/common';
import { 
  PermissionCheckerService, 
  UserPermissions,
  UnsupportedHttpMethodException,
  InvalidPermissionFormatException,
  InsufficientPermissionException
} from '@un-dev-suisse/nestjs-permissions';

@Injectable()
export class MyService {
  constructor(private readonly permissionService: PermissionCheckerService) {}

  async checkUserAccess(userPermissions: UserPermissions, resource: string) {
    try {
      // Vérifier une permission spécifique
      const hasAccess = this.permissionService.checkPermission(
        userPermissions, 
        `${resource}:read`
      );
      
      if (!hasAccess) {
        throw new InsufficientPermissionException(`${resource}:read`);
      }
      
      return true;
    } catch (error) {
      if (error instanceof InvalidPermissionFormatException) {
        console.error('Format de permission invalide:', error.message);
      } else if (error instanceof InsufficientPermissionException) {
        console.error('Permission insuffisante:', error.message);
      }
      throw error;
    }
  }

  async checkMultiplePermissions(userPermissions: UserPermissions) {
    const requiredPermissions = [
      'users:read',
      'users:create',
      'posts:read'
    ];

    try {
      // Vérifier toutes les permissions
      const hasAllPermissions = this.permissionService.checkMultiplePermissions(
        userPermissions,
        requiredPermissions
      );

      // Vérifier au moins une permission
      const hasAnyPermission = this.permissionService.checkAnyPermission(
        userPermissions,
        ['admin:all', 'moderator:read']
      );

      return { hasAllPermissions, hasAnyPermission };
    } catch (error) {
      console.error('Erreur de vérification des permissions:', error.message);
      throw error;
    }
  }

  getPermissionFromHttpMethod(method: string) {
    try {
      return this.permissionService.getPermissionFromMethod(method);
    } catch (error) {
      if (error instanceof UnsupportedHttpMethodException) {
        console.error('Méthode HTTP non supportée:', error.message);
      }
      throw error;
    }
  }
}

Gestion des exceptions

Le service fournit des exceptions spécifiques pour différents cas d'erreur. Toutes les exceptions sont utilisées directement avec leurs constructeurs :

Utilisation directe des exceptions

// ✅ Correct - Utilisation directe
throw new InvalidPermissionFormatException('users:invalid');
throw new InsufficientPermissionException('admin:all');
throw new UnsupportedHttpMethodException('INVALID');

// ❌ Incorrect - Pas de classe utilitaire
// throw PermissionExceptions.invalidFormat('users:invalid');

Exceptions disponibles

  • UnsupportedHttpMethodException : Méthode HTTP non supportée
  • InvalidPermissionFormatException : Format de permission invalide
  • MissingPermissionComponentException : Ressource ou action manquante
  • InvalidPermissionActionException : Action de permission invalide
  • InvalidUserPermissionsException : Permissions utilisateur invalides
  • InsufficientPermissionException : Permission insuffisante
  • ResourcePermissionNotFoundException : Ressource non trouvée
  • DefaultPermissionNotConfiguredException : Permissions par défaut non configurées
  • InvalidPermissionMaskException : Masque de permission invalide
  • EmptyPermissionListException : Liste de permissions vide

Exemples d'utilisation des exceptions

import { 
  UnsupportedHttpMethodException,
  InvalidPermissionFormatException,
  MissingPermissionComponentException,
  InvalidPermissionActionException,
  InvalidUserPermissionsException,
  InsufficientPermissionException,
  EmptyPermissionListException
} from '@un-dev-suisse/nestjs-permissions';

// Validation des méthodes HTTP
try {
  const permission = service.getPermissionFromMethod('INVALID');
} catch (error) {
  if (error instanceof UnsupportedHttpMethodException) {
    console.error('Méthode non supportée:', error.message);
  }
}

// Validation des formats de permission
try {
  const hasAccess = service.checkPermission(permissions, 'invalid-format');
} catch (error) {
  if (error instanceof InvalidPermissionFormatException) {
    console.error('Format invalide:', error.message);
  }
}

// Validation des composants manquants
try {
  const hasAccess = service.checkPermission(permissions, 'users:');
} catch (error) {
  if (error instanceof MissingPermissionComponentException) {
    console.error('Composant manquant:', error.message);
  }
}

// Validation des actions invalides
try {
  const hasAccess = service.checkPermission(permissions, 'users:invalid');
} catch (error) {
  if (error instanceof InvalidPermissionActionException) {
    console.error('Action invalide:', error.message);
  }
}

// Validation des permissions utilisateur
try {
  const hasAccess = service.checkPermission(null, 'users:read');
} catch (error) {
  if (error instanceof InvalidUserPermissionsException) {
    console.error('Permissions invalides:', error.message);
  }
}

// Gestion des permissions insuffisantes
try {
  const hasAccess = service.checkPermission(permissions, 'admin:all');
  if (!hasAccess) {
    throw new InsufficientPermissionException('admin:all');
  }
} catch (error) {
  if (error instanceof InsufficientPermissionException) {
    console.error('Accès refusé:', error.message);
  }
}

// Validation des listes vides
try {
  const hasAccess = service.checkMultiplePermissions(permissions, []);
} catch (error) {
  if (error instanceof EmptyPermissionListException) {
    console.error('Liste vide:', error.message);
  }
}

Exemple de gestion d'erreurs

import { 
  PermissionCheckerService,
  InvalidPermissionFormatException,
  InsufficientPermissionException,
  InvalidUserPermissionsException,
  UnsupportedHttpMethodException
} from '@un-dev-suisse/nestjs-permissions';

@Injectable()
export class MyController {
  constructor(private readonly permissionService: PermissionCheckerService) {}

  @Get()
  async getData(@Req() request: Request) {
    try {
      const userPermissions = request.user?.permissions;
      
      if (!userPermissions) {
        throw new InvalidUserPermissionsException();
      }

      const hasAccess = this.permissionService.checkPermission(
        userPermissions,
        'data:read'
      );

      if (!hasAccess) {
        throw new InsufficientPermissionException('data:read');
      }

      return { message: 'Accès autorisé' };
    } catch (error) {
      if (error instanceof InvalidUserPermissionsException) {
        throw new BadRequestException('Permissions utilisateur invalides');
      } else if (error instanceof InvalidPermissionFormatException) {
        throw new BadRequestException('Format de permission invalide');
      } else if (error instanceof InsufficientPermissionException) {
        throw new ForbiddenException('Accès refusé');
      }
      throw error;
    }
  }

  @Post()
  async createData(@Req() request: Request, @Body() data: any) {
    try {
      const userPermissions = request.user?.permissions;
      
      if (!userPermissions) {
        throw new InvalidUserPermissionsException();
      }

      // Convertir la méthode HTTP en permission
      const permissionType = this.permissionService.getPermissionFromMethod('POST');
      
      const hasAccess = this.permissionService.checkPermission(
        userPermissions,
        `data:${permissionType}`
      );

      if (!hasAccess) {
        throw new InsufficientPermissionException(`data:${permissionType}`);
      }

      return { message: 'Données créées' };
    } catch (error) {
      if (error instanceof UnsupportedHttpMethodException) {
        throw new BadRequestException('Méthode HTTP non supportée');
      } else if (error instanceof InvalidUserPermissionsException) {
        throw new BadRequestException('Permissions utilisateur invalides');
      } else if (error instanceof InsufficientPermissionException) {
        throw new ForbiddenException('Accès refusé');
      }
      throw error;
    }
  }
}

Format des permissions

Les permissions suivent le format : "ressource:action"

Actions supportées

  • create : Création de ressources
  • read : Lecture de ressources
  • update : Modification de ressources
  • delete : Suppression de ressources
  • all : Toutes les actions

Exemples

  • "users:read" : Permission de lecture des utilisateurs
  • "posts:create" : Permission de création d'articles
  • "admin:all" : Toutes les permissions d'administration

Masques de permissions

Le système utilise des masques binaires pour les permissions :

const PERMISSION_MASKS = {
  CREATE: 0b1000, // 8
  READ: 0b0100,   // 4
  UPDATE: 0b0010, // 2
  DELETE: 0b0001, // 1
  ALL: 0b1111,    // 15
};

Avantages de l'utilisation directe des exceptions

Simplicité

  • Code plus direct sans couche d'abstraction supplémentaire
  • Pas besoin de mémoriser des méthodes statiques

Performance

  • Pas d'appel de méthode statique supplémentaire
  • Construction directe des exceptions

🎯 Flexibilité

  • Possibilité de personnaliser les messages d'erreur si nécessaire
  • Contrôle total sur la création des exceptions

📖 Lisibilité

  • Plus facile de voir quelle exception est levée
  • Code plus explicite et compréhensible

🛠️ Maintenabilité

  • Moins de code à maintenir
  • Pas de classe utilitaire à gérer

API

PermissionCheckerService

checkPermission(permissions: UserPermissions, permission: string): boolean

Vérifie si un utilisateur a une permission spécifique.

checkMultiplePermissions(permissions: UserPermissions, permissionList: string[]): boolean

Vérifie si un utilisateur a toutes les permissions d'une liste.

checkAnyPermission(permissions: UserPermissions, permissionList: string[]): boolean

Vérifie si un utilisateur a au moins une permission d'une liste.

getPermissionFromMethod(method: string): PermissionType

Convertit une méthode HTTP en type de permission.

Licence

MIT