我正在尝试使用以下测试类通过 python manage.py test
测试 drf-social-oauth2 与 Google 的集成:
class DRFSocialOAuthIntegrationTest(TestCase):
def setUp(self):
self.test_user = UserModel.objects.create_user("test_user", "test@user.com", TEST_USER_PASSWORD)
self.application = Application(
name="Test Application",
redirect_uris="",
user=self.test_user,
client_type=Application.CLIENT_CONFIDENTIAL,
authorization_grant_type=Application.GRANT_PASSWORD, # https://github.com/jazzband/django-oauth-toolkit/blob/master/oauth2_provider/models.py
)
self.application.save()
# Every test needs a client.
self.client = Client()
def tearDown(self):
self.application.delete()
self.test_user.delete()
def test_drf_social_oauth2_integration(self):
'''Following testing steps found at curl -X POST -d "grant_type=convert_token&client_id=<django-oauth-generated-client_id>&client_secret=<django-oauth-generated-client_secret>&backend=google-oauth2&token=<google_token>" http://localhost:8000/auth/convert-token'''
def convert_google_token(self):
'''
Convert Google token to our access token
curl -X POST -d "grant_type=convert_token&client_id=<client_id>&client_secret=<client_secret>&backend=google-oauth2&token=<google_token>" http://localhost:8000/auth/convert-token
'''
return self.client.post(
'/auth/convert-token',
{
'grant_type': 'convert_token',
'client_id': self.application.client_id,
'client_secret': self.application.client_secret,
'backend': 'google-oauth2',
'token': <google_token>
}
)
这似乎工作正常,但我必须通过手动导航到 google_token
来继续喂它 https://developers.google.com/oauthplayground/?code=<my_code>&scope=email+profile+https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fuserinfo.email+https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fuserinfo.profile+openid&authuser=0&prompt=consent#
:
在那里,我点击“令牌的交换授权代码”按钮,获取访问令牌,然后将该访问令牌粘贴到 token
中请求的 convert_google_token()
参数中。这感觉不是很自动化。我不确定是否应该只单击复选框,以便自动刷新访问令牌,因此不必在 convert_google_token()
中对其进行编辑。或者也许我应该以编程方式获取该访问令牌。但我相信这将需要首先获得授权代码,这也必须以编程方式进行,因为它是一次性代码,对吗?
因此,为了获得该授权码,我尝试像这样解析来自 developers.google.com/oauthplayground/
的 html 响应:
def get_google_authorization_code_html():
import requests
return requests.post(
'https://developers.google.com/oauthplayground/',
json={
'code': <my_code>,
'scope': "email+profile+https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fuserinfo.email+https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fuserinfo.profile+openid",
'authuser': "0",
'prompt': "consent"
}
)
response = get_google_authorization_code_html() #;print(f'Google authorization code html returned: {response.content=}')
self.assertEqual(response.status_code, 200)
from bs4 import BeautifulSoup
soup = BeautifulSoup(response.content) ;print('Google authorization code html return: '); print(soup.prettify())
但是,在浏览器中显示授权码的输入元素在 html 响应中实际上是空白的,所以我无法从那里检索它。这甚至是解决此问题的正确方法吗?我可能缺少关键知识,因为我对 OAuth2、Django 和测试还很陌生。我一直在努力阅读它,特别是在这个 Medium article 中找到的图表让我觉得我或多或少走在正确的轨道上,但我不确定。