FACEBOOK开发过程用的官方提供的SDK,TWITTER用的开源TWITTER4J,为我在公司开发的解决方案。
整个过程很简单
Oauth协议
一、产生背景:校内网希望去提取用户的MSN好友列表,有一种方法是(的确曾经用过,还记得吗?):要求用户在校内的一个导入页面输入MSN用户名密码,然后MSN以用户的角色去访问MSN,获得列表。该方法存在很大的安全隐患:校内能够保证不保存我们的MSN密码么?鬼才信!为了解决这个问题,OAuth诞生了。
二、协议理解:校内可以用一个特殊的ID号去访问MSN好友列表,并且MSN承认这个ID号,如何获得这个ID号呢?首先校内请求MSN的一个开放地址: msn.com/oauth/input_password?key=key_xiaonei&callback=xiaonei.com/wait,现在控制权转移到了msn。msn在input_password页面中让用户输入用户名密码以登陆msn(这是安全的,因为input_password页面位于msn站点内,校内无法控制)成功登陆msn后(如果不成功呢?说明非法呗!),msn会对key校内进行签名得到一个key_public_msn,然后把这个key_public_msn传给xiaonei: xiaonei.com/wait?key=key_public_msn,从此以后,校内用key_public_msn来访问msn即可,msn肯定会承认key_public_msn。以上是通俗的口语化理解,如果想看官方的说明请链接:http://oauth.net。
在官方网站的首页,可以看到下面这段简介:
An open protocol to allow secure API authorization in a simple and standard method from desktop and web applications.
大概意思是说OAUTH是一种开放的协议,为桌面程序或者基于BS的web应用提供种简单的,标准的方式去访问需要用户授权的API服务。
1. 简单:不管是OAUTH服务提供者还是应用开发者,都很容易于理解与使用;
2. 安全:没有涉及到用户密钥等信息,更安全更灵活;
3. 开放:任何服务提供商都可以实现OAUTH,任何软件开发商都可以使用OAUTH;
三、Oauth认证授权流程
OAUTH认证授权的流程进行初步认识。其实,简单的来说,OAUTH认证授权就三个步骤,三句话可以概括:
1. 获取未授权的Request Token
2. 获取用户授权的Request Token
3. 用授权的Request Token换取Access Token
当应用拿到Access Token后,就可以有权访问用户授权的资源了。这三个步骤对应OAUTH的三个URL服务地址嘛。上面的三个步骤中,每个步骤分别请求一个URL,并且收到相关信息,并且拿到上步的相关信息去请求接下来的URL直到拿到Access Token。
具体每步执行信息如下:
A. 使用者(第三方软件)向OAUTH服务提供商请求未授权的Request Token。向Request Token URL发起请求。
B. OAUTH服务提供商同意使用者的请求,并向其颁发未经用户授权的oauth_token与对应的oauth_token_secret,并返回给使用者。
C. 使用者向OAUTH服务提供商请求用户授权的Request Token。向User Authorization URL发起请求,请求带上上步拿到的未授权的token与其密钥。
D. OAUTH服务提供商将引导用户授权。该过程可能会提示用户,你想将哪些受保护的资源授权给该应用。此步可能会返回授权的Request Token也可能不返回。
E. Request Token 授权后,使用者将向Access Token URL发起请求,将上步授权的Request Token换取成Access Token。
F. OAUTH服务提供商同意使用者的请求,并向其颁发Access Token与对应的密钥,并返回给使用者。
G. 使用者以后就可以使用上步返回的Access Token访问用户授权的资源。
从上面的步骤可以看出,用户始终没有将其用户名与密码等信息提供给使用者(第三方软件),从而更安全。
四、OAUTH服务提供商
OAUTH标准提出到现在不到两年,但取得了很大成功。不仅提供了各种语言的版本库,甚至Google,Yahoo,Microsoft等等互联网大头都 实现了OAUTH协议。由于OAUTH的client包有很多,所以我们就没有必要在去自己写,避免重复造轮子,直接拿过来用就行了。
五、开发Twitter申请access_token流程案例
OAuth中有三方:一,用户;二,Consumer;三,服务提供商。
一,Consumer 向 服务提供商 申请接入权限 ,必须先注册Twitter账户,然后注册个app
如上图流程,申请成功后可得到:Consumer Key,Consumer Secret。
twitter申请oauth的话,在 setting - connection - developer 里面申请。 同时给出三个访问网址:
request_token_url = 'http://twitter.com/oauth/request_token'
access_token_url = 'http://twitter.com/oauth/access_token'
authorize_url = 'http://twitter.com/oauth/authorize'
二,当Consumer接到用户请求想要访问第三方资源(如twitter)的时候
Consumer需要先取得 请求另牌(Request Token)。网址为上面的 request_token_url,参数为:
oauth_consumer_key:Consumer Key
oauth_signature_method:签名加密方法
oauth_signature:加密的签名 (这个下面细说)
oauth_timestamp:UNIX时间戳
oauth_nonce:一个随机的混淆字符串,随机生成一个。
oauth_version:OAuth版本,可选,如果设置的话,一定设置为 1.0
oauth_callback:返回网址链接。
及其它服务提供商定义的参数
这样 Consumer就取得了 请求另牌(包括另牌名 oauth_token,另牌密钥 oauth_token_secret。
Request token: rSsphqrC2737ejnC0iR7FipCPPenM3w2uiPdsun8
Request token secret: f7JUiNfcKIwcKO239FSSOUctQTLF8fICwLu6aEc1tg
二,浏览器自动转向服务提供商的网站:
网址为 authorize_url?oauth_token=请求另牌名
http://api.twitter.com/oauth/authorize?oauth_token=rSsphqrC2737ejnC0iR7FipCPPenM3w2uiPdsun8
四,用户同意 Consumer访问 服务提供商资源
那么会自动转回上面的 oauth_callback 里定义的网址。同时加上 oauth_token (就是请求另牌),及 oauth_verifier(验证码)。
五,现在总可以开始请求资源了吧?
NO。现在还需要再向 服务提供商 请求 访问另牌(Access Token)。网址为上面的 access_token_url,参数为:
oauth_consumer_key:Consumer Key
oauth_token:上面取得的 请求另牌的名
oauth_signature_method:签名加密方法
oauth_signature:加密的签名 (这个下面细说)
oauth_timestamp:UNIX时间戳
oauth_nonce:一个随机的混淆字符串,随机生成一个。
oauth_version:OAuth版本,可选,如果设置的话,一定设置为 1.0
oauth_verifier:上面返回的验证码。
请求 访问另牌的时候,不能加其它参数。
这样就可以取得 访问另牌(包括Access Token 及 Access Token Secret)。这个就是需要保存在 Consumer上面的信息(没有你的真实用户名,密码,安全吧!)
oauth.consumerSecret=q59l1i8Vp5Fyg94ymYmCjrKVfOVK3qMKlo3x7qYAw
oauth.accessToken=228953071-Rd7Wy7G4tTbTZErm2d1cQgmRJlAgCxlwM4QFLsxb
oauth.accessTokenSecret=rrIWfaHZFhpnts6sz2AaeJB4DhJ31aJMUfNCFaORc
oauth.consumerKey=Q6U1JxawFIflghwX8eNFLA
六,取得 访问另牌 后,
Consumer就可以作为用户的身份访问 服务提供商上被保护的资源了。提交的参数如下:
oauth_consumer_key:Consumer Key
oauth_token:访问另牌
oauth_signature_method:签名加密方法
oauth_signature:加密的签名
oauth_timestamp:UNIX时间戳
oauth_nonce:一个随机的混淆字符串,随机生成一个。
oauth_version:OAuth版本,可选,如果设置的话,一定设置为 1.0
及其它服务提供商定义的参数
参考文献:
[1] http://blog.csdn.net/maray/archive/2010/04/13/5482216.aspx
[2] http://menglimengwai.javaeye.com/blog/496250
[4] http://jsx112.javaeye.com/blog/844858