20 février 2008

Yahoo! Pipes : un cas d'école et quelques explications

Je me suis lancé il y a quelques semaines dans Yahoo! Pipes, outil de Yahoo de génération de fils RSS, mais dont les capacités vont bien au-delà. Justement, c'est cet "au-delà" que je voulais explorer, au-delà de Ponyfish et Feed43 qui permettent de générer des fils RSS à partir de pages qui n'en possèdent pas, mais présentent leurs informations sous forme de listes.

Au moment de commencer l'expérimentation de cet outil, j'ai voulu me documenter pour voir à quoi cela ressemblait. Remarques :
  1. il n'y a rigoureusement rien en français. Mais ce n'est pas le plus grave.
  2. Yahoo! ne donne pour ainsi dire aucune documentation : un seul exemple par fonction, et l'exemple est d'une pauvreté désolante. Donc je ne renvoie même pas à cette documentation.
A défaut d'autre solution, je me suis donc lancé dans le vide, j'ai produit quelques "pipes", et je vais en présenter un ici, en expliquant les modules un par un, du début à la fin.
J'espère que ça donnera une idée plus claire de ce que permet Yahoo! Pipes (car en dépit de sa documentation indigente, l'outil est extraordinaire, bien qu'encore en beta). C'est une forme de tutoriel ou mode d'emploi par l'exemple.
Je ne prétend pas, par ailleurs, avoir utilisé les fonctions le plus intelligemment du monde. Il est certain que j'aurais pu économiser de l'énergie en utilisant certains modules de Yahoo! Pipes de manière plus appropriée. J'ai fait comme j'ai pu et il vous reste à aller encore plus loin.

Voici le "pipe" que je vais vous présenter : http://pipes.yahoo.com/pipes/pipe.info?_id=0de3ef5e7c6a74ded3f7a584c2b82ba3
L'objectif était le suivant : l'association des archivistes d'Angers (AEDAA) donne sur son site internet une liste d'expositions en cours dans les centres d'archives français (en essayant d'être exhaustive).
J'ai voulu la transformer pour en faire :
  1. un fil RSS, avec un classement par date : en tête (les plus urgents, donc) les expositions qui se terminent bientôt.
  2. une projection cartographique : on visualise une carte avec de petites icônes, et chaque icône correspond à une exposition. On clique sur une icône pour obtenir le détail de l'expo.
Difficulté supplémentaire : chaque exposition indiquée n'est pas "cliquable" vers le site officiel du service d'archives. J'ai voulu restituer l'URL.

Evidemment, tout doit être fait automatiquement : dès que la liste est enrichie, le fil RSS, la carte et le lien sont générés dynamiquement.
Donc il faut traiter la liste de départ, pour la transformer progressivement, étape par étape, afin d'obtenir le résultat attendu à la fin.
Je vous invite à voir le code source de ce "pipe", puis à lire ce qui suit pour le comprendre.
[quand on crée un nouveau pipe, la partie de droite est vide. On choisit avec la souris le module à intégrer et on le glisse (par drag'n'drop) dans la partie de droite]


1.
D'abord, je choisis le module "Fetch Page", qui permet de traiter une page n'ayant pas de fil RSS. Dans cette page (champ URL), j'indique que la liste à transformer en fil RSS se trouve entre telle et telle balise.
Et dans cette liste chaque item est séparé du suivant par la balise HTML </h4>
Donc chaque "item.content" va contenir à chaque fois l'intégralité de l'item en code HTML. Je vais aller y piocher les informations qu'il me faut, pour les répartir aux bons endroits.

2.
Le module "loop" fait une boucle : pour chaque item défini plus haut (le contenu entre chaque balise <h4>) et où tout est mélangé, j'extrais une information sur le titre, avec des expressions Perl.
Je ne vais pas vous donner des cours de Perl (expressions régulières), alors j'explique juste le principe de cette formule :
Remplacer : [\d\D]*]*>([^<]*)[\d\D]*
Par : $1
= Dans ce qui a été récupéré (l'intégralité du contenu de chaque item) j'extrais ce qui se trouve entre les balises <a> et </a>, et je le place dans le "item.title".
Le résultat, c'est que chaque item a désormais un titre.
De même, il me faut attribuer à chaque item (par des loop) :
  • une "description" (c'est ce qui correspond au contenu d'un fil RSS, sous le titre),
  • un lien (vers lequel pointe chaque billet),
  • une géolocalisation pour projection cartographique.
3.
Ici, je reprends ce qui se trouve après le saut de ligne (balise <br>) pour le mettre dans la "description", c'est-à-dire le corps du message du fil RSS.
4.
J'ai passé un certain temps pour savoir comment construire une URL pointant automatiquement vers la page de présentation de l'exposition.
J'ai finalement utilisé la fonction "J'ai de la chance de Google". En effet pour n'importe quelle requête, vous pouvez pointer vers une liste de résultats Google.
Par exemple, si je veux vous indiquer ce que donne la recherche "numismatique" dans Google, je vous enverrai vers l'URL :
http://www.google.fr/search?q=numismatique&btnG
Mais en remplaçant à la fin btnG par btnI (ce qui correspond au code envoyé par le bouton "J'ai de la chance" de Google), j'obtiendrai non pas la liste des résultats, mais directement le premier résultat qui sort quand on chaque "numismatique" dans Google.
Essayez : http://www.google.fr/search?q=numismatique&btnI
Donc au lieu de chercher "numismatique", je vais lancer une requête Google avec ce qui se trouve dans le titre de chaque billet. Le titre a été défini à l'étape 2, et correspond exactement au titre de l'exposition.
Certains titres d'expositions sont un peu "flous" (ex. : "Travaux publics, travaux privés") et ne donnaient pas sur Google le résultat escompté. J'ai donc lancé la requête sur :
archives+exposition+"titre".
Les trois premières lignes du "loop" ci-dessus sont pour supprimer du titre toute apostrophe ' par un espace, parce qu'elles entraient en conflit avec les guillemets dans l'URL demandée à Google.
Il reste donc à Google à avoir un classement pertinent de ses résultats pour que le premier soit le bon !

Toutes les étapes suivantes sont consacrées à la géolocalisation : il faut extraire une notion de lieu, en récupérant l'indication du département (ou de la ville) dans des intitulés comme "AD du Tarn-et-Garonne", "AM de Marseille".
Le problème est que Yahoo est incapable de reconnaître certains départements au nom trop "flou" : la Creuse, les Landes.
En outre, tous les signes diacritiques (é, è, â) lui posent problème. Donc je suis obligé de remplacer les noms : Ardèche devient Ardeche, etc.
J'ai essayé de remplacer simplement les lettres (è devient e), mais il m'escamote alors la lettre suivante, et Ardèche devient Areche. C'est encore une version beta !
5.
Ici, j'extrais du titre (qui contient par exemple : "AD Haute-Garonne - Les Cathares : quelles sources pour l'histoire ?") l'indication du lieu (Haute-Garonne).
Je place le résultat dans un champ temporaire : item.loop:strregex (c'est Yahoo! qui me propose tout seul le nom de ce champ. Je le garde -- mais je pourrais lui donner un autre nom).

6.
Je remplace dans ce champ tous les mots accentués par les mêmes mots non accentués.
J'ajoute pour les départements problématiques le nom de la préfecture : "Creuse" devient "Creuse Guéret".
Je place le tout dans un nouveau champ : item.loop:strreplace.
7.
Encore une boucle : dans le résultat précédent, je rajoute le nom du pays, pour lui éviter de me localiser Paris au Texas !
A ce stade :
  • "AM Marseille" est devenu "Marseille FRANCE"
  • "Côtes d'Armor" est devenu "Cotes d'Armor FRANCE"
  • "Landes" est devenu "Landes Mont-de-Marsan FRANCE"
Je remets le résultat obtenu dans un nouveau champ (toujours proposé par Yahoo!). Je peux désormais utiliser la fonction qui va interroger Yahoo! Maps et reconnaît dans la valeur obtenue un nom de lieu
8.

"Location Builder" va chercher pour chaque item (Location Builder doit être inséré dans un module "Loop") la valeur obtenue précédemment.
Il lui attribue une longitude et une latitude.
Par exemple pour les AD de l'Ardèche, il me dit qu'il a dans item.y:location :
  • country: France
  • lat: 44.815340
  • lon: 4.373790
  • quality: 30 (qualité = niveau de précision de la localisation)
Il va ainsi placer le curseur sur la carte au centre du département. Pas sur la préfecture. A ce stade, je ne sais pas encore faire mieux, mais il existe une fonction "Yahoo! local" qui théoriquement sait trouver, pour un lieu indiqué (latitude et longitude), des services à proximité (5 miles, 10 miles, 20 miles). Mais il semble que les services d'archives ne sont pas référencés dans Yahoo! local. En outre, il faudrait chercher tantôt des services d'archives départementales, tantôt des services d'archives municipales...

Donc à ce stade, nous avons un fil RSS avec :
  • un titre
  • une "description" (= contenu du message)
  • une URL
  • une géolocalisation
Mais les items sont encore classés dans leur ordre de départ, à savoir par numéro de département.
Les étapes qui restent extraient une notion de date de fin (exposition jusqu'au 20 mars 2008, jusqu'au 30 juillet 2008, etc.) pour retrier l'ensemble, afin de faire apparaître en tête celles qui se terminent bientôt.
9.
C'est la "description" qui contient l'indication de date. Avec une expression régulière, je récupère la mention de jour et de mois (si elle existe) et l'indication de l'année.
Je suis obligé de séparer l'année, car Yahoo propose un "Date Builder" de même que son "Location Builder", et celui-ci fonctionne mieux si l'année est avant ("2008 Mars", plutôt que "Mars 2008").
Par ailleurs, il ne fonctionne que si les noms des mois sont en anglais. Je dois donc utiliser la fonction "Translate".
10.
Dans une nouvelle boucle, j'entre la valeur du champ obtenu juste avant, où j'avais interverti la l'année et le mois. Et je traduis cette valeur du français vers l'anglais.
J'obtiens une valeur en anglais :
"jusqu'au 28 mars 2008" est devenu : "2008, 28 March".
11.
Je fais une nouvelle boucle pour "construire" une date à partir de la valeur traduite.
Désormais, mon "pipe" sait que cette valeur est une date, il peut la traiter sous la forme normalisée "2008-03-28".
Cette valeur normalisée va me permettre de faire un tri.
J'aurais pu aller plus loin, et obtenir de Yahoo! Pipes une sortie au format ICal, c'est-à-dire un format plus ou moins standardisé qui permet à des calendriers de dialoguer : le fichier ICal obtenu aurait pu être rentré dans un Agenda Google, ou Netvibes, et on aurait pu naviguer dans cette liste d'expositions à la fois sous forme de liste (fil RSS), de carte géographique, et d'agenda.
Mais j'avoue que je fatigue un peu, et vous aussi sans doute.
12.
Voilà le tri : je prends l'information stockée dans le champ précédent (item.loop:datebuilder) et j'en fais un tri "ascendant".
Ouf ! une fonction toute simple.
13.
On sort du pipe.


Il n'est pas nécessaire de faire son premier pipe avec autant d'étapes. Les choses plus simples sont également autorisées. Mais j'ai choisi d'expliquer celui-ci précisément parce qu'il est complexe, et parce que j'ai beaucoup peiné sur certaines fonctions.
Yahoo! Pipes permet aussi plus simplement de fusionner deux fils RSS, de les trier de nouveau, etc.
Par exemple : si vous voulez savoir qui parle de votre blog, vous utiliser la recherche Yahoo! qui vous fournit un fil RSS + une recherche Google Blog Search + une recherche Technorati + Ask.com Blogs et Flux, vous fusionnez tout ça (fonction Union), puis vous dédoublonnez les résultats (car évidemment toutes ces requêtes vont souvent vous donner les mêmes réponses) avec la fonction Unique. Et ce sera très bien pour commencer.

Outil simple ou complexe ?
Beaucoup plus simple que de tout taper en code (il paraît que c'est possible avec des httpRequest).
Mais il faut connaître un peu de Perl (uniquement les expressions régulières), et maîtriser progressivement l'interface Yahoo! Pipes elle-même.
Surtout, il faut être capable de renoncer à toute documentation, et ça, c'est dur !
Par exemple, je n'ai toujours pas réussi à trouver comment insérer la carte obtenu sur un autre site (le mien, par exemple).
J'espère en tout cas que vous voyez à peu près tout ce que permet Yahoo! Pipes en terme de traitement des données : c'est assez prodigieux !

Libellés : , , ,

3 Commentaires:

Blogger Unknown a dit...

Bonjour,

Bien content d'avoir trouvé un utilisateur francophone de Yahoo Pipes. Je vais de ce pas me documenter sur Perl et les expressions régulières pour gérer mon problème d'accentués.
Cordialement,

14:42  
Anonymous Anonyme a dit...

Comment intégrer cela a son site aussi?

11:30  
Blogger Lully a dit...

Intégrer quoi, exactement ? Quel est le service espéré ? Quel est le type de site ?
Est-ce que l'idée serait de récupérer la carte créée ici pour l'intégrer dans votre site ? Ou de faire la même chose mais avec d'autres données ?
Bref, pouvez-vous préciser ?
Je serais tenté de dire que, a priori, tout est possible.

12:54  

Enregistrer un commentaire

<< Accueil

Mentions légales

MonnaieCe n'est pas un blog de collectionneur.
Je suis historien, un peu informaticien (j'adore les métadonnées !). D'où ce que vous pouvez lire ici.
Comme vous pouvez le constater, même si je le laisse en ligne, il n'est plus alimenté depuis longtemps.

Recherche sur le web numismate

Recherche dans les livres de numismatique de Google Book Search[...]

 

 

Généré par Blogger

Site Meter