Date de publication du RFC : Avril 2010
Auteur(s) du RFC : E. Hammer-Lahav
Pour information
Première rédaction de cet article le 3 mai 2010
Le protocole OAuth, déjà fréquemment déployé, voit son développement officiellement passer du côté de l'IETF, avec ce RFC 5849 qui reprend la description de la version 1 du protocole, pendant que le groupe de travail Oauth travaille à la version 2 (dont le premier document publié a été le RFC 6749, en octobre 2012).
OAuth, parent de OpenID, est un protocole d'authentification d'un tiers, le client, qui veut accéder à une ressource, par exemple un fichier, située sur un serveur et dont le contrôle revient à un propriétaire. (OpenID vise à authentifier un utilisateur humain, OAuth à authentifier la requête d'un programme, agissant pour le compte d'un humain.) Prenons un exemple (vous en trouverez d'autres dans le RFC, comme l'exemple classique de l'impression de photos, mais celui que j'indique a l'avantage d'être un exemple réel) : le service de microblogging Twitter permet à des utilisateurs (les propriétaires, dans la terminologie OAuth) de faire connaître au monde entier leurs pensées profondes en moins de 140 caractères. Le succès de ce service et l'existence d'une bonne (car très simple) API a poussé à l'arrivée de nombreux services tiers qui ont tous en commun de devoir accéder au compte Twitter de l'utilisateur (par exemple, Auto FollowFriday, Twibbon ou TwitterCounter - à noter que le premier des trois n'est pas encore passé à Oauth). Une façon possible, pour ces services, d'accéder au compte Twitter de l'utilisateur est de lui demander son nom et son mot de passe. On voit les conséquences que cela peut avoir pour la sécurité... OAuth fournit une meilleure solution : le serveur, en recevant la requête du client, demande au propriétaire l'autorisation :
Tout se fait par redirections HTTP (RFC 2616, section 10.3). Bien sûr, pour que cela soit sûr, il y a de nombreux détails à prendre en compte, ce qui explique les quarante pages du RFC.
OAuth existe depuis plusieurs années et était géré par un groupe informel (voir la section 1 du RFC pour un historique). Il est désormais documenté dans ce RFC 5849 (la version documentée n'a pas subi de changement significatif à l'IETF, c'est surtout une officialisation, avec quelques corrections de bogues, l'annexe A détaille ces changements ; le plus gênant est la refonte complète de la terminologie) et les nouvelles versions sont maintenant développées à l'IETF.
Une fois que Twitter a adopté ce protocole et documenté son usage, la plupart des services tiers l'ont intégré (par exemple Twibbon).
Lisons maintenant le RFC. Premièrement, le vocabulaire (section 1.1). Ce qui se jouait autrefois à deux (le client et le serveur) est désormais fréquemment une partie à trois (OAuth Love Triangle, dit Leah Culver), le client (client, Twibbon dans le cas plus haut), le serveur (server, Twitter dans le cas plus haut) et le propriétaire (resource owner, moi). Notez que la terminologie OAuth a changé avec ce RFC (par exemple, le propriétaire était nommé « utilisateur » - user).
Pour voir le cheminement complet d'une authentification OAuth, on
peut regarder la jolie
image de Yahoo (mais attention, elle utilise l'ancienne terminologie) ou bien suivre l'exemple de la section 1.2 du
RFC. Si le client, le service d'impression
printer.example.com
veut accéder aux photos
stockées sur le serveur photos.example.net
, et
dont le propriétaire est Jane :
oauth_token
).oauth_signature
).La requête initiale du client auprès du serveur pourra ressembler à :
POST /initiate HTTP/1.1 Host: photos.example.net Authorization: OAuth realm="Photos", oauth_consumer_key="dpf43f3p2l4k3l03", oauth_signature_method="HMAC-SHA1", oauth_timestamp="137131200", oauth_nonce="wIjqoS", oauth_callback="http%3A%2F%2Fprinter.example.com%2Fready", oauth_signature="74KNZJeDHnMBp0EMJ9ZHt%2FXKycU%3D"
Si le serveur renvoie le token
hh5s93j4hdidpola
,
la redirection de Jane vers le serveur pourra se faire via un URL
comme :
https://photos.example.net/authorize?oauth_token=hh5s93j4hdidpola
et, une fois l'authentification de Jane auprès du serveur et son
autorisation de la requête effectuées, le client pourra demander son
autorisation pour le token hh5s93j4hdidpola
:
POST /token HTTP/1.1 Host: photos.example.net Authorization: OAuth realm="Photos", oauth_consumer_key="dpf43f3p2l4k3l03", oauth_token="hh5s93j4hdidpola", oauth_signature_method="HMAC-SHA1", oauth_timestamp="137131201", oauth_nonce="walatlh", oauth_verifier="hfdp7dh39dks9884", oauth_signature="gKgrFCywp7rO0OXSjdot%2FIHF7IU%3D"
Et enfin, après encore un nouveau token, le client pourra demander la photo :
GET /photos?file=vacation.jpg&size=original HTTP/1.1 Host: photos.example.net Authorization: OAuth realm="Photos", oauth_consumer_key="dpf43f3p2l4k3l03", oauth_token="nnch734d00sl2jdk", oauth_signature_method="HMAC-SHA1", oauth_timestamp="137131202", oauth_nonce="chapoH", oauth_signature="MdpQcU8iPSUjWoN%2FUDMsK2sui9I%3D"
Voici pour le principe. Le reste du RFC est consacré aux détails. D'abord, comment obtenir son token ? Comme indiqué dans l'exemple, la méthode la plus courante est la redirection HTTP, normalisée en détail dans la section 2. Elle nécessite trois URL à connaître par le client. Par exemple, ceux de Twitter (apparemment documentés uniquement dans le source) sont :
https://twitter.com/oauth/request_token
(le terme
de request token fait référence à l'ancienne
terminologie, dans le RFC, vous trouverez le même concept sous le nom
de temporary credentials, cd. section 1.1),http://twitter.com/oauth/authorize
,https://twitter.com/oauth/access_token
.Comment authentifier toutes ces requêtes ? C'est le but de la section 3.
À noter qu'il existe
plusieurs méthodes, dépendant du serveur. Le paramètre
oauth_signature_method
indique celle choisie,
cela peut utiliser de la cryptographie asymétrique - cf. RFC 3447 -, un condensat
incluant un secret partagé - cf. RFC 2104 -, voire même du
texte brut, qui doit alors évidemment être emballé dans
https. Les sections 3.4 à 3.6 détaillent la
canonicalisation à pratiquer et autres formalités.
Le but de Oauth étant la sécurité, il n'est pas étonnant que la section résumant les questions de sécurité (section 4) soit longue. Parmi les points passés en revue :
Authorization:
(ce qui est permis : section 3.5.1), le relais ne peut pas savoir que
la ressource est protégée et risque donc de la distribuer après à
d'autres clients. Il faut donc, dans ce cas, utiliser
Cache-control:
pour l'en empêcher (section
4.4).oauth_consumer_key
et signature de la requête initiale), certes, mais le client peut être du
logiciel distribué avec son code source et, de
toute façon, un attaquant déterminé peut trouver les paramètres du
client même sans le code source, puisqu'il tourne sur une machine que
l'attaquant contrôle. Le serveur ne doit donc pas faire une confiance
aveugle que le client est bien celui qu'il prétend être (section
4.6).Un guide complet sur OAuth est disponible en http://hueniverse.com/oauth/guide/
. Une autre bonne introduction est « Gentle introduction to OAuth ». Parmi les applications
amusantes d'OAuth, un curl OAuthisé
en http://groups.google.com/group/twitter-api-announce/browse_thread/thread/788a1991c99b66df
. Un
exemple de programmation OAuth pour accéder à Twitter en
Python figure dans mon article. Fin 2012, la version 2 de
OAuth est en cours de finalisation à l'IETF,
mais de grosses incertitudes demeurent. Le premier RFC de la nouvelle
version est le RFC 6749.
Version PDF de cette page (mais vous pouvez aussi imprimer depuis votre navigateur, il y a une feuille de style prévue pour cela)
Source XML de cette page (cette page est distribuée sous les termes de la licence GFDL)