oauth - 帐户链接成功,但访问令牌显示无效 - Google OAuth
问题描述
我一直在尝试使用我的 Dialogflow 帐户链接的隐式流程来实现 Google OAuth 服务(使用此文档)
我已经根据该文档开发了代码。当用户链接他的帐户并显示“您已成功,将您的帐户与聊天机器人链接”时,它可以正常工作。
但是当我尝试使用我在该文档的第 3 步中生成的访问令牌时,它说访问令牌无效。看起来它没有在 Google 服务中注册!
这是我实现它的代码
import os
import flask
from flask import request, redirect
import string
import random
from random import choice, randint
import google_auth_oauthlib.flow
from AES import AESCipher
import json
CLIENT_SECRETS_FILE = "client_secret.json"
SCOPES = ['https://www.googleapis.com/auth/userinfo.profile', 'https://www.googleapis.com/auth/userinfo.email']
app = flask.Flask(__name__)
app.secret_key = 'SECRET_KEY'
#
# Actions on google call this function with client_id, redirect_uri, state, and response_type
#
@app.route('/auth')
def authorize():
flow = google_auth_oauthlib.flow.Flow.from_client_secrets_file(
CLIENT_SECRETS_FILE, scopes=SCOPES)
flow.redirect_uri = flask.url_for('oauth2callback', _external=True)
print ("%%%%STATE", request.args["state"])
authorization_url, state = flow.authorization_url(
access_type='offline',
include_granted_scopes='true')
flask.session['state'] = request.args["state"]
print ("IN AUTH STATE ", state)
return flask.redirect(authorization_url)
def get_user_id():
min_char = 8
max_char = 12
allchar = string.ascii_letters + string.punctuation + string.digits
password = "".join(choice(allchar) for x in range(randint(min_char, max_char)))
return password
@app.route('/oauth2callback')
def oauth2callback():
print ("### IN CALLBACK ###", request)
state = flask.session['state']
user_id = get_user_id()
client_id = ''.join(random.sample("Google", len("Google")))
key = ''.join(random.sample("JayPatel", len("JayPatel")))
bytes_obj = {
'user_id': user_id,
'client_id': client_id
}
access_token = AESCipher("Jay").encrypt(json.dumps(bytes_obj))
access_token = access_token.replace('+', 'p')
access_token = access_token.replace('&', '1')
# My generated access_token looks like
# 6u2PeFcUtNmAblw5N3YAKSn7EC46xQVmgv3Rc8XK9sTW4xcgAxw1doRsvmgE/CC2qGUJ1x7XpNpdYvGes6qJHIEQSwvgEJt8hnYEUbm0qEA=
print ("###### Access Token ", access_token)
print ("###### State ", state)
url = "https://oauth-redirect.googleusercontent.com/r/test-happierbot-4c514#access_token=" + access_token + "&token_type=bearer&state=" + state
return redirect(url)
if __name__ == '__main__':
os.environ['OAUTHLIB_INSECURE_TRANSPORT'] = '1'
app.run('localhost', 8080, debug=True)
当我尝试https://www.googleapis.com/oauth2/v1/tokeninfo?access_token=my_generated_token
通过API使用 access_token获取信息时,它给出了
{
"error": "invalid_token",
"error_description": "Invalid Value"
}
是否有任何其他过程来激活 access_token 或者我 错过了任何步骤?
解决方案
如果我正确地遵循代码,您正在生成自己的访问令牌以返回给用户,然后使用谷歌的“tokeninfo”端点来查看令牌是否有效?
谷歌不知道你的令牌是什么或意味着什么,所以它返回它是无效的。助理使用您的服务获取令牌,并在发送来自用户的消息时返回它。否则,它只是将其视为不记名令牌。
您的服务应根据您想要的任何方式确定其有效性(在表格中查找它,反转解密和验证它的过程,检查有效签名等)。由于 Google 对令牌一无所知,因此无法确定它是否真的有效。
tokeninfo 服务返回有关Google 生成的令牌的信息。
Google 不允许您将其令牌端点用于 OAuth 帐户链接。相反,您可以使用Google 登录助手,这将为您提供一个 id 令牌。您可以通过网站将其与常规 Google 登录一起使用,以获取访问令牌和刷新令牌,您可以使用这些令牌在获得用户许可的情况下访问用户的 Google 资源。(有关更多详细信息,请参阅此 Stack Overflow 答案。)
推荐阅读
- ruby - 是否可以保留传递给延迟作业的模型中的跟踪更改?
- android-espresso - AWS Device Farm 是否支持 Android Orchestrator?
- android - 我可以将安卓应用的照片保存在 SD 卡上吗?
- c# - 在每个循环迭代中创建对象
- cassandra-3.0 - Cassandra jmx 指标缺失
- angular - 如何让 forEach 等待订阅完成?
- java - 如何自动将 jar 从 s3 部署到 aws lambda?
- java - 从列表活动中的路径显示和播放我的音频文件
- java - 增强了字符串的 for 循环
- c# - 异步 Lambda 函数