jueves, 9 de septiembre de 2010

Autentificación con OAuth en Twitter utilizando oauthtwitter.py

Como venían anunciando desde hace algún tiempo, desde el 31 de agosto de 2010, Twitter ya no permite que las aplicaciones se autentifiquen utilizando "Basic Authentication" (mandar el usuario y contraseña en la petición http, resumiendo).

El método que debe utilizarse ahora es OAuth, una especie de estándar para que aplicaciones y clientes se autentifiquen sin proporcionar credenciales. Facebook, Linkedin, Twitter y otros servicios similares lo utilizan.

El caso es que un script que actualizaba periódicamente (programado como tarea cron) el "timeline" de una cuenta ya no funciona y hay que reescribirlo para que utilice OAuth.

En la página de Twitter recomiendan varias librerías para diferentes lenguajes, para Python mencionan, entre otras, oauth-python-twitter2.

Esta librería es muy fácil de utilizar y se adecúa perfectamente a mis necesidades. Para utilizarla debemos instalar los módulos oauth2 y simplejson. En mi equipo (corre Ubuntu) es tan fácil como esto:
$ sudo apt-get install python-simplejson
$ sudo easy_install oauth2

Una vez instalados, ya podemos utilizar la librería.

OAuth para "dummies" como yo


Voy a resumir mucho cómo funciona OAuth en Twitter.

Lo primero que tenemos que hacer es crear una aplicación cliente en Twitter. Al terminar se nos proporcionarán dos claves que debemos guardar como oro en paño: "Consumer key" y "Consumer secret".

Con este par de claves se solicita a Twitter un "request token", un valor temporal que utilizaremos para pedirle permiso al usuario de nuestra aplicación y que nos deje actuar en su cuenta.

El usuario otorga permiso a nuestra aplicación (aunque la aplicación esté asociada a nuestra cuenta, incluso debemos autorizarla para que acceda a nuestra cuenta) a través de una interfaz web. Si registramos nuestra aplicación como un servicio web, al autorizar el usuario a nuestra aplicación, llegarán a nuestro servicio web claves nuevas que serán permanentes (oauth token y oauth secret token).

Si la aplicación no la registramos como servicio web, sino como "Desktop", cuando el usuario aprueba nuestra aplicación, Twitter le da un "PIN" (como el del teléfono móvil) que deberá introducir en la aplicación "Desktop". Con este PIN, Twitter nos proporciona entonces los oauth token y oauth secret token.
Este último es mi caso, mi script, a todos los efectos, es como un cliente "Desktop".

Con estos oauth tokens que Twitter nos da cuando el usuario autoriza a nuestra aplicación, ya podemos interaccionar con la cuenta del usuario, ahora nuestra aplicación se autentificará en Twitter con las claves "consumer" y los "oauth token".

Utilizando oauth-python-twitter2


Antes de nada: hay un pequeño bug en el código del autor: hay que comentar la línea 82. También hay que tener instalados los módulos oauth2 y simplejson.

El primer script que prepararemos sólo lo utilizaremos una vez, para dar permiso a la aplicación que hemos creado que pueda actuar en nuestra cuenta. Está basado en el script que acompaña a la librería oauth-python-twitter2:
#!/usr/bin/python
# -*- coding: utf-8 -*-
# autorizacion-usuario.py
from oauth import oauth
from oauthtwitter import OAuthApi
consumer_key = "LA CLAVE DE MI APLICACIÓN"
consumer_secret = "LA CLAVE SECRETA DE MI APLICACIÓN"
# Autenficación
twitter = OAuthApi(consumer_key, consumer_secret)
# Capturamos solicitud de autorización, primero credenciales temporales
temp_credentials = twitter.getRequestToken()
# Muestra la URL para que el usuario autorice a nuestra aplicación
print(twitter.getAuthorizationURL(temp_credentials))
# Capturamos el PIN y pedimos credenciales definitivas
oauth_verifier = raw_input('¿Cuál es el PIN? ')
access_token = twitter.getAccessToken(temp_credentials, oauth_verifier)
# Mostramos los token: estos ya no cambiarán
print("oauth_token: " + access_token['oauth_token'])
print("oauth_token_secret: " + access_token['oauth_token_secret'])

Una vez que lo hemos ejecutado, pegado en el navegador la URL para autorizar a la aplicación y proporcionado el PIN, tendremos unas credenciales permanentes (los oauth_token) para la cuenta de usuario. Vamos a utilizarlas:

#!/usr/bin/python
# -*- coding: utf-8 -*-
# actualizar-status.py
import sys
from oauth import oauth
from oauthtwitter import OAuthApi
consumer_key = "LA CLAVE DE MI APLICACIÓN"
consumer_secret = "LA CLAVE SECRETA DE MI APLICACIÓN"
oauth_token = "EL TOKEN QUE NOS DEVOLVIÓ EL SCRIPT ANTERIOR"
oauth_token_secret = "EL TOKEN QUE NOS DEVOLVIÓ EL SCRIPT ANTERIOR"
twitter = OAuthApi(consumer_key, consumer_secret, oauth_token, oauth_token_secret)
twitter.UpdateStatus("Esto es una prueba")

Hemos actualizado el "timeline" de la cuenta de usuario que autorizó nuestra aplicación. Sencillo a más no poder ;-)

P.S.: Al final he acabado utilizando en el trabajo, por cuestiones de compatibilidad, una librería en PHP: twitteroauth