Il y a 14 ans -
Temps de lecture 4 minutes
Prenez le contrôle de Confluence avec Swizzle
Je vais vous révéler un secret à propos de notre célèbre Revue de Presse ! Elle est élaborée collectivement par l’ensemble des consultants de Xebia sous Confluence avant d’être publiée sur notre blog. L’utilisation d’un wiki permet de suivre facilement les différentes modifications (contribution, corrections, commentaires). Une fois celle-ci terminée, la page est archivée et une autre est créée, vide, afin de recevoir la prochaine version. La fin de l’année arrive, c’est l’heure de faire les statistiques 2008. L’une des questions que je me pose est « Quelle est la proportion des entrées de la revue de presse entre les différentes catégories (Actualité éditeurs / SSII, Agilité, RIA, SOA, …) ? »
Solution N°1 : Ouvrir dans le navigateur toutes les pages ‘Revue de Presse’ une par une et compter les entrées. Une revue de presses par semaine, 52 semaines … non
Solution N°2 : Utiliser une API. En effet Confluence expose ses principales fonctions par web services. Voici le wsdl. Plus de 7300 lignes, 238 opérations, 50 types. À ce moment-là, j’étais presque prêt à repasser à la solution N°1 quand je suis tombé au détour d’une recherche Google (Google est notre ami à tous !), sur le projet Swizzle…
Swizzle est un wrapper Java autour de l’api XML-RPC proposée par Confluence.
Installation
Rapide ! Swizzle est disponible dans le repository Maven
org.codehaus.swizzle swizzle-confluence 1.1
Principe
- Une seule classe,
org.codehaus.swizzle.confluence.Confluence
, permet d’accéder aux différents services. - Un ensemble de POJO qui servent de paramètres d’entrée et de retour. Exemple :
org.codehaus.swizzle.confluence.PageSummary
.
Se connecter
String endpoint = "https://the.confluence.of.xebia.com/confluence/rpc/xmlrpc"; confluence = new Confluence(endpoint); System.out.println("Connected to " + endpoint); String username = "bmoussaud"; String password = "tiger"; confluence.login(username, password);
Si vous êtes dérrière un proxy, initialiser les variables d’environnement suivantes:
System.getProperties().put("proxySet", "true"); System.getProperties().put("proxyHost", "17.240.34.194"); System.getProperties().put("proxyPort", "3128");
Retrouver une page
Les Revues de Presse sont archivées, comme l’ensemble du blog, par trimestre. Il faut donc :
- Retrouver la page correspondant à ce trimestre.
- Récupérer les pages filles.
- Filtrer pour ne garder que les articles « Revue de Presse ».
public ListgetRevuesDePresse(String quarter) throws Exception { List results = new ArrayList (); Page page = confluence.getPage("Espace Xebia France", quarter); //#1 List children = confluence.getChildren(page.getId()); //#2 for (PageSummary pageSummary : children) { if (pageSummary.getTitle().contains(REVUE_DE_PRESSE)) { //#3 results.add(pageSummary); } } return results; }
- Une page est identifiée par son Id représenté par un type
java.lang.String
. - La classe
PageSummary
contient les informations minimales d’une page :Id
,ParentId
,Title
,URL
. - La classe
Page
contient toutes les informations de la page, y compris son contenu.
Analyser le contenu d’une page
La Revue de Presse contient 6 catégories principales (Actualité éditeurs / SSII, Agilité, RIA, SOA, …). Elles sont hiérarchisées en niveau 3 (syntaxe wiki h3.
). Les différentes entrées de la revue de presse sont de niveau 4 (syntaxe wiki h4.
). Il faut donc :
- Récupérer le contenu de la page.
- Filtrer les titres de niveau 3 et 4.
- Effectuer le comptage.
public MapcountArticleByCategory(String pageId) throws Exception { String content = confluence.getPage(pageId).getContent(); // #1 String currentCategory = null; String currentEntry = null; Pattern h3h4 = Pattern.compile("(^h3|^h4) .(.*)", Pattern.MULTILINE); // #2 Matcher matcher = h3h4.matcher(content); Map categories = newMap(); while (matcher.find()) { //entrées vides if (matcher.group().contains("...") || matcher.group().contains("..")) continue; // niveau 3 if ("h3".equals(matcher.group(1))) { // #2 currentCategory = matcher.group(2).trim(); categories.put(currentCategory, 0); continue; } // niveau 4 if ("h4".equals(matcher.group(1))) { // #2 currentEntry = matcher.group(2); if (currentCategory != null && categories.containsKey(currentCategory)) { int c = categories.get(currentCategory); categories.put(currentCategory, ++c); // #3 } } } return categories; }
Conclusion
Il suffit maintenant :
- D’assembler les deux méthodes.
- De dumper les informations au format CSV.
- D’ouvrir Excel.
- De construire un tableau croisé dynamique.
et vous n’aurez pas les résultats !!
Pour en revenir à Swizzle / Confluence : l’encapsulation proposée est correcte et performante. Le seul point négatif : toutes les méthodes de la classe Confluence
lancent des java.lang.Exceptions
, non typées. Elles sont dans l’ensemble le résultat d’un comportement de type Runtime
. J’aurais donc préféré une signature finissant par throws RuntimeException
.
L’api permet également :
- D’obtenir des informations sur l’historique des pages et des contributeurs, les commentaires, l’état de la page (nombre de verrous, supprimées, …).
- De créer, déplacer et détruire des pages et des espaces.
Exemple : archivage des revues de presse :
void run(String newParent) throws Exception { System.out.println("Archivage des Revues de Presse dans "+newParent); myConfluence = new MyConfluence(); ListdraftedRevuesDePresse = myConfluence.getDraftedRevuesDePresse(); int count = 0; for (PageSummary pageSummary : draftedRevuesDePresse) { if (pageSummary.getTitle().startsWith("DRAFT")) continue; myConfluence.moveTo(pageSummary,newParent); } System.out.println("Total "+count); } //.... public void moveTo(PageSummary pageSummary, String newParent) throws Exception { Page targetPage = confluence.getPage("XF", newParent); Page page = confluence.getPage(pageSummary.getId()); System.out.println("Change Parent from '" + confluence.getPage(page.getParentId()).getTitle() + "' to '" + targetPage.getTitle() + "'"); page.setParentId(targetPage.getId()); //Changement de Parent confluence.storePage(page); //Applique les modifications }
Swizzle propose également un wrapper sur les API exposées par Jira.
Note: Swizzle ne fonctionne que si l’option « API à distance (XML-RPC & SOAP) » est activée.
Commentaire
3 réponses pour " Prenez le contrôle de Confluence avec Swizzle "
Published by Alexis MP , Il y a 14 ans
WSDL qui pousse à faire du JAX-RPC? Pouah!
A quand une interface JAX-RS?
Published by Franck , Il y a 14 ans
Et le résultat des statistiques ?
Published by Nicolas , Il y a 14 ans
A quand un bêtisier 2008 sur les perles de la programmation comme l’an dernier ?
Nicolas