Atol C&D met à disposition de la communauté Alfresco (sous licence GPL) une extension qui utilise à la fois le Framework Audit Trail et le Framework SURF, son nom de code : AuditSurfCet outil permet d’avoir une vue d’ensemble sur l’utilisation de l’entrepôt Alfresco. Il fournit une assistance à l’administration et un suivi de l’utilisation d’Alfresco.

# Fonctionnement général

AuditSurf est découpé en deux blocs :

  • un module responsable de la récupération des données d’audit coté entrepôt (module AMP)
  • une extension SURF qui assure la présentation / mise en forme des données (Application basée sur le Framework SURF)

Les échanges entre ces deux blocs s’effectuent au travers de connecteurs (HTTP), ce qui permet à notre application SURF d’appeler des WebScripts situés coté entrepôt (le format majoritairement utilisé lors de ces échanges est le JSON).

Voici une schématisation du fonctionnement d’AuditSurf :

 

Accès aux données :

Les informations d’AuditSurf sont issues du mécanisme d’audit trail d’Alfresco, de JMX (pour la version entreprise seulement) et de l’entrepôt lui-même.

Cette partie va traiter des mécanismes que nous avons utilisés pour extraire les données d’audit de la base de données Alfresco. Si vous désirez avoir des informations sur le mécanisme d’audit au sein d’Alfresco, je vous invite à lire l’article concernant l’audit sur ce blog.

J’illustrerai les mécanismes coté entrepôt Alfresco à l’aide d’un exemple simple (qui sera disponible au téléchargement).

  • Accès aux données d’audit (Utilisation d’Hibernate)

La majorité des fonctionnalités de notre application utilisent des données qui sont stockées dans la base de données.

Pour récupérer les informations dans les tables d’audit, nous utilisons le mapping Hibernate mis en place dans Alfresco et plus particulièrement l’API que propose Hibernate : Criteria (c‘est une API d’interrogation par critères intuitive et extensible).

Pour commencer, nous avons créé un service afin de centraliser tous les accès à la base de données via Hibernate. Ce service hérite de la classe abstraite HibernateDaoSupport indispensable pour pouvoir « exécuter » des requêtes Hibernate.

Afin de réaliser des requêtes Criteria, il est utile de consulter le fichier de mapping Hibernate concernant l’audit qui se trouve dans le SDK Alfresco : Audit.hbm.xml.

Prenons un exemple simple : on désire récupérer la liste des documents créés lors des sept derniers jours :

Pour récupérer la liste des documents créés, il faut auditer le service « FileFolderService » et plus particulièrement sa méthode « create ».

Pour construire la requête Criteria, nous aurons besoins des trois tables d’audit :

  • La table ALF_AUDIT_SOURCE pour pouvoir sélectionner le service « FileFolderService » et la méthode « create ».
  • La table ALF_AUDIT_FACT pour récupérer les informations sur le document (sa date de création et son NodeRef).
  • et la table ALF_AUDIT_DATE si l’on souhaite restreindre nos résultats sur une période précise.

Création du service : SimpleAuditService.java

Implémentation du service : SimpleAuditServiceImpl.java

L’implémentation de notre service hérite de la classe HibernateDaoSupport et implémente évidement l’interface SimpleAuditService que nous venons de créer.

  • Construction de la requête Criteria

Explication de la requête :

La requête ci-dessus est relativement simple et peut se décomposer comme une requête SQL classique.

Puisque l’on utilise Hibernate, on ne travail pas sur des tables mais sur des classes cependant le raisonnement est sensiblement similaire (bien que la construction n’est pas ordonnée de la même façon).

On commence par sélectionner les classes sur lesquelles on désire travailler (équivalent à clause FROM en SQL) en utilisant « createCriteria ». Ensuite, on définit des restrictions (clause WHERE) à l’aide de « Restrictions ». Puis on projette ce dont on a besoin (clause SELECT) à l’aide de « Projections ».

Cette requête Crtieria équivaut à la requête SQL suivante :

Pour plus d’informations sur Criteria, je vous renvoie vers le site d’Hibernate.

Cet exemple n’est plus d’actualité dans Alfresco 3.2 Entreprise. En effet, dans la dernière monture d’Alfresco, il faut s’intéresser au service « ContentService » et à sa méthode « getWriter » pour avoir des informations sur la création de contenu.
Voici à quoi ressemblerait la requête criteria :

  • Injection du service via le Framework Spring

Afin de pouvoir utiliser notre service, il faut créer un bean Spring pour que l’on puisse facilement l’injecter dans nos WebScripts.

La déclaration du bean se fait dans le fichier module-context.xml du module : 

  • Création d’un WebScript

Maintenant que l’on a créé un service capable de récupérer des données d’audit, on peut créer un WebScript qui fera appel à ce dernier.

Les WebScripts d’AuditSurf (coté entrepôt) sont des WebScripts Java-Backed. Ces WebScripts permettent de faire des traitements plus évolués que des WebScripts « classiques ».

Ce genre de WebScript est composé :

  • d’une classe Java (qui fera appel à notre service pour pouvoir récupérer les informations d’audit)
  • d’un fichier de description qui indique les URLs par lesquelles le WebScript est accessible, son mode d’authentification, …
  • d’un ou plusieurs templates (FreeMarker) correspondant aux représentations possibles (un template par format (HTML, JSON, Atom, etc.))
  • et éventuellement d’un fichier JavaScript.

Poursuite de l’exemple : on créé un WebScript qui va faire appel à la méthode getCreatedDocuments du service que l’on a créé précédemment (SimpleAuditService).

# 1. Création de la classe JAVA

Ce WebScript sera de type « DeclarativeWebScript » du fait que les données qu’il renverra seront mises en forme par un template.

Ce WebScript aura besoin du NodeService et du service que nous avons créé. Ces services seront injectés à l’aide de Spring.

Afin de pour pouvoir réceptionner ces services dans la classe Java du WebScript, il faut dans un premier temps définir des « setters ».

Fonctionnement :

Le fonctionnement du WebScript est simple, il va faire appel à notre service puis il va traiter les données qui lui seront renvoyées. Les résultats seront ensuite insérés dans le « model » qui sera transmis au template.

CreatedDocumentsGet.java
(Dans cette exemple, la période est défini par défaut, le WebScript va récupérer les fichiers créés lors des 7 derniers jours)

# 2. Création du fichier de description du WebScript

Nom du fichier : createddocuments.get.desc.xml

# 3. Création de templates

Ensuite, à l’aide de Freemarker, il possible d’effectuer le rendu que l’on souhaite (HTML, JSON, …). Voici deux exemples:

Rendu HTML : createddocuments.get.html.ftl

Rendu JSON : createddocuments.get.json.ftl

# 4. Injection Spring du Web Script

Il est important de ne pas oublier de lier la classe java (CreatedDocumentsGet.java) au WebScript, pour cela, il est nécessaire de créer un bean Spring, auquel on injectera les deux services dont on a besoin.

On active l’audit :

On se limitera d’auditer la méthode « create » du service « FileFolderService ».

Cet exemple est disponible ici sous la forme d’un module Alfresco, les sources complètes étant disponibles ici.

Cet exemple ne sera pas fonctionnel en l’état sur Alfresco 3.2 Entreprise.

Adresse pour accéder au WebScript (rendu HTML) :
http://adresse-serveur:port/alfresco/service/auditexample/CreatedDocuments.html

Adresse pour accéder au WebScript (rendu JSON) :
http://adresse-serveur:port/alfresco/service/auditexample/CreatedDocuments.json

Mise en forme / Application SURF :

AuditSurf a été construit à l’aide du Framework SURF (Framework web léger) et est basé sur les WebScripts. (Je vous renvoie vers l’article sur les fondamentaux de SURF, rédigé par Thomas Broyer).

Comportement SURF

Toute notre application SURF est contenue dans une seule page (hormis la connexion et la déconnexion qui sont gérées par deux autres pages). La page principale est découpée en une multitude de régions. Chacune de ces régions étant associée à un composant et chaque composant est lié à un WebScript SURF.

Tous les WebScripts SURF font appels à des WebScripts situés coté entrepôt Alfresco. Pour cela, on utilise des « endpoint » et des connecteurs pour communiquer (Je vous renvoie une nouvel fois vers l’article de Thomas Broyer, §4 de la section « Architecture »).

Ces connecteurs sont définis dans le fichier webscript-framework-config.xml, ils permettent de définir le mode d’accès (mais pas seulement) à l’entrepôt Alfresco (ou une autre source de données).

Nous avons utilisé comme brique de départ, l’excellent tutoriel de Ben Hagan disponible à adresse suivante : http://www.benh.co.uk/alfresco/surf-part-1-getting-started/

WebScripts SURF, récupération des données

Dans AuditSurf, on distingue deux familles de WebScript : ceux destinés à une mise en forme sous forme de « dashlets » (rendu HTML) et ceux destinés pour l’affichage des graphiques (JSON pour Open Flash Chart).

Chaque WebScript de notre extension SURF fait appel à un WebScript qui se situe coté entrepôt Alfresco. Les données récupérées, à l’aide des connecteurs, sont majoritairement des données au format JSON (cependant, ces données peuvent être parfois textuelles).

Ces données sont par la suite traitées afin de pouvoir générer un rendu graphique.

Ces WebScripts sont composés :

  • d’un fichier de description
  • d’un fichier JavaScript (pour se connecter à un WebScript Alfresco)
  • d’un template pour le rendu (HTML ou JSON pour les graphiques)
  • des fichiers .properties pour l’internationalisation


Schématisation du fonctionnement des WebScripts coté SURF

Voici un exemple de connexion à un WebScript « Alfresco » via un connecteur (fichier JavaScript) :

Il faut ensuite traiter les données (JSON dans le cas présent) afin de récupérer les informations qui nous intéressent.
Ces informations sont ensuite stockées dans le « model » afin que le template Freemarker du Web Script SURF puisse mettre en forme les données.

Le fichier Freemarker se charge ensuite de faire le rendu (soit en renvoyant du code HTML soit en renvoyant du JSON pour l’affichage des graphiques).

 

Mise en page

La mise en page de notre application SURF est assurée essentiellement par deux choses : d’une part OpenFlashChart pour la génération des graphiques (histogrammes dans notre cas) et d’autre part YUI pour tout ce qui est lié à la mise en page.

Open Flash Chart

Afin de mettre en valeur les statistiques, nous avons utilisé un projet de rendu graphique Open Source : Open Flash Chart 2.

Cet outil propose une API JavaScript (il existe aussi des librairies PHP, Perl, Python, Ruby, …) pour produire des graphiques en Flash. Les graphiques sont soignés, et offre d’excellentes capacités d’interaction.

Pour générer les graphiques, Open Flash Chart prend en entrée des données au format JSON.

La syntaxe du JSON pour Open Flash Chart est scindée en deux parties : une partie définissant la mise ne page du graphique et une autre partie contenant les données à proprement dit.

http://teethgrinder.co.uk/open-flash-chart-2/json-format.php

L’utilisation de cet outil nécessite l’installation de Flash coté client.

YUI

YUI est une librairie JavaScript développée par Yahoo (Yahoo User Interface). Cette librairie permet de mettre en place relativement facilement des effets tels que des animations, des panels, la gestion des cookies, etc… Alfresco utilise très largement cette librairie pour son interface SURF Alfresco Share.

YUI a été utilisé, dans AuditSurf, notamment pour :

  • créer des effets de transitions
  • l’affichage des popups d’information
  • le Drag & Drop des dashlets
  • et la gestion de cookies (pour se souvenir du positionnement des « dashlets »)

Pour finir

AuditSurf est disponible dans son intégralité au téléchargement sur la forge Alfresco : http://forge.alfresco.com/projects/auditsurf/

AuditSurf est compatible avec

  • les versions Entreprise : 3.0, 3.0.1, 3.1, 3.1.1 et 3.1.2 (cependant les informations JMX avec les versions 3.0.x sont limitées)
  • la version Entreprise 3.2
  • les versions Community 3.2 / 3.2r / 3.2r2

AuditSurf a été élu contribution du mois d’Août 2009 par Alfresco.