## page was renamed from Python/AuthentificationROA <> = Concept = Le projet [[http://code.welldev.org/django-roa/|django-roa]] permet de créer un système de sérialisation/dé-sérialisation d'objets en passant par une couche HTTP, tout en maintenant un API compatible avec l'ORM de Django. La couche HTTP utilise un API [[http://en.wikipedia.org/wiki/Representational_State_Transfer|REST]], et donc peut être consulté facilement depuis nimporte quel environnement. En plus de l'accès direct aux objets et aux collections, on peut ajouter des paramètres GET pour réstreindre la réponse. Ces paramètres sont les mêmes que pour les querysets, par exemple: {{{ GET /roa/utilisateurs/?filter_email__contains=auf.org }}} = Clients = == Client django == Pour faciliter l'utilisation du système de réferences avec Django, un paquet est installable depuis notre serveur [[Python/DépôtPypi|Pypi]]: [[http://pypi.auf.org/auf_references_client/|auf_references_client]]. En plus de ce paquet, il existe [[http://pypi.auf.org/auf_references_modeles/|auf_references_modeles]], qui est utilisé aussi bien par le serveur que le client. Le client django se connecte par défaut à `auf_references.auf`, sauf si on l'utilise depuis l'un des 3 serveurs de production, dans ce cas, il se connectera à `references.auf.org`. === Ajout de la dépendance === La première étape pour utiliser réferences est d'ajouter le client comme dépendance dans `buildout.cfg`, par exemple: {{{ [buildout] parts = django find-links = http://pypi.auf.org/django-roa/ http://pypi.auf.org/auf_references_client/ http://pypi.auf.org/auf_references_modeles/ [django] recipe = djangorecipe version = 1.1.1 project = auf_ninja wsgi=true settings=production extra-paths = auf_ninja eggs = django_exportateur auf_references_client }}} '''Note''': `auf_references_modeles` et `django-roa` doiventt figurer dans `find-links`, mais ils ne sont pas obligatoire dans `eggs`. '''Avertissement''': Il faut à tout prix que django-roa soit pris depuis notre pypi, il comporte plusieurs changements nécessaires au bon fonctionnement du système. Il faut ensuite modifier `settings.py` pour activer et configurer le client: {{{ INSTALLED_APPS += ( 'django_roa', ) ROA_CUSTOM_ARGS = {'api-key': ROA_API_KEY} from auf_references_client.settings import * TEMPLATE_DIRS.extend(REFERENCES_TEMPLATE_DIRS) }}} === API_KEY === Tous les clients de `references` doivent s'identifier en fournissant une API-KEY, il faut en demander une au responsable du système, en précisant quel est le client, quelles opérations il a besoin de faire, et sur quels objets, et s'il s'agit d'une clé de test ou de production. === Objets === L'utilisation des objects via `references` se fait de facon transparente: {{{ from auf_references_modeles import Etablissement, Region ameriques = Region.objects.get(nom_court = 'A') etablissements = Etablissement.objects.filter(region = ameriques) }}} === Authentification === Un autre besoin du systeme de réference était d'avoir une source unifiée pour vérifier les comptes utilisateurs. Le paquet [[http://pypi.auf.org/auf_references_client/|auf_references_client]] fournit un backend d'authentification pour Django. Pour activer cette authentification, il faut ajouter les lignes suivantes a `settings.py`: {{{ AUTHENTICATION_BACKENDS = ( 'auf_references_client.backends.CascadeBackend', ) AUTH_PASSWORD_REQUIRED = True USERS_AS_STAFF = False }}} La variable `AUTH_PASSWORD_REQUIRED` peut être mise à `False` si on a besoin de pouvoir tester l'application avec plusieurs comptes utilisateurs. La variable `USERS_AS_STAFF` peut être mise à `True` si on a besoin que tous les utilisateurs aient le flag `is_staff` à `True` (pour leur donner accès à l'admin). (Utilisé pour jutda) === Cache (coté client) === L'utilisation de cache est critique pour certains sites, et pour limiter l'utilisation de bande passante. Un système de cache a été ajouté à la version `AUF` de `django-roa`. Pour l'activer, il faut modifier `MIDDLEWARE_CLASSES` dans `settings.py`: {{{ MIDDLEWARE_CLASSES = ( 'django.middleware.cache.UpdateCacheMiddleware', 'django.middleware.common.CommonMiddleware', 'django.middleware.cache.FetchFromCacheMiddleware', .... }}} '''Note''': CommonMiddleware devrait déja être présent, les 2 autres sont à ajouter, dans cet ordre. Ensuite, on peut spécifier le systeme de cache à utiliser, en ajoutant une ligne dans `settings.py`: {{{ CACHE_BACKEND = 'memcached://localhost:11211/' }}} Plus d'informations: [[http://docs.djangoproject.com/en/dev/topics/cache/|django cache]]. == Client manuel == En guise d'exemple, une méthode rapide pour vérifier un compte utilisateur: {{{ def roa_login (self, email, password): rc = None api_key = "" url = "%s?filter_email=%s&filter_password=%s&format=json&api-key=%s" \ % (self.auf_roa_url, email, password, api_key) try: ud = urllib.urlopen (url) list = simplejson.load (ud) ud.close () rc = list[0] except: rc = None return rc }}} '''Note''': Ne pas utiliser cette méthode, la gestion d'erreur est très mauvaise. = Serveur = == Restrictions == === API-KEY === Toute requète au service de réferences doit être identifié par une `api-key`, passée en GET. Ces clés sont générées sur le serveur, et elles sont associées à une liste de permissions, qui permet de définir ce qu'un application peut et ne peut pas faire. (Accès en lecture seule, accès a certains objets uniquement, etc.) La définition des droits ainsi que la génération de la clé se font directement sur l'interface admin du système de réferences. === Lister === Une permission supplémentaire a été ajoutée sur chaque objet publié par `references`, elle autorise l'obtention du listing complet de l'objet en question. Si cette permission n'est pas accordée, l'application ne pourra qu'obtenir des sous-ensembles (en utilisant filter_, exclude_, ...). == Ajout d'un modele == === auf_references_modeles === Ce module ne sert qu'à définir uniformément les modèles utilisés par `references`, il faut donc commencer par ici. Il faut toujours faire attention à ce que le nouveau modèle hérite de la classe `Parent`, et utilise la métaclasse `PermissionMeta`. Exemple: {{{ class Groupe(Parent): __metaclass__ = PermissionMeta id = models.AutoField(primary_key=True) nom = models.CharField(max_length=255) def __unicode__(self): return u"Groupe: %s" % self.nom }}} Il faut ensuite publier le module sur [[Python/DépôtPypi|Pypi]]. === auf_references === Du coté serveur, la démarche est un peu plus complexe. Dans l'application `roa`, on doit d'abord définir de nouveaux handlers pour nos nouveaux modèles (handlers.py): {{{ class GroupeHandler(ROAHandler): model = Groupe class GroupeCountHandler(ROACountHandler): model = Groupe }}} '''Note''': Il est nécessaire d'avoir 2 handlers par objet. Ensuite, toujours dans l'application `roa`, on doit instancier nos handlers, et leur assigner des urls (urls.py): {{{ # Instanciation groupe = Resource(handler=GroupeHandler) groupe_c = Resource(handler=GroupeCountHandler) # URLs urlpatterns = patterns( ... url(r'^groupe/?(?P\d+)?/?$', groupe), url(r'^groupe/count/$', groupe_c), ... ) }}} === auf_references_client === Il faut définir au client quelle est l'url racine du handler du nouvel objet, dans `settings.py`: {{{ ROA_URL_OVERRIDES_LIST = { ... 'auf_references_modeles.groupe': ROA_BASE_URL + 'groupe/', ... } }}} == Portail == Un début de portail de gestion de compte existe, dans l'application `portail`. Elle permet seulement de changer son mot de passe pour le moment (non testée).