Fonctionnement de SAML
Les grands principes
Security Assertion Markup Language ou langage de balisage d’assertion de sécurité
Dédié aux applis Web
L’utilisateur est au coeur de son authentification
Jeton échangé via XML
L’application cliente (Service Provider ou SP) demande une authentification
Elle redirige l’utilisateur vers un IDP ou Identity Provider, en transmettant une requête d’authentification donnant notemment des informations sur le SP. Ce n’est pas obligatoire dans le protocole mais la requête doit être signée (clé privée du SP) et chiffrée (clé publique de l’IDP)
L’IDP recherche le SP appelant, vérifie la signature et cherche à authentifier l’utilisateur
En cas de réussite, il redirige vers le SP avec une assertion qu’il signe (clé privée de l’IDP) et chiffre (clé publique du SP).
Le SP valide l’assertion
CC BY-SA 3.0, LinkDu SAML à l’ère d’OpenIdConnect ?
- Nécessaire si l’application cliente et le serveur d’authentification ne sont pas connectés directement (Un en interne, un en DMZ)
- Applications atypiques ne supportant que SAML (progiciel,…)
Contenu d’une configuration SAML
- Les fichiers metadatas du SP et des IDP : éléments centraux des configuration SAML
- Un keystore contenant la clé privé et le certificat du Service provider : permet de signer les requêtes et de déchiffrer les réponses
- Selon les implémentations, il faut extraire des informations des fichiers metadatas et les présenter comme des paramètres.
Le metadata SAML
- Une application cliente connait un ou plusieurs IDP
- Un IDP connait une liste d’application
Un moyen simple de s’échanger les informations sur un client ou un IDP est le metadata
Metadata d’un SP
<md:EntityDescriptor ... entityID="https://localhost:8443">
<md:SPSSODescriptor AuthnRequestsSigned="true" WantAssertionsSigned="true" ...>
<md:KeyDescriptor use="signing"><ds:KeyInfo ...><ds:X509Data><ds:X509Certificate>Certificat du SP (clé plublique)</ds:X509Certificate></ds:X509Data></ds:KeyInfo></md:KeyDescriptor>
<md:KeyDescriptor use="encryption"><ds:KeyInfo ...><ds:X509Data><ds:X509Certificate>Certificat du SP (clé plublique)</ds:X509Certificate></ds:X509Data></ds:KeyInfo></md:KeyDescriptor>
<!-- Indique où rediriger la requête dans le cas d'une demande de SLO selon le type de bind -->
<md:SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect" Location="https://localhost:8443/saml/LogoutServiceHTTPRedirect" ResponseLocation="https://localhost:8443/saml/LogoutServiceHTTPRedirectResponse" />
<md:SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" Location="https://localhost:8443/saml/LogoutServiceHTTPPost" ResponseLocation="https://localhost:8443/saml/LogoutServiceHTTPRedirectResponse" />
<!-- Format du "Name ID" qui est l'identifiant selon le fournisseur d'identité. Dans le cas "transcient", c'est une chaine aléatoire pour chaque assertion -->
<md:NameIDFormat>urn:oasis:names:tc:SAML:2.0:nameid-format:transient</md:NameIDFormat>
<!-- Indique où poster la demande d'assertion -->
<md:AssertionConsumerService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" Location="https://localhost:8443/saml/SAMLAssertionConsumer" index="0" isDefault="true" />
<md:Extensions>
<!-- Informations destinées à configurer la page de login dans le cas de la fédération externe -->
<mdui:UIInfo>
<mdui:DisplayName xml:lang="fr"></mdui:DisplayName><mdui:DisplayName xml:lang="en"></mdui:DisplayName><mdui:Description xml:lang="fr"></mdui:Description><mdui:Description xml:lang="en"></mdui:Description><mdui:Logo height="320" width="75"></mdui:Logo><mdui:InformationURL xml:lang="fr"></mdui:InformationURL><mdui:InformationURL xml:lang="en"></mdui:InformationURL>
</mdui:UIInfo>
</md:Extensions>
</md:SPSSODescriptor>
<md:Organization>...</md:Organization><md:ContactPerson ...>...</md:ContactPerson>
</md:EntityDescriptor>
- Attention les Endpoints doivent être identique sur la conf du SP et tel que déclarés sur l’IDP.
- C’est une vérification pour ne pas envoyer l’utilisateur n’importe où (Le SP redonne l’url de redirection lors d’une requête d’authentification)
Metadata d’un idp
Récupérable sur un endpoint spécifique du fournisseur
<EntityDescriptor ... entityID="https://idp.test/idp/shibboleth">
<IDPSSODescriptor ...>
<KeyDescriptor><ds:KeyInfo><ds:X509Data><ds:X509Certificate>certificat de l'idp (clé publique)</ds:X509Certificate></ds:X509Data></ds:KeyInfo></KeyDescriptor>
<!-- Services proposés, type de bind (POST, Redirect, SOAP, ...) et url associées en particulier SSO et SLO -->
<SingleSignOnService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect" Location="https://idp.test/idp/profile/SAML2/Redirect/SSO"/>
<SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect" Location="https://idp.test/idp/profile/SAML2/Redirect/SLO"/>
<SingleLogoutService Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" Location="https://idp.test/idp/profile/SAML2/POST/SLO"/>
<!-- NameID possibles de la part de cet IDP -->
<NameIDFormat>urn:mace:shibboleth:1.0:nameIdentifier</NameIDFormat>
<NameIDFormat>urn:oasis:names:tc:SAML:2.0:nameid-format:transient</NameIDFormat>
</IDPSSODescriptor>
</EntityDescriptor>
Une assertion SAML
Les points importants :
<?xml version="1.0" encoding="UTF-8"?>
<saml2:Assertion ... IssueInstant="2018-06-07T11:00:48.151Z" ...>
<saml2:Issuer>https://idp.test/idp/shibboleth</saml2:Issuer>
<ds:Signature ...><ds:SignedInfo>...infos algo...</ds:SignedInfo><ds:SignatureValue>Signature de l'assertion par l'idp</ds:SignatureValue><ds:KeyInfo>... Rappel certificat IDP ...</ds:KeyInfo>
</ds:Signature>
<saml2:Subject>
<saml2:NameID ... NameQualifier="https://idp.test/idp/shibboleth" SPNameQualifier="https://mon-appli.test" ...>...</saml2:NameID>
<!-- Infos validité de l'assertion -->
<saml2:SubjectConfirmation ...>
<saml2:SubjectConfirmationData Address="10.92.108.2%3" InResponseTo="_0196a897-0111-4d6f-9c69-d35436e7c590" NotOnOrAfter="2018-06-07T11:05:48.163Z" Recipient="https://mon-appli.test/saml/SAMLAssertionConsumer"/>
</saml2:SubjectConfirmation>
</saml2:Subject>
...
<saml2:AuthnStatement ...><saml2:SubjectLocality Address="192.168.1.1%3"/><saml2:AuthnContext>
<!-- Quelle méthode d'authentification a été réalisée -->
<saml2:AuthnContextClassRef>urn:oasis:names:tc:SAML:2.0:ac:classes:Kerberos</saml2:AuthnContextClassRef>
</saml2:AuthnContext></saml2:AuthnStatement>
<saml2:AttributeStatement>... Attributs ...</saml2:AttributeStatement>
</saml2:Assertion>