Some checks are pending
CI / Lint bridge (Biome) (push) Waiting to run
CI / Type-check bridge (push) Blocked by required conditions
CI / Tests unit bridge (push) Blocked by required conditions
CI / Tests integration bridge (push) Blocked by required conditions
CI / Security scan (push) Waiting to run
CI / Docker build + healthcheck (push) Blocked by required conditions
- Support JWT OIDC Authentik via jose + JWKS (cache 10min) - Lookup Personne via PersonneRepo.findByEmail + cache Redis 60s - Mapping groups Authentik + roles formation-hub vers scopes - Mode OIDC active uniquement si AUTHENTIK_ISSUER + JWKS_URI + AUDIENCE set - Service tokens brg_* inchanges, restent voie principale en local
62 lines
2 KiB
TypeScript
62 lines
2 KiB
TypeScript
import { describe, expect, it } from 'vitest';
|
|
import {
|
|
DEFAULT_ROLE_SCOPES,
|
|
computeOidcScopes,
|
|
parseGroupsScopesMap,
|
|
} from '../../src/middleware/scopes.js';
|
|
|
|
describe('parseGroupsScopesMap', () => {
|
|
it('retourne {} si vide', () => {
|
|
expect(parseGroupsScopesMap(undefined)).toEqual({});
|
|
expect(parseGroupsScopesMap('')).toEqual({});
|
|
});
|
|
|
|
it('parse un mapping valide', () => {
|
|
const map = parseGroupsScopesMap('{"g1":["a","b"],"g2":["c"]}');
|
|
expect(map).toEqual({ g1: ['a', 'b'], g2: ['c'] });
|
|
});
|
|
|
|
it('throw si JSON invalide', () => {
|
|
expect(() => parseGroupsScopesMap('{')).toThrow(/JSON/);
|
|
});
|
|
|
|
it('throw si pas un objet', () => {
|
|
expect(() => parseGroupsScopesMap('[1,2]')).toThrow(/objet/);
|
|
expect(() => parseGroupsScopesMap('"x"')).toThrow(/objet/);
|
|
});
|
|
|
|
it('throw si valeur pas array of strings', () => {
|
|
expect(() => parseGroupsScopesMap('{"g":[1]}')).toThrow();
|
|
expect(() => parseGroupsScopesMap('{"g":"x"}')).toThrow();
|
|
});
|
|
});
|
|
|
|
describe('computeOidcScopes', () => {
|
|
it('union groups + roles + dedup', () => {
|
|
const scopes = computeOidcScopes(['formation-hub-formateurs'], new Set(['formateur']), {
|
|
'formation-hub-formateurs': ['formation:read', 'admin:custom'],
|
|
});
|
|
expect(scopes).toContain('formation:read');
|
|
expect(scopes).toContain('admin:custom');
|
|
// Vient du DEFAULT_ROLE_SCOPES.formateur
|
|
expect(scopes).toContain('write:attributions');
|
|
});
|
|
|
|
it("group inconnu ignore (pas d'erreur)", () => {
|
|
const scopes = computeOidcScopes(['unknown-group'], new Set(), {});
|
|
expect(scopes).toEqual([]);
|
|
});
|
|
|
|
it('default mapping admin role -> admin:*', () => {
|
|
const scopes = computeOidcScopes([], new Set(['admin']), {});
|
|
expect(scopes).toContain('admin:*');
|
|
});
|
|
|
|
it('aucun group + aucun role = scopes vides', () => {
|
|
expect(computeOidcScopes([], new Set(), {})).toEqual([]);
|
|
});
|
|
|
|
it('DEFAULT_ROLE_SCOPES couvre les 5 roles', () => {
|
|
expect(Object.keys(DEFAULT_ROLE_SCOPES)).toHaveLength(5);
|
|
});
|
|
});
|