dimanche 22 avril 2007

Ajax vers d'autres sites, sans proxy, JSON With Padding et Google AJAX Feed API

Ajax, c'est cool. Mais beaucoup d'entre vous aurons remarqué que les requètes AJAX doivent se limiter à appeler le site où est hébergée la page. Tout comme essayer de modifier une iframe situéee sur un autre domaine, appeler un autre site par Ajax provoque une erreur de sécurité.

Ceci est nécessaire afin de limiter autant que possible les attaques par "cross-scripting". Par exemple, si tel n'était pas le cas, il me suffirait de présenter un DIV avec un accès AJAX à GMail dans mon site et alors il me serait possible de voler tous vos idendentifiants (et donc votre compte) si jamais vous vous logguiez en passant par mon site...

Donc lorsqu'on veut inclure des flux RSS venant de l'extérieur ou permettre les requêtes AJAX vers l'extérieur, il faut mettre une place un proxy sur votre serveur. Par exemple, voici comment faire en java . Hélas ceci est complexe et a plein de défauts, notamment:
  1. vous chargez votre serveur alors qu'on pourrait très bien utiliser la puissance du client web qui vous visite.
  2. Il vous faut maîtriser la programmation serveur, c'est à dire que cela limite l'offre de service aux seuls avertis et cela limite donc globalement la qualité de l'offre par manque de concurrence.
  3. Il n'est pas forcément possible ou facile de mettre cela en oeuvre chez les hébergeurs mutualisés qui offrent les coût d'hébergement les plus faibles...
A) JSON with padding

Heureusement il existe des solutions. Le première soultion générique que je vais évoquer est JSON with padding. L'idéee générique est que si les requètes AJAX vers d'autres domaines sont interdites, il est tout à fait possible d'inclure dans sa page une feuille javascript provenant d'un autre site. Et on peut l'appeler par javascript depuis sa page. Mais surtout, il est possible de changer dynamiquement la source (attribut src) d'une page javascript inclue dans la page.

Le principe de JSON with padding est donc le suivant: on va 'inliner' une requète AJAX classique en une requète de type GET et cette requète GET sera l'url de l'attribut src de la feuille javascript à inclure.

Du coup, notre serveur, distant, s'il est conçu pour traiter les appels JSON with Padding, il va recevoir cette requète GET contenant un certain nombre de paramètre. Lui va traiter la requète et générer une feuille javascript correspondante dans la quelle il y a un objet javascript réponse sérializé au format JSON. Il va renvoyer cette feuille javascript en réponse. Là, notre client web reçoit la feuille de style et demande l'évaluation du code JSON qu'elle contient, c'est le format JSON with padding.

Vous êtes perplexes? Eh bien regarder cette démo qui notamment fait des recherches Google en AJAX sans taper sur le serveur qui héberge la démo, mais en appelant directement Google:
http://www.geocities.jp/stormriders999/jsontest.html
(cliquez sur Google, entrez un mot et enfin dépliez l'arbre de la réponse).
Vous pouvez aussi utiliser le plugin LiveHTTPHeaders pour Firefox pour vérifier que la requète AJAX par directement chez Google et que c'est Google qui répond.

B) Google entre en scène: AJAX Feed API

Vous l'avez vu, Google fournis déjà une API de recherche de ce type (mais aussi Yahoo, Del.ico.us, Amazon...). Mais ajourdh'ui, Google va plus loin, il fourni une API pour rechercher n'importe quel flux RSS qu'il aura mis dans ses caches!
Les détails sont fournis ici:
http://code.google.com/apis/ajaxfeeds/index.html

Mieux que ça, l'API traite de façon unifiée les différents types de flux: Atom 1.0, Atom 0.3, RSS 2.0, RSS 1.0, RSS 0.94, RSS 0.93, RSS 0.92, RSS 0.91, RSS 0.9. Au final, on se retrouve avec les éléments title, link, description, author et une liste de entries[]. Cette liste entries[] a elle même les élements suivant: title, link, content, contentSnippet, publishDate, et categories.

C'est dément. Cela veut par exemple dire que sur ce blog (dont je ne maître pas l'hébergement), je peux par exemple donner les dernières nouvelle parues sur le site du Monde. Avant ça n'était pas possible. Cela devrait démultiplier la puissance des échanges de flux, merci Google.

Aucun commentaire: