Authlib强大OAuth框架入门

7次阅读

共计 2326 个字符,预计需要花费 6 分钟才能阅读完成。

基于 Python 的 Authlib 是集所有主流 WebAPI 权限认证协议的客户端、服务端、底层实现、高层架构于一身的强大工具库。
参考官方:Authlib: Python Authentication
Authlib 几乎是能将 RFC 所有相关的 API 认证协议都包括进来了,甚至从协议的底层实现、高层架构,从客户端到服务端都能实现的,当之无愧称为 Monolithic project 的一个项目。
目前 Authlib 支持的 Authentication 协议有:

OAuth 1.0
OAuth 2.0
JWT
many more…

安装:
$ pip install Authlib
Oauth2.0 客户端验证
参考官方:Authlib – Client Guide – OAuth 2 Session
Authlib 中用来登录验证 OAuth2.0 的对象叫 Session,其中包括了所有相关的验证所需方法函数。
from authlib.client import OAuth2Session

# 生成 session,用来之后的创建 URL、获取 token、刷新 token 等所有动作
session = OAuth2Session(
client_id=’Your Client ID’, client_secret=’Your Client Secret’,
scope=’user:email’, # 这个授权范围根据每个 API 有所不同
redirect_uri=’https://MyWebsite.com/callback’
)

# 生成 URL
uri, state = session.create_authorization_url(
‘https:// 目标网址的授权入口 /authorize’
)
print(uri)

#「手动」打开浏览器访问 URI,登录 API 帐户,点击授权,然后获取最终的 URL
# 或者自己有服务器的话,可以自己接收
#。。。
# 将 callback 返回的 URL 复制下来,因为其中包含授权 code
authorization_response = ‘https://MyWebsite.com/callback?code=42..e9&state=d..t’

# 用获得的 Code 去访问 access_token 入口
tokens = session.fetch_access_token(
access_token_url=’https:// 目标网址的授权入口 /api/access_token’,
authorization_response=authorization_response
)
print(tokens) #返回字典格式: {‘access_token’: ‘e..ad’, ‘token_type’: ‘bearer’, ‘scope’: ‘user:email’}

# 过期后,刷新 token。需重建 session 对象:
session = OAuth2Session(
client_id=’Your Client ID’, client_secret=’Your Client Secret’,
scope=’user:email’, state=state, redirect_uri=’https://MyWebsite.com/callback’
)
new_tokens = session.refresh_token(
access_token_url, refresh_token=tokens[‘refresh_token’]
)
print(‘[Refreshed tokens]:’, new_tokens)

设置的 callback 或 redirect_url 不存在怎么获取 Code?
在调试过程中,如果我们向上面一样手动去打开浏览器复制 URL,再复制回应过来的 URL 是很麻烦的。
Oauth2 的逻辑就是:要求各种客户自己在自己的浏览器里登录帐户,然后给你的 App 授权。所以这一步 redirect_url 是躲不过的。但是我们测试过程中,还没来得及专门建一个服务器或网页来接收这个 callback 回调怎么办呢?有办法!
方法一:直接截取
我们可以在第一次登录并授权后,复制 cookies,然后在测试中直接使用 requests 带着 cookies 登录信息去访问,就不再需要手动打开浏览器了:
raw_cookies = “”” 这里是你复制过来的 cookies “””
cookies = dict([line.split(“=”, 1) for line in raw_cookies.strip().split(“; “)])

try:
r = requests.get(uri, cookies=cookies, allow_redirects=True)
except requests.exceptions.ConnectionError as e:
print(‘[Final URL]: ‘, e.request.url )
authorization_response = e.request.url
由于你最开始设置的 callback 是公网上的某个网址,应该是不存在的(只要你没有设置的话)。所以,这里去 request 的时候,肯定会报错,且是 ConnectionError。所以我们可以将最终报错的 URL 获取到,这个里面就包含了我们想要的 Code 码。
方法二:更改本地 hosts
如果本地已经搭建了测试服务器,比如 Nginx 或 Flask,这种方法更简单。
比如在供应商中设定的 redirect_url 为 http://example.com/callback,那么只需简单编辑 hosts:
# /etc/hosts

127.0.0.1 example.com
那么,只要本机设置了 Nginx 或 Flask 等服务器,只需要获取 127.0.0.1/callback 即可得到需要的内容。

正文完
 0