60 lines
5.0 KiB
Markdown
60 lines
5.0 KiB
Markdown
# SEC-03 — Les WebSockets acceptent des sessions révoquées ou désactivées
|
||
|
||
**Gravité historique : Moyenne.** Classification : CWE-287.
|
||
|
||
**État au 14 septembre 2026 :** Corrigé dans le code suivi : stratégie commune vérifiant type access, utilisateur actif et version de credentials. Les messages et les émissions sortantes réauthentifient la connexion. Un changement de mot de passe est également couvert par SEC-08.
|
||
|
||
## Executive Summary
|
||
|
||
Le détenteur d'un JWT encore signé et non expiré tente de rejoindre le canal Socket.IO de notifications après désactivation du compte, ou réemploie un refresh token révoqué pour le renouvellement HTTP. Il possède déjà ce jeton : ce n'est pas une falsification de signature.
|
||
|
||
Cette fiche repose sur la relecture du code historique accessible et du correctif courant, ainsi que des preuves documentées lors des passes précédentes. Elle ne constate aucun incident réel. La plus ancienne version ici vérifiée est le snapshot `8446f87` ; les corrections historiques figurent dans `c09b8be`. Aucun tag local ni version déployée n'a permis d'établir une première release vulnérable ou corrigée. Voir [METHODOLOGIE.md](../METHODOLOGIE.md).
|
||
|
||
## Background
|
||
|
||
Un jeton peut être signé correctement tout en représentant un type de session inadapté ou un compte devenu inactif. L’authentification du transport doit rester cohérente avec celle des requêtes HTTP.
|
||
|
||
## Vulnerability Details
|
||
|
||
L'ancien `NotificationsGateway.handleConnection` se limite à `jwtService.verifyAsync(token)`, extrait `payload.sub` et rejoint la salle de cet utilisateur. La clé de signature est partagée avec les jetons HTTP. Le gateway ne requiert pas le type `access`, ne consulte pas le compte actif et ne réutilise pas la stratégie JWT HTTP. Il transmet le compteur puis les notifications récentes. Une connexion déjà ouverte ne réévalue pas non plus l'expiration avant chaque utilisation. La validité cryptographique d'un JWT était confondue avec le droit actuel d'utiliser cette surface.
|
||
|
||
Extrait historique vérifié, `apps/backend/src/application/gateways/notifications.gateway.ts`, lignes 60–61 du snapshot préaudit :
|
||
|
||
```typescript
|
||
const payload = await this.jwtService.verifyAsync(token);
|
||
const userId = payload.sub;
|
||
```
|
||
|
||
Les numéros ci-dessus décrivent le snapshot ancien ; les liens suivants ouvrent les fichiers courants, où les lignes peuvent avoir changé.
|
||
|
||
Sources à examiner ensemble :
|
||
|
||
- [apps/backend/src/application/gateways/notifications.gateway.ts](../../apps/backend/src/application/gateways/notifications.gateway.ts)
|
||
- [apps/backend/src/application/notifications/notifications.module.ts](../../apps/backend/src/application/notifications/notifications.module.ts)
|
||
- [apps/backend/src/application/auth/auth.service.ts](../../apps/backend/src/application/auth/auth.service.ts)
|
||
- [apps/backend/src/application/auth/jwt.strategy.ts](../../apps/backend/src/application/auth/jwt.strategy.ts)
|
||
|
||
## Exploitability Analysis
|
||
|
||
La frontière démontrée concerne les notifications, leurs messages et métadonnées. Elle ne prouve pas une prise de contrôle générale des routes REST. La signature et la date d'expiration restent vérifiées à la connexion initiale. La révocation d'un refresh token à la déconnexion ne signifie pas qu'un access token valide était lui aussi révoqué ; ne pas confondre ces politiques.
|
||
|
||
Le code applicatif établit le chemin décrit, mais ne renseigne pas les protections effectives d'un déploiement donné, sa version en ligne ou les accès déjà exercés par un attaquant. La gravité ci-dessus est celle du mécanisme vulnérable avant correction ; elle n'est pas un score de risque résiduel calculé pour la production.
|
||
|
||
## Proof of Concept
|
||
|
||
Tests de non-régression existants, inspectables dans le dépôt :
|
||
|
||
- [apps/backend/src/application/gateways/notifications.gateway.spec.ts](../../apps/backend/src/application/gateways/notifications.gateway.spec.ts)
|
||
|
||
Ils testent les refus et les usages autorisés avec des données locales. Ils ne prouvent pas qu'une ancienne exploitation a eu lieu en production. Les commandes et résultats consolidés sont dans [VALIDATION.md](../VALIDATION.md) ; aucun nouvel exploit n'a été exécuté pendant la rédaction.
|
||
|
||
## Remediation
|
||
|
||
Corrigé dans le code suivi : stratégie commune vérifiant type access, utilisateur actif et version de credentials. Les messages et les émissions sortantes réauthentifient la connexion. Un changement de mot de passe est également couvert par SEC-08.
|
||
|
||
Pour solder le constat en exploitation, vérifier le comportement sur la version effectivement déployée et conserver les contrôles légitimes décrits. La présente passe ajoute uniquement de la documentation ; les correctifs mentionnés existaient avant sa rédaction.
|
||
|
||
## Summary
|
||
|
||
Les WebSockets acceptent des sessions révoquées ou désactivées est un constat historique de l'audit, à lire avec son état courant ci-dessus. La preuve porte sur le mécanisme et les contrôles cités ; elle ne constitue ni une attestation d'exploitation réelle ni une certification exhaustive du projet.
|