Projet

Général

Profil

Wiki » Historique » Version 22

Lionel Morin, 07/11/2012 14:59

1 16 Lionel Morin
{{toc}}
2 16 Lionel Morin
3 1 Gaston TJEBBES
h1. Cassification d'une application sur Scribe 
4 1 Gaston TJEBBES
5 16 Lionel Morin
Scribe est fourni avec un serveur d'authentification SSO compatible CAS. Cette page a pour objectif de guider les utilisateurs (administrateurs) de Scribe à utiliser le mode SSO dans leurs applications web php. Les indications fournies permettent de garantir la compatibilité avec les versions 1.2.0 et 1.3.1 de la librairie php-cas sur lesquelles se base le paquet php5-cas.
6 1 Gaston TJEBBES
7 2 Gaston TJEBBES
8 1 Gaston TJEBBES
h2. Cas n°1 : authentification simple 
9 1 Gaston TJEBBES
10 18 Lionel Morin
Ici, seule l'authentification de l'utilisateur est nécessaire (l'application ne requiert aucune autre information). La cassification de l'accès à une page reste très simple (fonctionnement du CAS classique). On utilisera la configuration centralisée située dans /usr/share/php/configCAS/cas.inc.php. 
11 1 Gaston TJEBBES
12 2 Gaston TJEBBES
13 1 Gaston TJEBBES
h3. Initialisation du client 
14 1 Gaston TJEBBES
15 1 Gaston TJEBBES
<pre>
16 1 Gaston TJEBBES
<?php
17 16 Lionel Morin
// require_once('CAS/eoleCAS.php'); // pointe sur la version 1.2.0
18 16 Lionel Morin
require_once('CAS-1.3.1/eoleCAS.php'); // pointe sur la version 1.3.1
19 1 Gaston TJEBBES
require_once('configCAS/cas.inc.php');
20 1 Gaston TJEBBES
eolephpCAS::client(__CAS_VERSION, __CAS_SERVER, __CAS_PORT, __CAS_URL, false);
21 7 Gérald Schwartzmann
</pre>
22 1 Gaston TJEBBES
Les variables __CAS... sont configurées dans le fichier 'cas.inc.php'. La variable à false signifie qu'une session php a déjà été démarrée avant l'appel au client.
23 22 Lionel Morin
Si __CAS_URL n'existe pas dans la conf on peut l'ajouter dans cas.inc.php de l'appli et l'initialiser à "" cf webcalendar ou ajaxplorer. 
24 1 Gaston TJEBBES
25 1 Gaston TJEBBES
26 16 Lionel Morin
h3. Contrôle des certificats
27 16 Lionel Morin
28 21 Lionel Morin
Pour une meilleure sécurité, la validation par la CA devrait être activée.
29 21 Lionel Morin
Mais pour éviter trop de changement, on distingue selon la version d'Eole : 
30 20 Lionel Morin
31 20 Lionel Morin
* Eole 2.2, on ne change rien :
32 20 Lionel Morin
33 1 Gaston TJEBBES
<pre>
34 20 Lionel Morin
    if (method_exists("EolephpCAS", "setNoCasServerValidation")){
35 20 Lionel Morin
         EolephpCAS::setNoCasServerValidation();
36 20 Lionel Morin
    }
37 20 Lionel Morin
</pre>
38 20 Lionel Morin
39 20 Lionel Morin
* Eole 2.3 : dans gen_config en mode expert, onglet Applications web, "activer_web_valider_ca" de type oui/non avec valeur par défaut à non
40 20 Lionel Morin
41 20 Lionel Morin
<pre>
42 20 Lionel Morin
    if (__CAS_VALIDER_CA) {  // gen_config : activer_web_valider_ca
43 20 Lionel Morin
        EolephpCAS::setCasServerCACert(__CAS_CA_LOCATION); // gen_config : eolesso_ca_location (onglet Eole-sso)
44 16 Lionel Morin
    } else {
45 16 Lionel Morin
        if (method_exists("EolephpCAS", "setNoCasServerValidation")){
46 16 Lionel Morin
            EolephpCAS::setNoCasServerValidation();
47 16 Lionel Morin
        }
48 8 Gérald Schwartzmann
    }
49 1 Gaston TJEBBES
</pre>
50 18 Lionel Morin
51 1 Gaston TJEBBES
L'utilisation de la fonction method_exists permet d'assurer la compatibilité avec les différentes versions du client phpCas (paquet php5-cas).
52 1 Gaston TJEBBES
53 1 Gaston TJEBBES
54 8 Gérald Schwartzmann
h3. Authentification 
55 1 Gaston TJEBBES
56 6 Joël Cuissinat
<pre>
57 1 Gaston TJEBBES
eolephpCAS::forceAuthentication();
58 2 Gaston TJEBBES
</pre>
59 1 Gaston TJEBBES
La redirection vers le serveur CAS est effectuée si nécessaire, par la suite le code est exécuté dans un contexte authentifié.
60 1 Gaston TJEBBES
61 10 Gérald Schwartzmann
62 1 Gaston TJEBBES
h3. Déconnexion 
63 1 Gaston TJEBBES
64 1 Gaston TJEBBES
La variable de redirection ici : $_SERVER["SCRIPT_URI"]  peut être remplacée par la page de logout prévue au départ dans l'application.
65 10 Gérald Schwartzmann
66 10 Gérald Schwartzmann
Nouvelle méthode : https://wiki.jasig.org/display/CASC/phpCAS+logout
67 10 Gérald Schwartzmann
68 1 Gaston TJEBBES
<pre>
69 8 Gérald Schwartzmann
eolephpCAS::logout(array("url"=>$_SERVER["SCRIPT_URI"]));
70 7 Gérald Schwartzmann
</pre>
71 10 Gérald Schwartzmann
72 7 Gérald Schwartzmann
ou
73 10 Gérald Schwartzmann
74 7 Gérald Schwartzmann
<pre>
75 7 Gérald Schwartzmann
eolephpCAS::logout(array("service"=>$service));
76 1 Gaston TJEBBES
</pre>
77 1 Gaston TJEBBES
78 2 Gaston TJEBBES
Dans le premier cas, on est redirigé après déconnexion vers la page $url.
79 2 Gaston TJEBBES
Dans le deuxième cas, on est redirigé sur la mire d'authentification prête pour se reconnecter sur le service $service.
80 1 Gaston TJEBBES
81 22 Lionel Morin
82 1 Gaston TJEBBES
h3. Déconnexion centralisée 
83 19 Lionel Morin
84 1 Gaston TJEBBES
Lorsque l'on se déconnecte d'une application, celle-ci supprime généralement sa session et demande sa déconnexion du serveur SSO. Les sessions des autres applications ne sont pas supprimées dans ce processus et (la plupart du temps), l'application conserve les informations de connexion dans sa session et conserve donc la connexion. Lors de l'activation de la fonction de déconnexion centralisée, le serveur sso demande à chaque application de supprimer la session associée à l'utilisateur qui s'est déconnecté. Le serveur CAS au moment de la déconnexion d'une application, appelle la déconnexion des différentes applications ayant une session SSO ouverte.
85 1 Gaston TJEBBES
86 8 Gérald Schwartzmann
<pre>
87 1 Gaston TJEBBES
if (__CAS_LOGOUT){
88 1 Gaston TJEBBES
    if (method_exists(eolephpCAS, 'eolelogoutRequests')){
89 1 Gaston TJEBBES
        eolephpCAS::eolelogoutRequests(false);
90 3 Gaston TJEBBES
    }
91 1 Gaston TJEBBES
}
92 13 Lionel Morin
</pre>
93 17 Lionel Morin
94 16 Lionel Morin
La variable __CAS_LOGOUT est configurée dans le fichier configCAS/cas.inc.php. 
95 16 Lionel Morin
-A noter : cette fonction fournie par le client CAS d'origine a un fonctionnement très limité, elle ne fonctionne pas lorsque le nom de la session est forcé par l'application cassifiée (appel à session_name(nomdelasession)). 
96 1 Gaston TJEBBES
Dans ce cas, préférez l'utilisation de la librairie eolePhpCAS.- 
97 1 Gaston TJEBBES
98 1 Gaston TJEBBES
99 1 Gaston TJEBBES
h3. Forcer l'url de votre application auprès du serveur CAS
100 1 Gaston TJEBBES
101 1 Gaston TJEBBES
Dans certains cas, par exemple : 
102 1 Gaston TJEBBES
Accès au travers d'un reverseproxy d'une application http par le protocole https et port 80 fermé sur le reverseproxy.
103 1 Gaston TJEBBES
104 1 Gaston TJEBBES
Il peut être utile de forcer l'url de l'application.
105 1 Gaston TJEBBES
<pre>
106 1 Gaston TJEBBES
eolephpCAS::setFixedServiceURL("https://adressedemonapplication");
107 8 Gérald Schwartzmann
</pre>
108 1 Gaston TJEBBES
Il est possible de construire l'url depuis les variables php ($_SERVER par exemple).
109 1 Gaston TJEBBES
110 1 Gaston TJEBBES
111 1 Gaston TJEBBES
h3. Récupération du login de l'utilisateur
112 1 Gaston TJEBBES
113 1 Gaston TJEBBES
<pre>
114 1 Gaston TJEBBES
eolephpCAS::getUser();
115 1 Gaston TJEBBES
</pre>
116 1 Gaston TJEBBES
117 1 Gaston TJEBBES
118 20 Lionel Morin
h3. Le tout dans des fonctions (pour Eole 2.3)
119 1 Gaston TJEBBES
120 1 Gaston TJEBBES
<pre>
121 8 Gérald Schwartzmann
<?php
122 16 Lionel Morin
function cas_auth(){
123 8 Gérald Schwartzmann
   require_once('CAS-1.3.1/eoleCAS.php');
124 8 Gérald Schwartzmann
   require_once('configCAS/cas.inc.php');
125 16 Lionel Morin
   eolephpCAS::client(__CAS_VERSION, __CAS_SERVER, __CAS_PORT, __CAS_URL, false);
126 16 Lionel Morin
   if (__CAS_VALIDER_CA) {
127 16 Lionel Morin
       eolephpCAS::setCasServerCACert(__CAS_CA_LOCATION);
128 16 Lionel Morin
   } else {
129 16 Lionel Morin
       if (method_exists(eolephpCAS, 'setNoCasServerValidation')){
130 16 Lionel Morin
           eolephpCAS::setNoCasServerValidation();
131 1 Gaston TJEBBES
       }
132 1 Gaston TJEBBES
   }
133 1 Gaston TJEBBES
   if (__CAS_LOGOUT){
134 1 Gaston TJEBBES
       if (method_exists(eolephpCAS, 'eolelogoutRequests')){
135 2 Gaston TJEBBES
          eolephpCAS::logoutRequests(false);
136 2 Gaston TJEBBES
       }
137 2 Gaston TJEBBES
   }
138 3 Gaston TJEBBES
   eolephpCAS::forceAuthentication();
139 2 Gaston TJEBBES
}
140 16 Lionel Morin
function cas_logout(){
141 2 Gaston TJEBBES
   require_once('CAS-1.3.1/eoleCAS.php');
142 2 Gaston TJEBBES
   require_once('configCAS/cas.inc.php');
143 16 Lionel Morin
   eolephpCAS::client(__CAS_VERSION, __CAS_SERVER, __CAS_PORT, __CAS_URL, false);
144 16 Lionel Morin
   if (__CAS_VALIDER_CA) {
145 16 Lionel Morin
       eolephpCAS::setCasServerCACert(__CAS_CA_LOCATION);
146 16 Lionel Morin
   } else {
147 16 Lionel Morin
       if (method_exists(eolephpCAS, 'setNoCasServerValidation')){
148 16 Lionel Morin
           eolephpCAS::setNoCasServerValidation();
149 1 Gaston TJEBBES
       }
150 2 Gaston TJEBBES
   }
151 2 Gaston TJEBBES
   eolephpCAS::logout(array("url"=>$_SERVER["SCRIPT_URI"]));
152 2 Gaston TJEBBES
}
153 2 Gaston TJEBBES
?>
154 2 Gaston TJEBBES
</pre>
155 2 Gaston TJEBBES
156 1 Gaston TJEBBES
Du coup dans ma page php: 
157 2 Gaston TJEBBES
<pre>
158 22 Lionel Morin
<?php // Ce qui s'exécute ici n'est pas authentifié ?>
159 1 Gaston TJEBBES
<?php 
160 2 Gaston TJEBBES
cas_auth();
161 2 Gaston TJEBBES
?>
162 22 Lionel Morin
<?php // Ici on n'exécute que du code authentifié avec le user : eolephpCAS::getUser(); ?>
163 2 Gaston TJEBBES
</pre>
164 8 Gérald Schwartzmann
165 8 Gérald Schwartzmann
166 2 Gaston TJEBBES
h2. Cas n°2 : authentification avec récupération de données utilisateurs 
167 2 Gaston TJEBBES
168 2 Gaston TJEBBES
Lors de l'authentification CAS, pour récupérer des données utilisateurs en parallèle, le fonctionnement est identique (au Cas n°1). 
169 2 Gaston TJEBBES
170 2 Gaston TJEBBES
171 2 Gaston TJEBBES
h3. Récupération des informations utilisateurs 
172 2 Gaston TJEBBES
173 2 Gaston TJEBBES
<pre>
174 2 Gaston TJEBBES
$user_login = eolephpCAS::getUser();
175 2 Gaston TJEBBES
$user_details = eolephpCAS::getDetails();
176 2 Gaston TJEBBES
</pre>
177 2 Gaston TJEBBES
178 2 Gaston TJEBBES
Les détails utilisateurs sont renvoyés sous forme de Array php.
179 2 Gaston TJEBBES
Les données qu'ils contiennent dépendent du filtre sso configuré pour l'application.
180 2 Gaston TJEBBES
181 2 Gaston TJEBBES
h4. Configuration du filtre SSO
182 2 Gaston TJEBBES
183 2 Gaston TJEBBES
Le serveur SSO est capable de fournir des données utilisateurs aux applications sous la forme de xml. Un filtre par défaut se contente de fournir l'uid de l'utilisateur qui se connecte, mais tout un ensemble de données peut être fournit.
184 2 Gaston TJEBBES
185 2 Gaston TJEBBES
h5. Première étape : configurer l'application dans un fichier monfiltre_apps.ini que l'on place dans /usr/share/sso/app_filters/
186 2 Gaston TJEBBES
187 2 Gaston TJEBBES
On renseigne "url" et "filtre" qui sont l'url et le filtre associés. 
188 2 Gaston TJEBBES
Quand l'url "http://adresse/lechemin" me demande d'authentifier quelqu'un, une fois authentifiée, je lui renvoie les données renseignées dans le filtre 'monfiltre'.
189 2 Gaston TJEBBES
<pre>
190 2 Gaston TJEBBES
[democas]
191 2 Gaston TJEBBES
baseurl=/lechemin
192 2 Gaston TJEBBES
scheme=http
193 2 Gaston TJEBBES
addr=0/0
194 2 Gaston TJEBBES
typeaddr=ip
195 2 Gaston TJEBBES
filter=monfiltre
196 2 Gaston TJEBBES
</pre>
197 2 Gaston TJEBBES
198 2 Gaston TJEBBES
h5. Deuxième étape : configurer le fichier filtre monfiltre.ini 
199 2 Gaston TJEBBES
200 2 Gaston TJEBBES
<pre>
201 2 Gaston TJEBBES
[user]
202 2 Gaston TJEBBES
user=uid                
203 2 Gaston TJEBBES
[infos] 
204 4 Gaston TJEBBES
user_groups=user_groups
205 2 Gaston TJEBBES
typeadmin=typeadmin
206 15 Lionel Morin
rne=rne
207 2 Gaston TJEBBES
</pre>
208 2 Gaston TJEBBES
	
209 2 Gaston TJEBBES
Le filtre "user=uid" est obligatoire.
210 2 Gaston TJEBBES
211 2 Gaston TJEBBES
Autres propriétés que l'on peut récupérer et donc assigner dans monfiltre.ini:
212 2 Gaston TJEBBES
213 2 Gaston TJEBBES
    * cn=cn
214 2 Gaston TJEBBES
    * user_groups=user_groups
215 2 Gaston TJEBBES
    * employeeType=employeeType
216 2 Gaston TJEBBES
    * typeadmin=typeadmin
217 2 Gaston TJEBBES
    * pam=pam
218 2 Gaston TJEBBES
    * user=uid
219 2 Gaston TJEBBES
    * profil=profil
220 2 Gaston TJEBBES
    * classe=Divcod
221 2 Gaston TJEBBES
    * firstname=givenName
222 2 Gaston TJEBBES
    * lastname=sn
223 2 Gaston TJEBBES
    * email=mail
224 2 Gaston TJEBBES
    * ctemail=mail_acad
225 2 Gaston TJEBBES
    * fullname=displayName
226 2 Gaston TJEBBES
    * civil=codecivilite
227 2 Gaston TJEBBES
    * codeRNE=rne
228 2 Gaston TJEBBES
    * nomEtab=nom_etab
229 2 Gaston TJEBBES
    * typeEtab=typeEtab
230 2 Gaston TJEBBES
    * uid=secureid
231 2 Gaston TJEBBES
    * ENTEleveNivFormation=Meflcf
232 2 Gaston TJEBBES
    * ENTPersonProfils=profilcns 
233 2 Gaston TJEBBES
234 2 Gaston TJEBBES
(voir la documentation pour l'accès aux informations ldap)
235 2 Gaston TJEBBES
236 2 Gaston TJEBBES
A cette étape le serveur eole-sso nécessite d'être recharger pour prendre votre nouveau filtre en compte:
237 2 Gaston TJEBBES
238 2 Gaston TJEBBES
<pre>
239 2 Gaston TJEBBES
/etc/init.d/eole-sso restart
240 2 Gaston TJEBBES
</pre>
241 2 Gaston TJEBBES
242 2 Gaston TJEBBES
243 2 Gaston TJEBBES
h5. Troisième étape : récupérer les données dans le script PHP 
244 2 Gaston TJEBBES
245 2 Gaston TJEBBES
*Sous forme de XML*
246 2 Gaston TJEBBES
247 2 Gaston TJEBBES
Dans le script php appeler la méthode getCasXML() de la manièe suivante:
248 2 Gaston TJEBBES
<pre>
249 2 Gaston TJEBBES
eolephpCAS::getCasXML()
250 2 Gaston TJEBBES
</pre>
251 2 Gaston TJEBBES
252 2 Gaston TJEBBES
Ici, les données récupérées pour l'utilisateur courant sont :
253 2 Gaston TJEBBES
254 2 Gaston TJEBBES
<pre>
255 2 Gaston TJEBBES
<?xml version="1.0" encoding="UTF-8"?>
256 2 Gaston TJEBBES
<cas:serviceResponse xmlns:cas="http://www.yale.edu/tp/cas">
257 2 Gaston TJEBBES
    <cas:authenticationSuccess>
258 2 Gaston TJEBBES
        <cas:infos>
259 2 Gaston TJEBBES
            <cas:typeadmin>2</cas:typeadmin>
260 2 Gaston TJEBBES
            <cas:rne>1234567X</cas:rne>
261 2 Gaston TJEBBES
            <cas:user_groups>domainusers</cas:user_groups>
262 2 Gaston TJEBBES
            <cas:user_groups>professeurs</cas:user_groups>
263 2 Gaston TJEBBES
            <cas:user_groups>math</cas:user_groups>
264 2 Gaston TJEBBES
            </cas:infos>
265 2 Gaston TJEBBES
        <cas:user>
266 2 Gaston TJEBBES
            <cas:user>prof5e1</cas:user>
267 2 Gaston TJEBBES
        </cas:user>
268 2 Gaston TJEBBES
        
269 2 Gaston TJEBBES
      </cas:authenticationSuccess>
270 2 Gaston TJEBBES
</cas:serviceResponse>
271 2 Gaston TJEBBES
</pre>
272 2 Gaston TJEBBES
273 2 Gaston TJEBBES
274 2 Gaston TJEBBES
*Sous forme de tableau PHP*
275 2 Gaston TJEBBES
276 2 Gaston TJEBBES
Dans le script php appeler la méthode getDetails() de la manière suivante:
277 2 Gaston TJEBBES
<pre>
278 2 Gaston TJEBBES
eolephpCAS::getDetails()
279 2 Gaston TJEBBES
</pre>
280 2 Gaston TJEBBES
La méthode retourne un tableau associatif à plusieurs dimensions(tableau de tableaux).
281 2 Gaston TJEBBES
282 2 Gaston TJEBBES
Si on suit l'exemple du filtre monfiltre.ini le tableau renvoyé contient deux tableaux dont les clés correspondent aux étiquettes [user] et [infos] définies dans monfiltre.ini.
283 2 Gaston TJEBBES
La clé du tableau contenu à la clé [user] est le nom donné dans notre exemple monfiltre.ini : "user="
284 2 Gaston TJEBBES
[user][user][0] contient l'uid.
285 2 Gaston TJEBBES
286 2 Gaston TJEBBES
Ici les données renvoyées pour l'utilisateur courant sont :
287 2 Gaston TJEBBES
288 2 Gaston TJEBBES
<pre>
289 2 Gaston TJEBBES
Array ( [infos] => Array ( [typeadmin] => Array ( [0] => 2 ) [rne] => Array ( [0] => 1234567X ) [user_groups] => Array ( [0] => domainusers [1] => professeurs [2] => math ) ) [user] => Array ( [user] => Array ( [0] => prof5e1 ) ) 
290 2 Gaston TJEBBES
</pre>
291 2 Gaston TJEBBES
292 2 Gaston TJEBBES
293 2 Gaston TJEBBES
h4. Récupération des informations utilisateurs construites 
294 2 Gaston TJEBBES
295 2 Gaston TJEBBES
Il est possible de renvoyer des données utilisateurs autre que celle du ldap.
296 2 Gaston TJEBBES
Il est possible de fournir un script python au serveur SSO qui fournit des données plus complexes. 
297 2 Gaston TJEBBES
Exemple l'envoi de données sorties de la configuration du serveur dans un fichier rne.py (utilisé dans l'exemple):
298 2 Gaston TJEBBES
<pre>
299 2 Gaston TJEBBES
	def calc_info(user_infos):
300 1 Gaston TJEBBES
	    """ renvoie le rne de l'étab de l'uitilisateur """
301 11 Gérald Schwartzmann
	    from creole.parsedico import parse_dico
302 11 Gérald Schwartzmann
	    return [parse_dico().get('numero_etab', 'renvide')]
303 11 Gérald Schwartzmann
</pre>
304 11 Gérald Schwartzmann
305 11 Gérald Schwartzmann
h2. Des applications externes
306 11 Gérald Schwartzmann
307 11 Gérald Schwartzmann
h3. Campus
308 11 Gérald Schwartzmann
309 11 Gérald Schwartzmann
<pre>
310 11 Gérald Schwartzmann
/usr/share/sso/app_filters/local_apps.ini
311 11 Gérald Schwartzmann
...
312 11 Gérald Schwartzmann
[campus]
313 11 Gérald Schwartzmann
baseurl=/LaureatsNet
314 11 Gérald Schwartzmann
scheme=https
315 11 Gérald Schwartzmann
addr=scolarite.net
316 11 Gérald Schwartzmann
typeaddr=dns
317 11 Gérald Schwartzmann
filter=attributs_campus
318 11 Gérald Schwartzmann
...
319 11 Gérald Schwartzmann
320 11 Gérald Schwartzmann
/usr/share/sso/app_filters/attributs_campus.ini
321 11 Gérald Schwartzmann
[utilisateur]
322 11 Gérald Schwartzmann
nom=sn
323 11 Gérald Schwartzmann
prenom=givenName
324 11 Gérald Schwartzmann
login=ENTPersonLogin
325 11 Gérald Schwartzmann
categories=ENTPersonProfils
326 11 Gérald Schwartzmann
dateNaissance=ENTPersonDateNaissance
327 11 Gérald Schwartzmann
codePostal=ENTPersonCodePostal
328 11 Gérald Schwartzmann
eleveClasses=ENTEleveClasses
329 11 Gérald Schwartzmann
uid=uid
330 11 Gérald Schwartzmann
rne=rne
331 11 Gérald Schwartzmann
</pre>
332 1 Gaston TJEBBES
333 1 Gaston TJEBBES
L'Url d'accès est : https://scolarite.net/LaureatsNet/IdentificationCasEOLE<codeRNE>
334 1 Gaston TJEBBES
Doc en ligne : http://campuswiki.fr/index.php/Scolarite.net:CAS