CAS – SSO
1 CAS : Central Authentication Service
CAS est un système d’authentification unique : on s’authentifie sur un site Web, et on est alors authentifié sur tous les sites Web qui utilisent le même serveur CAS.
Il évite de s’authentifier à chaque fois qu’on accède à une application en mettant en place un système de ticket.
1.1 PRINCIPE DE FONCTIONNEMENT
CAS est essentiellement un protocole basé sur des requêtes HTTP pures. Certains messages sont cependant formatés en XML.
Ce protocole est basé sur une notion d’échange de tickets, un peu à la manière de Kerberos. Ces tickets sont des « opaque handles » : ils ne transportent aucune information.
Il y a deux tickets nécessaires au fonctionnement de base, plus deux autres tickets dans le cas d’utilisation de proxy CAS :
- Ticket-Granting Cookie (TGC)
- Service Ticket (ST)
- Proxy-Granting-Ticket (PGT)
- Proxy-Ticket (PT)
1.1.1 Ticket-Granting Cookie (TGC)
C’est un cookie de session qui est transmis par le serveur CAS au navigateur du client lors de la phase de login. Ce cookie ne peut être lu / écrit que par le serveur CAS, sur canal sécurisé (HTTPS).
Si le navigateur web n’accepte pas les cookies, l’utilisateur devra se ré-authentifier à chaque appel au serveur CAS.
1.1.2 Service Ticket (ST)
Ce ticket va servir à authentifier une personne pour une application web donnée. Il est envoyé par le serveur CAS après que l’utilisateur se soit authentifié, et est transporté dans l’URL.
Ce ticket ne peut être utilisé qu’une seule fois. Il y a ensuite dialogue direct entre l’application web et le CAS via un GET HTTP, avec le ST en paramètre. En réponse, le serveur CAS retourne l’identifiant de la personne, et donc l’authentifie. Il invalide également le ticket (libération des ressources associées).
En fait, ce ticket concerne une personne, pour un service, et utilisable une seule fois.
1.1.3 Proxy-Granting-Ticket (PGT)
Il est envoyé par le serveur CAS à une application web proxy CAS disposant d’un ST valide. Ce ticket confère au proxy CAS la possibilité de demander au serveur CAS de générer un Proxy Ticket (PT) pour une application tierce et une personne donnée.
1.1.4 Proxy-Ticket (PT)
Il est généré par le serveur CAS à la demande d’un proxy CAS. Il permet d’authentifier l’utilisateur pour un service distant, avec lequel le client web n’a pas d’accès direct. Le service distant l’utilisera comme le ST.
Il est possible d’utiliser des proxies CAS en cascade.
Dans le fonctionnement de CAS, le service ayant besoin de l’authentification est en relation directe avec le serveur CAS lors de la validation du ticket. Ceci rend possible l’utilisation de ce mécanisme pour transporter des informations complémentaires (autorisations, attributs,…).
Le paquet fourni propose le nécessaire pour mettre en œuvre le protocole CAS ; à charge de l’implémenteur de développer le module d’authentification interne. Un module d’authentification LDAP a été récupéré pour les essais ; il est à améliorer.
Le portage de CAS vers uPortal se fait facilement (les bibliothèques sont fournies). Dans ce cas, uPortal devient proxy CAS ; il obtient donc un PGT du serveur CAS. Il est donc possible à un canal qui utiliserait un service tiers sachant authentifier CAS de demander un PT pour ce service ; des essais fructueux ont été faits dans ce sens.
1.2 FONCTIONNEMENT DE BASE
Le fonctionnement en mode non proxy est le suivant :

- Requête initiale : le client web accède à une appli web qui nécessite authentification. Cette appli redirige la requête vers l’url login du serveur CAS, en https.
En paramètre du GET est passé l’ID du service (c’est en fait l’URL de retour). - Authentification : le serveur CAS authentifie la personne grâce au mécanisme local d’authentification (LDAP, kerberos, certificat, …).
Il redirige la requête vers l’appli initiale. Si le client web accepte les cookies, le TGC est positionné. - Retour à l’application web avec le ST, passé en paramètre du GET.
- Validation : L’appli web accède directement au serveur CAS en http(s) (url validate ou serviceValidate), et passe en paramètres l’ID de service (l’URL) et le ST.
Le serveur CAS s’assure de la validité du ticket ; il retourne l’uid de la personne. Le ticket ne peut plus être rejoué.
A ce moment, la personne est authentifiée, et l’application connait son identifiant.
1.3 FONCTIONNEMENT EN MODE PROXY
Pour utiliser certains services comme un webmail type Roundcube ou un serveur XMPP type Jappix, il se pose des problèmes pour utiliser l’authentificationCAS.
Ces applications utilisent les identifiants des utilisateurs pour se connecter sur d’autres serveurs : serveur imap pour roundcube et serveur jabber (XMPP) pour Jappix.
Or lorsqu’on identifie un utilisateur par le CAS on le fait via un ticket et à aucun moment le mot de passe de l’utilisateur n’est accessible par le service qui l’identifie (roundcube par exemple).
Le “CAS proxying” consiste à remplacer le mot de passe par un ticket fournis par le CAS, puis transmettre par le proxy ou CAS proxy client (roundcube) au service tiers ou Proxy Service (serveur imap).
Il est donc nécessaire de relier le service tiers (serveur imap) au CAS pour qu’il puisse vérifier ce ticket.
Le fonctionnement en mode proxy est le suivant :

- Requête initiale : le client web accède à une appli web qui nécessite authentification. Cette appli redirige la requête vers l’url login du serveur CAS, en https.
En paramètre du GET est passé l’ID du service (c’est en fait l’URL de retour). - Authentification : le serveur CAS authentifie la personne grâce au mécanisme local d’authentification (LDAP, kerberos, certificat, …).
Il redirige la requête vers l’appli initiale. Si le client web accepte les cookies, le TGC est positionné. - Retour à l’application web avec le ST, passé en paramètre du GET.
- Validation : L’appli web accède directement au serveur CAS en http (url serviceValidate), et passe en paramètres l’ID de service (l’URL), le ST et une url de callback.
Si le ST est valide, le serveur retourne comme auparavant l’identifiant de l’utilisateur, et un PGT-id : ce n’est pas le PGT, mais un index permettant de valider le PGT. - Envoi du PGT : en synchronisme, le serveur CAS génère une connexion https vers l’URL de callback de l’appli proxy CAS ; cette requête contient le PGT, et le PGT-id. Le PGT a une durée de vie limitée ; seuls, les tickets TGC et PGT sont rejouables.
Maintenant, l’application web proxy CAS dispose d’un PGT propre à l’utilisateur. Grâce à celui-ci, le proxy CAS pourra demander au CAS de lui générer des PT, qui sont l’équivalent du ST, mais pour des services (URLs) tiers.On suppose maintenant que le proxy CAS fait appel à un service tiers nécessitant authentification ; ça peut être tout type d’application, ce qui compte, c’est qu’elle sache parler http. Dans l’illustration, il s’agit d’un ’web service’. - Demande d’un PT : le proxy CAS génère une requête https vers le serveur CAS (url proxy), en passant en paramètres le PGT et le ’targetService’ : c’est l’URL de l’application finale (ici, le web service). Si le PGT est valide, le CAS retourne un PT
- Transmission du PT : le proxy CAS passe le PT au service tiers.
- Validation : le service utilise le PT comme un ST : il accède directement au serveur CAS en http(s) (url proxyValidate), et passe en paramètre son ID de service et le PT. Le serveur CAS s’assure de la validité du ticket, il retourne l’identifiant de la personne et le proxy ou la liste de proxies traversé(s).
L’utilisateur est alors authentifié par le web service.
2 INSTALLATION
Nous nous basons sur une serveur Ubuntu 14.04 LTS. Nous partons sur la base que nous disposons déjà d’un serveur LDAP qui va gérer l’authentification des utilisateurs. Nous utilisons la version 3.5.2 du serveur CAS.
2.1 PARAMETRAGE DE L’ANNUAIRE
On part sur le principe que l’annuaire LDAP 389 est déjà installé sur le serveur sous la forme d’un replicat en lecture seule.
Cette étape n’est pas obligatoire puisque l’on pourrait directement utiliser l’annuaire maître du laboratoire, mais cela augmente la sécurité globale du système.
2.1.1 OBJETS ET CLASSES
Le service CAS authentifie des utilisateurs : il suffit donc d’avoir les individus dans l’annuaire.
L’annuaire dispose entres autres des schémas eduperson.schema, supann.schema, nosland.schema, samba.schema permettant de référencer les personnes.
Ces fichiers sont présents dans l’archive de la documentation.
Remarque : Il est préférable de dupliquer ce ldif sur le serveur CAS, même si l’action de réplication copiera les objets et classes nécessaires
2.1.2 DIT
Sur le serveur LDAP maître et son esclave CAS, pour assurer la réplication, il est nécessaire de créer une base dédiée aux objets manipulés par CAS : les individus.
Un sous-suffix “ou=people” est créé à la base du suffix “dc=nosland,dc=com”, et c’est ce suffix qui est répliqué sur le serveur esclave.
Les domaines gérés dans l’annuaire représentent l’ensemble des matériels présents dans le réseau des laboratoires.

FIGURE 1: DIT pour CAS
Voici un exemple de fichier LDIF correspondant au DIT :
dn: ou=people,dc=nosland,dc=com
objectClass: organizationalunit
objectClass: top
ou: dns
dn: uid=nospheratus,ou=people,dc=nosland,dc=com
objectClass: sambaSamAccount
objectClass: person
objectClass: organizationalPerson
objectClass: supannPerson
objectClass: inetOrgPerson
objectClass: shadowAccount
objectClass: posixAccount
objectClass: account
objectClass: top
cn: NosPHeratus
gidNumber: 666
homeDirectory: /users/nospheratus
sambaSID: S−XXXXXXXXXXXXXXXXXXXXXXXXXXXX
sn: NosPHeratus
uid: nospheratus
uidNumber: 666
displayName: NosPHeratus
gecos: NosPHeratus,demandeur NosPHeratus,Permanent
givenName: NosPHeratus
labeledURI: http://cas.nosland.com/~nospheratus/
loginShell: /bin/bash
mail: nospheratus@nosland.com
preferredLanguage: fr
sambaAcctFlags: [U]
sambaLMPassword: XXXXXXXXXXXXXXXXXXXXXXXXXXXX
sambaNTPassword: XXXXXXXXXXXXXXXXXXXXXXXXXXXX
sambaPasswordHistory: 000000000000000000000000000000000000000000000000000000
0000000000
sambaPwdLastSet: 765908865
sambaPwdMustChange: 256899754
shadowLastChange: 15392
shadowMax: 1000
shadowWarning: 7
supannAliasLogin: nospheratus
supannCivilite: M.
supannListeRouge: TRUE
supannParrainDN: uid=nospheratus,ou=people,dc=nosland,dc=com
telephoneNumber: +33 6 XX XX XX XX
userPassword:: XXXX
2.2 TOMCAT
CAS nécessite un conteneur J2EE pour fonctionner.
Au choix, on peut utiliser la version Tomcat de la distribution ou télécharger les binaires du site d’Apache :
Voilà la liste des commandes pour faire fonctionner le serveur d’applications :
# apt−get update
# apt−get install openjdk−6−jdk
# apt−get install tomcat6
# apt−get install maven2
# apt−get install ant
# apt−get install maven−ant−helper
Note : il peut être nécessaire d’installer maven (version 3) en lieu et place du paquet maven2 sur les dernieres versions ubuntu suivant la version cas récupérée (cf ci-après).
A ce stade, on peut déjà vérifier l’activité du serveur d’applications :

2.3 CERTIFICAT
Pour utiliser un serveur CAS, il faut que les connexions soient encryptées en SSL.
Pour cela, il faut soit utiliser un certificat valide (fourni par l’Université par exemple), soit en générer un.
Dans le second cas, il faut commencer par le générer le keystore :
# keytool −genkey −alias tomcat −keypass changeit −keyalg RSA
Tapez le mot de passe du Keystore :
Ressaisissez le nouveau mot de passe :
Quels sont vos prenom et nom ?
[Unknown] : NosPHeratus
Quel est le nom de votre unite organisationnelle ?
[Unknown] : NosLand
Quelle est le nom de votre organisation ?
[Unknown] : DSI
Quel est le nom de votre ville de residence ?
[Unknown] : RIOZ
Quel est le nom de votre etat ou province ?
[Unknown] : Franche-Comte
Quel est le code de pays a deux lettres pour cette unite ?
[Unknown] : FR
Est−ce CN=NosPHeratus, OU=NosLand, O=DSI, L=Rioz, ST=Franche-Comte, C=FR ?
[non] : oui
Le fichier .keystore est généré.
Note :
- Il est important d’utiliser l’utilitaire keytool livré avec la jvm , au besoin préciser le chemin par ex : /usr/lib/jvm/java-6-openjdk-amd64/bin/keytool. Cela afin que le keystore généré soit bien au format JKS (Java Keystore Format).
- Par defaut, tomcat s’attend à trouver le fichier .keystore dans le home de l’utilisateur sous lequel il est lancé (/usr/share/tomcat6 sous ubuntu), si tel n’est pas le cas il convient d’ajouter un attribut keystoreFile à l’element Connector dans le fichier de configuration de tomcat server.xml.
On ajoute ensuite le certificat à la JRE :
# keytool −export −alias tomcat −keypass changeit −file .keystore
# keytool −import −alias tomcat −file .keystore \
−keypass changeit −keystore /etc/ssl/certs/java/cacerts
On modifie le fichier de configuration du serveur Tomcat “/var/lib/tomcat6/conf/server.xml” :<Connector port= »8080″ protocol= »HTTP/1.1″
connectionTimeout= »20000″
redirectPort= »8443″ />
<Connector port= »8443″ protocol= »HTTP/1.1″ SSLEnabled= »true »
maxThreads= »150″ scheme= »https » secure= »true »
clientAuth= »false » sslProtocol= »TLS » />
2.4 CAS
On télécharge la version de CAS désirée :
# wget http://downloads.jasig.org/cas/cas−server−3.5.2−release.tar.gz
# tar −xvzf cas−server−3.5.2−release.tar.gz
# cd cas−server−3.5.2/cas−server−wepapp
On configure l’utilisation du support LDAP en modifiant “pom.xml” :
<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>cas−server−support−ldap</artifactId>
<version>${project.version}</version>
</dependency>
On nettoie les librairies non utilisées, on télécharge les dernières versions, et on copie le tout dans la racine des applications du serveur :
# cp ../modules/cas−server−webapp−3.5.2.war /var/lib/tomcat6/webapps/
# mvn clean package
# cp −Rp target/cas−server−webapp−3.5.2 /var/lib/tomcat6/webapps/
On peut ensuite se connecter à l’url http://localhost:8080/cas-_server-_webapp-_3.5.2/

Il faut ensuite configurer l’accès à l’annuaire LDAP en ajoutant le bean au fichier de configuration “/var/lib/tomcat6/webapps/cas-server-webapp-3.5.2/WEB-INF/deployerConfigContext.xml” :
<bean id= »contextSource »
class= »org.springframework.ldap.core.support.LdapContextSource »>
<property name= »anonymousReadOnly » value= »true » />
<property name= »pooled » value= »true » />
<property name= »urls »>
<list>
<value>ldap://ldap−maitre:389/</value>
</list>
</property>
<property name= »baseEnvironmentProperties »>
<map>
<entry>
<key><value>java.naming.security.authentication</value></key>
<value>none</value>
</entry>
</map>
</property>
</bean>
Dans ce même fichier, on modifie également la méthode d’authentification en remplacant le bean “org.jasig.cas.authentication.handler.support.SimpleTestUsernamePasswordAuthenticationHandler” par le bean :
<bean class= »org.jasig.cas.adaptors.ldap.FastBindLdapAuthenticationHandler » >
<property name= »filter » value= »uid=%u,ou=people,dc=nosland,dc=com » />
<property name= »contextSource » ref= »contextSource » />
</bean>
Après avoir redémarrer tomcat, on peut tester l’authentification pour un utilisateur présent dans le LDAP :

2.5 FINALISATION
Pour rendre l’accès à l’application plus élégant, on crée une url d’accès plus simple via un lien :
# cd /var/lib/tomcat6/webapps
# ln −s cas−server−webapp−3.5.2 cas
# /etc/init.d/tomcat6 restart
Cela permet en plus d’utiliser/tester d’autres versions du serveur CAS de manière transparente.
3 TUNING
3.1 PROXY APACHE
Pour faire du load balancing, ou tout simplement pour gérer plus efficacement les au serveur CAS, il est possible d’ajouter un serveur Apache en frontal du CAS :

Ce serveur Apache peut être localisé soit sur le serveur CAS lui-même, soit délocalisé sur un autre serveur.
Dans les deux cas, la configuration du proxy se fait au niveau de la configuration d’Apache :ProxyPass /cas http://127.0.0.1:8443/cas
ProxyPassReverse /cas http://127.0.0.1:8443/cas
“127.0.0.1” correspond à l’adresse du serveur CAS.
Il est conseillé/nécessaire :
- d’activer les modules PROXY et SSL d’Apache
- de configurer le certificat du nom du serveur CAS pour passer en HTTPs
L’exemple suiviant montre une configuration possible en passant par l’interface AJP de Tomcat :
ProxyRequests Off
<Location /cas>
ProxyPass ajp://localhost:8009/cas
ProxyPassReverse http://192.168.73.24/cas
</Location>
SSLEngine on
SSLCertificateFile /etc/apache2/ssl/cas.nosland.com.pem
SSLCertificateKeyFile /etc/apache2/ssl/cas.nosland.com.key
3.2 SKIN
Sur le serveur CAS, pour modifier sensiblement les pages JSP, il faut directement modifier les vues dans /var/lib/tomcat6/webapps/cas/WEB-INF/view/jsp/default/ui.
Il faut donc faire une copie de sauvegarde préalable de ces fichiers.
Voila la liste des vues modifiées :
- includes/bottom.jsp
- includes/top.jsp
- casLoginView.jsp
Il faut de plus modifier le CSS “css/cas.css”.

4 CLIENTS
4.1 APACHE-MODCAS
Sur le serveur web Apache, il est facile de configurer une authentification CAS.
On installe le module adequat et on l’active :
# apt−get install libapache2−mod−auth−cas
# a2enmod auth_cas
Dans la configuration de l’hôte virtuel, on ajoute les directives :
: /etc/apache2/sites-enabled/default-ssl.conf…
CASDebug On
CASRootProxiedAs https://proxy.nosland.com
CASValidateServer Off
CASLoginURL https://cas.nosland.com/cas/login
CASValidateURL https://cas.nosland.com/cas/serviceValidate
<LocationMatch « /cas/.∗ »>
AuthType CAS
require valid−user
</LocationMatch>
…
Si l’on souhaite autoriser que quelques personnes authentifiées, il faut compléter la ligne “require valid-user” par :
require user nospheratus Zorky
4.2 PHPCAS
Il est possible d’utiliser la librairie PHPCAS disponible sur le site du développeur du CAS :
- https ://wiki.jasig.org/display/casc/phpcas
Ce dessous le code pour forcer le passage de la page index.php par l’authentification auprès du serveur CAS, et récupération de l’identifiant de connexion :
:index.php
<?php
// Initialisation de l’authentification CAS
require_once ’cas/CAS.php’;
//phpCAS::setDebug();
phpCAS::client(CAS_VERSION_2_0, »cas.nosland.com », 443, »/cas »);
phpCAS::setLang(PHPCAS_LANG_FRENCH);
phpCAS::setNoCasServerValidation();
// Pour forcer l’authentification
phpCAS::forceAuthentication();
// Recuperation de l’identifiant de l’individu connecte
echo « identifiant : « . phpCAS::getUser();
?>
4.3 PAM_CAS
On utilise la version Pam_cas-2.0.11-esup-2.0.5 disponible sur https://sourcesup.cru.fr/frs/?group_id=28
Après avoir décompilé l’archive, on effectue les compilations :
# cd Pam_cas−2.0.11−esup−2.0.5/sources
# make
# make castest
# cp pam_cas.so /lib/security/pam_cas.so −> sur 32 bits
# cp pam_cas.so /lib/x86_64−linux−gnu/security/ −> sur 64 bits
# ldd pam_cas.so
On crée le fichier de configuration :
/etc/pam_cas.conf :
# le nom du serveur CAS
host cas.nosland.com
# le port
port 443
# uri de validation des tickets
uriValidate /cas/proxyValidate
# on utilise https
ssl on
# debug
debug off
# adresses autorisees s’authentifier sur le pam_cas
proxy https://cas.nosland.com/webmail/casimap.php
proxy https://cas.nosland.com/webmail/rc/?_action=pgtcallback
proxy https://cas.nosland.com/webmail/rc/?_task=mail
proxy https://cas.nosland.com/webmail/rc/?_action=caslogin
proxy https://cas.nosland.com/webmail/rc/
# chaine de certification
trusted_ca /etc/ssl/tcschain.pem
Il faut placer le fichier de chaîne de certification utilisée par le serveur CAS dans /etc/ssl/tcschain.pem
On modifie ensuite la pile PAM :
: /etc/pam.d/imapauth sufficient /lib/security/pam_cas.so \
−simap://mail.nosland.com \
−f/etc/pam_cas.conf
@include common−auth
@include common−account
@include common−session
…
\
−simap://mail.nosland.com \
−f/etc/pam_cas.conf
@include common−auth
@include common−account
@include common−session
…