Les erreurs liées à OpenID et à l'application e-CPS
Pro Santé Connect passe par le mécanisme de retour d'erreurs d'un fournisseur d'identité openid connect tel que décrit dans la norme (https://openid.net/specs/openid-connect-core-1_0.html#AuthError)
Authentication endpoint
C’est le point d’extrémité sur lequel l’user-agent (en général un navigateur Web) de l’utilisateur final est redirigé, pour lui permettre de s’identifier et d’accorder des autorisations à l’application cliente.
Dans le cas du flux d’autorisation avec code (Authorization code flow), le contrôleur Authorize redirige l’user-agent sur le point d’extrémité Token avec un code d’autorisation.
Réponse | Titre de l'erreur | Détail de l'erreur | Explication |
302 | login required | The user must login | Le jeton d’accès n’existe pas ou n’est plus valide. Cette réponse n’apparait que si login=’none’ car, dans les autres cas, le serveur OAuthSD prend à sa charge le dialogue de connexion. Cette erreur pourra apparaître en cas d’échecs successifs. |
302 | interaction_required | The user must grant access to your application | Le serveur a déterminé que des scopes doivent être approuvés par l’utilisateur final. Il y a peu de chance que cette erreur apparaisse avec OAuthSD, car la situation est gérée au niveau du contrôleur Authorize qui prend à sa charge le formulaire d’acceptation. |
400 | invalid_grant | incorrect redirect_uri | L'URL de redirection ne correspond pas à celle enregistrée du service |
400 | consent_required | The user denied access to your application | L’utilisateur final a explicitement refusé la demande d’autorisation qui lui a été présentée. |
400 | invalid_client | No client id supplied | Le paramètre client_id n'a pas été fourni. |
400 | invalid_client | The client id supplied is invalid | Le paramètre client_id doit être identique à ce qui a été inscrit pour l’application. |
400 | invalid_uri | The redirect URI must not contain a fragment | |
400 | invalid_uri | No redirect URI was supplied or stored | |
400 | invalid_uri | A redirect URI must be supplied when multiple redirect URIs are registered | |
400 | redirect_uri_mismatch | The redirect URI provided is missing or does not match | Le paramètre redirect_uri doit être identique à ce qui a été inscrit pour l’application. |
400 | invalid_uri | The redirect URI must not contain a fragment | |
400 | invalid_request | invalid user | L'identifiant utilisateur renseigné est inconnu dans l'environnement appelé. |
400 | invalid_request | invalid_binding_message | Le binding message envoyé ne respecte pas le format attendu |
401 | invalid_client | Invalid client credentials | Les informations d'authentification fournies par le FS sont erronées |
401 | unauthorized_client | Invalid client secret | Le secret envoyé par le FS est erroné |
401 | not_allowed | L’utilisateur final a fourni un identifiant (e-mail ou pseudo) mal formé. | |
401 | malformed_identifier | ||
403 | consent_required | The user denied access to your application | L’utilisateur a refusé son accord ou a abandonné l’authentification. |
Si le serveur retourne une erreur 401, il est de la responsabilité de l’application cliente de présenter un message d’erreur.
Token endpoint
Pour obtenir les jetons, une application cliente s’adresse au point d’extrémité token avec le code obtenu dans la phase d’autorisation. Dans le cadre du protocole OpenID Connect, l’appel au contrôleur Token suit la demande d’authentification.
La demande ne doit être effectuée que par la méthode POST.
Réponse | Titre de l'erreur | Détail de l'erreur | Explication |
405 | invalid_request | The request method must be POST when requesting an access token | La méthode de la demande doit être POST lorsque vous demandez un jeton d’accès. Notez que le Header contient ’Allow : POST’ |
400 | invalid_request | The grant type was not specified in the request | Le type d’autorisation n’a pas été spécifié dans la demande |
400 | unsupported_grant_type | Grant type "X" not supported | Le Type d’autorisation "X" n’est pas supporté. |
400 | invalid_grant |
Code not valid |
Le code d’autorisation n’existe pas ou est invalide pour le client ou a expiré. Cette situation peut résulter du fait que le code a déjà été utilisé pour une demande de jeton. |
400 |
invalid_grant |
Invalid Auth Req ID |
Le JSON fournit en auth_req_id est erroné ou a expiré |
400 |
authorization_pending |
The authorization request is still pending as the end-user hasn't yet been authenticated |
L'utilisateur n'a pas encore donné son consentement à l'authentification mobile |
400 | unauthorized_client | The grant type is unauthorized for this client_id | Le type d’autorisation n’est pas autorisé pour ce client_id |
400 | invalid_scope | The scope requested is invalid for this request | La portée d’autorisation demandée est invalide pour cette demande |
400 | invalid_scope | The scope requested is invalid for this client | La portée d’autorisation demandée est invalide pour ce client |
400 | invalid_scope | An unsupported scope was requested | La portée d’autorisation demandée n’est pas supportée |
400 |
access_denied |
not authorized |
Pour les connexions CIBA : l'utilisateur n'a pas donné son consentement à l'authentification mobile |
404 |
Could not find resource for full path |
L'adresse du endpoint est erronée |
Application e-CPS
Le tableau ci-dessous référence les différentes erreurs pouvant être remontées par l'application e-CPS à son utilisateur.
Etape | Erreur | Signification et résolution |
Accueil - e-CPS non activée | 1.1.x | Une erreur s'est produite lors de l'activation de votre e-CPS. Vérifiez que votre application est à jour et recommencez la séquence d'activation. Si le problème persiste veuillez contacter le support e-CPS. |
CGU | 2.1.x | Une erreur s'est produite au niveau des CGU. Assurez vous d'avoir accepté les CGU. Assurez-vous d'avoir l'application e-CPS à jour. Si c'est le cas désinstallez et réinstallez l'application e-CPS. |
Recherche par identifiant | 4.1.x | Une erreur s'est produite lors de la recherche de votre identifiant. Vérifiez que ce dernier est correct et assurez vous d'avoir l'application e-CPS à jour. Si le problème persiste contactez le support e-CPS. |
Séquence d'activation | 4.2.x | Une erreur technique s'est produite. Désinstallez puis réinstallez votre application e-CPS et assurez vous d'avoir un signal réseau correct. Si le problème persiste contactez le support e-CPS. |
Recherche par coordonnées | 5.1.x | Une erreur technique s'est produite lors de la récupération de vos coordonnées. Vérifiez qu'elles sont bien présentes et valides dans l'annuaire santé. Assurez vous d'avoir un signal réseau correct. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Scan du QR Code | 6.0.x | Une erreur technique s'est produite lors du scan de QR Code. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Séquence d'activation | 6.1.x | Le QR code a expiré. Procédez de nouveau à la séquence d'activation de votre e-CPS. Si le problème persiste contactez le support e-CPS. |
6.2.x | Une erreur technique s'est produite lors de l'activatin de votre e-CPS. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. | |
6.3.x | Une erreur technique s'est produite lors de la suppression de votre e-CPS. Assurez vous d'avoir un signal réseau correct. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. | |
6.4.x | Une erreur technique s'est produite lors de l'activation de votre e-CPS. Assurez vous d'avoir un signal réseau correct Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. | |
Code OTP | 9.1.x | Une erreur technique s'est produite lors de l'envoi du SMS de vérification. Assurez vous d'avoir un signal réseau correct et procédez de nouveau à la séquence d'activation de votre e-CPS. Si le problème persiste contactez le support e-CPS. |
10.1.x | Une erreur technique s'est produite lors de la saisie du code de vérification. Assurez vous d'avoir un signal réseau correct et procédez de nouveau à la séquence d'activation de votre e-CPS. Si le problème persiste contactez le support e-CPS. | |
Mot de passe e-CPS | 11.1.x | Une erreur technique s'est produite lors de la création votre mot de passe. Procédez de nouveau à la séquence d'activation de votre e-CPS. Si le problème persiste contactez le support e-CPS. |
11.2.x | Une erreur technique s'est produite lors de la modification votre mot de passe. Assurez vous d'avoir un signal réseau correct et procédez de nouveau à la modification de votre mot de passe. Si le problème persiste contactez le support e-CPS. | |
11.3.x | Une erreur technique s'est produite lors de la modification votre mot de passe. Assurez vous d'avoir l'application e-CPS à jour. Si le problème persiste contactez le support e-CPS. | |
Suppression e-CPS | 12.1.x | Une erreur technique s'est produite lors de la suppression de votre e-CPS. Assurez vous d'avoir l'application e-CPS à jour. Si le problème persiste contactez le support e-CPS. |
Activation par carte | 12.3.x | Une erreur technique s'est produite lors de la lecture de votre carte. Vérifiez qu'elle est bien insérée et détectée par votre poste. Si le problème persiste contactez le support e-CPS. |
Services serveur | 13.x | Une erreur technique s'est produite. Assurez vous d'avoir un signal réseau correct et l'application e-CPS à jour. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Gestion des sessions | 14.x | Une erreur technique s'est produite. Assurez vous d'avoir un signal réseau correct et l'application e-CPS à jour. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Authentification | 15.x | Une erreur réseau s'est produite à l'une des étapes de l'authentification. Assurez vous d'avoir un signal réseau correct et recommencez l'opération. Si le problème persiste contactez le support e-CPS. |
Mot de passe e-CPS | 16.x | Une erreur technique s'est produite lors de la procédure "Mot de passe oublié". Assurez vous d'avoir un signal réseau correct et l'application e-CPS à jour. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Gestion des sessions | 17.x | Une erreur technique s'est produite lors de la déconnexion de l'ensemble de vos sessions. Assurez vous d'avoir un signal réseau correct et l'application e-CPS à jour. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Centre de notifications | 18.x | Le centre de notification a connu une erreur. Assurez vous d'avoir un signal réseau correct et l'application e-CPS à jour. Désinstallez puis réinstallez votre application e-CPS. Si le problème persiste contactez le support e-CPS. |
Débug des traces du navigateur
Phase 1 : Lancement de l’authentification OIDC auprès de Pro Santé Connect
La première phase est le déclenchement de la requête OIDC à proprement parler.
Préalablement à l’authentification, le FS envoie sa requête OIDC afin de demander une authentification.
Requête 1 : le FS redirige vers la page d’authentification de Pro Santé Connect
Ici, le FS TryECPS renvoie vers Pro Santé Connect en retournant au navigateur de l’utilisateur un code HTTP 302 qui indique au navigateur d’effectuer une redirection vers une autre adresse. En l’occurrence, c’est lorsque l’on clique sur le bouton « Se Connecter » sur TryEcps que l’appel est effectué et que le serveur retourne un 302.
A noter que selon le choix des développeurs des FS, la redirection peut également être effectuée via du JavaScript.
Ici, l’argument « Location » dans la réponse effectuée par le FS contient l’adresse vers laquelle se diriger, c’est ici que passent les arguments OIDC (response_type, client_id, state, redirect_uri, acr_values, …) étant donné que l’on est passé par un 302.
Requête 2 : Premier appel sur le portail d’authentification PSC et redirection vers un autre endpoint PSC
Le navigateur se rend sur la page indiquée, ici le portail Pro Santé Connect.
A partir de là, le FS n’est plus en charge de l’authentification.
Pour des raisons historiques de développement, ce premier endpoint « /auth » redirige via un 301 vers un second endpoint « /auth/ »
Requête 3 : Appel OIDC
Il s’agit de la requête d’authentification OIDC effective adressée à Pro Santé Connect, telle que décrite dans la RFC (https://openid.net/specs/openid-connect-core-1_0.html#AuthRequest).
Le code 200 indique que la requête est bien formulée, et qu’aucun argument n’est manquant.
La requête est adressée en GET dans le cas de PSC, on y retrouve les arguments OIDC obligatoires.
Phase 2 : Redirection sur la mire d'authentification PSC
Récupération des fichiers de configuration
Lors du chargement de la page d’authentification de Pro Santé Connect, 4 fichiers Javascripts sont appelés.
Parmi eux, le script « polyfills.XXXXX.js » déclenche la récupération de plusieurs fichiers JSON.
Ces appels sont systématiques, ne dépendent pas de l’utilisateur ou du contexte d’authentification, ils sont simplement faits pour récupérer certains éléments de configuration.
Ces fichiers sont au nombre de 3 :
- config.json : gère les messages affichés en pop-in, le nom affiché de l’application, les liens présentés sur la page, la configuration DataDog
- api.json : décrit l’ensemble des appels rendus disponibles via API, des différents micro-services, avec la liste des endpoints et de la méthode HTTP pour chaque phase du processus d’authentification
- fr_FR.json : contient les textes à afficher en langue française.
Tentative d’authentification via SSO
Le portail Pro Santé Connect rend possible l’authentification par SSO.
Cela est géré via un cookie, valable 4h (dans la configuration actuelle).
Lorsque l’on arrive sur le portail d’authentification de PSC, un script JS déclenche un appel POST vers le endpoint « /api/esante-authentication/authenticate/sso ».
Cet appel permet de vérifier si l’utilisateur dispose ou non d’un cookie (le « WALLET_ID »), ce cookie étant rendu disponible pour le endpoint en question.
Le WALLET_ID est au format JWT, et est renvoyé par le serveur Pro Santé Connect après une authentification réussie, que ce soit par CPS ou via e-CPS.
Cas passant (authentification réussie par SSO)
Si l’utilisateur dispose d’un WALLET_ID, alors le serveur va vérifier sa signature, son horodatage etc.
Si le WALLET_ID est valide, alors le endpoint retourne un 200, avec un nouveau cookie mis à jour et l’utilisateur est authentifié de façon implicite (sans action de sa part).
Cas bloquant (authentification échouée par SSO)
Si l’utilisateur ne dispose pas de cookie WALLET_ID ou que celui-ci n’est pas valide (expiration notamment), alors le endpoint retourne un code 401 (Unauthorized), et l’utilisateur devra alors s’authentifier de façon active, via sa CPS ou sa e-CPS.
Etant donné que cette vérification est systématique, il est normal de voir, pour les authentifications réussies par CPS ou e-CPS, une requête « /sso » refusée.
Authentification par CPS
Récupération des certificats d'AC autorisées
Lors du chargement du portail d’authentification Pro Santé Connect (situé à l’adresse https://wallet.esw.esante.gouv.fr/), et afin de limiter les actions utilisateurs, un scripts JS (polyfills.XXXXXXXX.js, chargé avec la page) déclenche un appel HTTP HEAD (moins utilisé que GET ou POST) vers le endpoint https://wallet-secure.esw.esante.gouv.fr/certInfosAuth.
La méthode HTTP « HEAD » permet d’obtenir les en-têtes retournées par un appel « GET » ou « POST » sans effectuer de requêtes à proprement parler. Cela permet de se renseigner sur les en-têtes demandées sans multiplier les requêtes lourdes.
Dans notre cas, cet appel permet de tester si un certificat valide est présent dans le magasin de certificat utilisateur et d’indiquer au navigateur de se servir de ce certificat pour la suite des échanges avec le serveur.
Dans la négociation TLS sous-jacente (non visible dans la console développeur), ce endpoint demande une authentification client, et donne la liste des AC autorisées pour le certificat présenté par l’utilisateur.
Le navigateur détecte alors si des certificats utilisateurs correspondent à ce critère, et s’il en existe, alors le navigateur affiche la liste du/des certificat(s), et étant donné que la clé privée n’est pas stocké dans le navigateur, le navigateur interrogeant le middleware CPS pour la saisie du code PIN.
Cas passant (authentification réussie par CPx)
Lorsque l’on valide l’authentification (saisie du code PIN), on obtient un code 200, et on voit dans le journal le certificat de l’utilisateur en question.
En décodant le certificat renvoyé par le serveur dans le paramètre « X-Ssl-client-Cert », on voit logiquement qu’il s’agit du certificat client émis par l’IGC-Santé PERSONNES
Cet appel est effectué de façon automatique via le JavaScript, ce qui explique la pop-in qui apparaît sans action utilisateur lorsque la carte CPS est bien connectée au PC.
Cependant, si l’utilisateur ne valide pas l’authentification à ce moment-là, alors un deuxième appel HEAD exactement identique est effectué lors d’un clic sur le bouton « Se connecter avec la carte CPS ».
C’est ce qui explique que l’on a parfois 2 fois le même appel qui apparaît dans la stack trace, notamment lorsque la carte n’est pas insérée dès l’arrivée sur le portail d’authent.
Cas bloquant (authentification échouée par CPx)
Si l’utilisateur décline la première pop-in, ou que la CPS n’est pas dans le lecteur, on obtient également un code 200, mais le certificat client n’apparait pas.
Si l’on clique alors sur « Se Connecter avec la carte CPS » alors qu’elle n’est pas dans le lecteur, on obtient alors une erreur hors HTTP (d’où l’absence de code), et un script (main.XXXXXXXXX.js) redirige vers la page de diagCPS.
Appel d’authentification
L’appel effectif pour l’authentification est celui adressé vers « https://wallet-secure.esw.esante.gouv.fr/cert/api/esante-authentication/authenticate/card». Les appels précédents sont finalement « préparatoires » à cet appel.
A titre d’exemple, le script Python pour la sonde n’effectue que cet appel.
Il s’agit d’une requête POST contenant en argument tous les éléments de la requête OIDC, et pour laquelle l’authentification par certificat client est effectué (non visible dans la console).
En cas de requête réussie, alors on obtient un code 200, et un cookie WALLET_ID est retourné dans le header afin de permettre de se connecter plus tard via SSO.
Dans le retour du serveur à cette requête POST, on obtient, en cas de succès, un JSON indiquant la prochaine redirection à faire, avec en argument GET le code d’autorisation à adresser au FS.
Ce code d’autorisation une fois transmis, un script javascript récupère l’argument « redirectURI » de la réponse JSON et déclenche une redirection, permettant au FS de disposer du code d’autorisation, et de poursuivre le processus OIDC pour obtenir les jetons puis éventuellement le user_info.
Authentification e-CPS
Requête 1 : Déclenchement de la demande d’authentification par e-CPS
Lorsque l’on a saisi un identifiant existant au niveau du portail de connexion, dans l’onglet e-CPS, alors une requête POST est effectuée sur le endpoint https://wallet.esw.esante.gouv.fr/api/esante-authentication/request, avec les arguments OIDC correspondants.
Cas passant (authentification réussie par e-CPS)
Si la requête est formulée correctement et que l’utilisateur dont on a spécifié l’identifiant existe et possède une e-CPS activée, alors le processus d’authentification via e-CPS débute et on obtient une réponse 200.
Cas bloquant (authentification échouée par e-CPS)
Si aucune e-CPS n’est activée pour l’identifiant que l’on a renseigné (que l’utilisateur existe dans le RASS ou non), on obtient une réponse JSON
{"code": "BUSI-AUTHENT-9","message":"entity not found"} .
Une requête pour déclencher un processus d’activation est alors lancée par un script Javascript (https://wallet.esw.esante.gouv.fr/api/esante-manager/user/activation/info?natId=%identifiant_appelé% et selon que l’utilisateur existe ou non, on obtient un message d’erreur ou de succès
Requête 2 : Déclenchement web-socket
Une fois la demande d’authentification par e-CPS envoyée, le navigateur va demander la création d’une websocket avec le serveur afin d’être tenu au courant lors de la validation de la demande de connexion.
Dans la mesure où l’utilisateur dispose de 120 secondes pour valider sa connexion, ce système de websocket permet de prendre en compte le moment précis où l’utilisateur a validé sa connexion côté e-CPS.
Un websocket est un protocole différent d’HTTP, qui n’est pas synchrone (requête => réponse) mais asynchrone, ce qui permet au serveur de contacter le navigateur concerné. Cela permet d’éviter de devoir mettre en place un système de ping régulier du navigateur vers le serveur pour vérifier si la requête a été validée ou non.
Le premier appel (« https://wallet.esw.esante.gouv.fr/auth/ws/info?t=XXXXXXXXXXXXX ») sert donc à demander la création d’un socket.
On voit ensuite la séquence de message dans la console développeur.
Il est à noter que si la ligne « websocket » apparaît juste après « info ?t=XXXXX » dans la console, c’est car le premier message est envoyé à ce moment-là, cependant les échanges HTTP suivants ont techniquement lieu avant la fin de l’échange via la websocket.
Pour information, ces appels ne sont pas techniquement indispensables mais permettent de fluidifier l’expérience utilisateur en gérant la chronologie des échanges.
Requête 3 : Récupération config et code dynamique
L’appel suivant « config » sert à récupérer certaines variables concernant les modalités de l’authentification via e-CPS. Il sert surtout à gérer les transitions de comportement de la page utilisateur lors des MEP.
L’appel « messaging » en revanche, est indispensable car c’est cet appel qui permet d’obtenir le code dynamique, qui est ensuite affiché de façon claire sur la page grâce à du Javascript
Requête 4 : Finalisation
La dernière requête est déclenchée lorsque l’utilisateur a fourni une réponse d’authentification via sa e-CPS.
Lorsque l’utilisateur fournit sa réponse au niveau de son application, le serveur informe alors le navigateur via le websocket grâce à un message « wake up »
Le fichier Javascript « polyfills.XXXXXXX.js » déclenche alors l’appel « finalize », qui permet de tenter la validation de la demande d’authentification.
En se basant sur les cookies de session, le serveur identifie alors la demande d’authentification dont il est question, et selon que l’utilisateur a validé l’authentification ou non, le serveur retourne sa réponse.
Cas passant
Lors d’un cas passant, voilà ce qui est retourné :
- Réponse HTTP 200
- Cookie de session WALLET_ID
- URL de redirection vers le FS avec le code d’autorisation
Cas bloquant
A noter qu’une authentification refusée présentera également une réponse HTTP 200, mais qu’il n’y aura pas de cookie, et qu’une réponse négative sera indiquée dans le corps de la réponse.
Exemples cas passants
Voici, pour chaque type d’authentification réussie, un enregistrement des échanges effectués entre le navigateur et le serveur.