GoogleUser.getAuthResponse() 不包含 access_token
GoogleUser.getAuthResponse() doesn't contain access_token
UPDATE2: 我重新审视了这个问题,并通过仔细遵循下面链接的 doco 解决了这个问题。但首先,对于那些为此苦苦挣扎的人,你们是好伙伴。 Google 的 doco 版本太多,令人困惑!您在 html 中包含 platform.js 或 client.js 吗?你加载 gapi.auth 还是 gapi.auth2?你用的是gapi.auth2.render还是gapi.auth.authorize,还是gapi.auth2.init等等
returns 和 access_token(截至本文日期)的链接方式如下。通过仔细遵循指南和使用 platform.js 的参考,我成功地完成了这项工作。然后使用 gapi.load('drive', callback).
动态加载其他库,例如 client.js
https://developers.google.com/identity/sign-in/web/listeners
https://developers.google.com/identity/sign-in/web/reference
==== 繁荣的原始问题 ====
更新 1:
我更新了代码示例以对 googleUser 对象进行递归搜索。至少这不应该在后续库中中断。
下面是一个代码片段,用于处理 Google gapi.auth2.AuthResponse 对象中的 access_token 不在顶层...它被隐藏的问题: (在物体的深处!
所以它是可检索的,但不是在顶层!!??我注意到这似乎是一个时间问题......一旦应用程序在后续检查中 运行 一段时间,它确实包含顶层的访问令牌!!
var authResponse = _.googleUser.getAuthResponse();
_.id_token = authResponse.id_token; // Always exists
// access_token should also be a param of authResponse
if (authResponse.access_token) {
debug("Worked this time?");
_.access_token = authResponse.access_token;
} else {
// !!! Internal object access !!!
debug("Attempt to get access token from base object.");
_.access_token = _.objRecursiveSearch("access_token", _.googleUser);
if (_.access_token) {
debug("Access token wasn't on authResponse but was on the base object, WTF?");
} else {
debug("Unable to retrieve access token.");
return false;
}
}
_.objRecursiveSearch = function(_for, _in) {
var r;
for (var p in _in) {
if (p === _for) {
return _in[p];
}
if (typeof _in[p] === 'object') {
if ((r = _.objRecursiveSearch(_for, _in[p])) !== null) {
return r;
}
}
}
return null;
}
我猜 getAuthResponse 会在准备就绪后以某种方式提供回调,但我看不到 API 中的哪个位置。
https://developers.google.com/identity/sign-in/web/reference
找到解决办法。事实证明,如果我们不在 gapi.auth2.init 中提供登录范围配置,它就不会在 中 return access_token ]getAuthResponse。请拨打 gapi。auth2.init 如下所示,access_token 将出席。
gapi.auth2.init({
client_id: <googleClientID>,
'scope': 'https://www.googleapis.com/auth/plus.login'
})
我知道这个问题已经很老了,但是在谷歌搜索“.getAuthResponse() 没有 access_token”时它首先出现,这就是我来到这里的方式。
所以对于你们这些在 2016 年(也许更晚)的人来说,这是我发现的
.getAuthResponse
上有一个秘密论点,我发现 任何地方 都没有记录。如果您要 运行 在您的应用程序中使用以下内容
console.log(gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse);
您会看到以下内容(copy/pasted 来自我的控制台)
function (a){if(a)return this.hg;a=.HE;var c=.rf(this.hg);!a.Ph||a.dL||a.Lg||(delete c.access_token,delete c.scope);return c}
这表明 .getAuthResponse()
函数在寻找一个参数,据我所知甚至没有检查它的值——它只是检查它是否存在,然后 returns整个对象。没有那个函数,剩下的代码 运行s 我们可以很清楚地看到它删除了两个键:access_token
和 scope
.
现在,如果我们使用和不使用参数调用此函数,我们可以检查输出的差异。 (注意:我使用 JSON.stringify 因为试图从我的浏览器控制台 copy/paste 对象导致了一些问题)。
console.log(JSON.stringify(gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse()));
console.log(JSON.stringify(gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse(true)));
getAuthResponse() 对象
{
"token_type":"Bearer",
"login_hint":"<Huge mess of letters>
",
"expires_in":2112,
"id_token":"<insert your ridiculously long string here>
",...}
getAuthResponse(true) 对象
{
"token_type":"Bearer",
"access_token":"<an actual access token goes here>
",
"scope":"<whatever scopes you have authorized>
",
"login_hint":"<another mess of letters>
",
"expires_in":2112,
"id_token":"<Insert your ridiculously long string here>
",
...}
UPDATE2: 我重新审视了这个问题,并通过仔细遵循下面链接的 doco 解决了这个问题。但首先,对于那些为此苦苦挣扎的人,你们是好伙伴。 Google 的 doco 版本太多,令人困惑!您在 html 中包含 platform.js 或 client.js 吗?你加载 gapi.auth 还是 gapi.auth2?你用的是gapi.auth2.render还是gapi.auth.authorize,还是gapi.auth2.init等等
returns 和 access_token(截至本文日期)的链接方式如下。通过仔细遵循指南和使用 platform.js 的参考,我成功地完成了这项工作。然后使用 gapi.load('drive', callback).
动态加载其他库,例如 client.jshttps://developers.google.com/identity/sign-in/web/listeners https://developers.google.com/identity/sign-in/web/reference
==== 繁荣的原始问题 ====
更新 1: 我更新了代码示例以对 googleUser 对象进行递归搜索。至少这不应该在后续库中中断。
下面是一个代码片段,用于处理 Google gapi.auth2.AuthResponse 对象中的 access_token 不在顶层...它被隐藏的问题: (在物体的深处!
所以它是可检索的,但不是在顶层!!??我注意到这似乎是一个时间问题......一旦应用程序在后续检查中 运行 一段时间,它确实包含顶层的访问令牌!!
var authResponse = _.googleUser.getAuthResponse();
_.id_token = authResponse.id_token; // Always exists
// access_token should also be a param of authResponse
if (authResponse.access_token) {
debug("Worked this time?");
_.access_token = authResponse.access_token;
} else {
// !!! Internal object access !!!
debug("Attempt to get access token from base object.");
_.access_token = _.objRecursiveSearch("access_token", _.googleUser);
if (_.access_token) {
debug("Access token wasn't on authResponse but was on the base object, WTF?");
} else {
debug("Unable to retrieve access token.");
return false;
}
}
_.objRecursiveSearch = function(_for, _in) {
var r;
for (var p in _in) {
if (p === _for) {
return _in[p];
}
if (typeof _in[p] === 'object') {
if ((r = _.objRecursiveSearch(_for, _in[p])) !== null) {
return r;
}
}
}
return null;
}
我猜 getAuthResponse 会在准备就绪后以某种方式提供回调,但我看不到 API 中的哪个位置。 https://developers.google.com/identity/sign-in/web/reference
找到解决办法。事实证明,如果我们不在 gapi.auth2.init 中提供登录范围配置,它就不会在 中 return access_token ]getAuthResponse。请拨打 gapi。auth2.init 如下所示,access_token 将出席。
gapi.auth2.init({
client_id: <googleClientID>,
'scope': 'https://www.googleapis.com/auth/plus.login'
})
我知道这个问题已经很老了,但是在谷歌搜索“.getAuthResponse() 没有 access_token”时它首先出现,这就是我来到这里的方式。
所以对于你们这些在 2016 年(也许更晚)的人来说,这是我发现的
.getAuthResponse
上有一个秘密论点,我发现 任何地方 都没有记录。如果您要 运行 在您的应用程序中使用以下内容
console.log(gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse);
您会看到以下内容(copy/pasted 来自我的控制台)
function (a){if(a)return this.hg;a=.HE;var c=.rf(this.hg);!a.Ph||a.dL||a.Lg||(delete c.access_token,delete c.scope);return c}
这表明 .getAuthResponse()
函数在寻找一个参数,据我所知甚至没有检查它的值——它只是检查它是否存在,然后 returns整个对象。没有那个函数,剩下的代码 运行s 我们可以很清楚地看到它删除了两个键:access_token
和 scope
.
现在,如果我们使用和不使用参数调用此函数,我们可以检查输出的差异。 (注意:我使用 JSON.stringify 因为试图从我的浏览器控制台 copy/paste 对象导致了一些问题)。
console.log(JSON.stringify(gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse()));
console.log(JSON.stringify(gapi.auth2.getAuthInstance().currentUser.get().getAuthResponse(true)));
getAuthResponse() 对象
{ "token_type":"Bearer", "login_hint":"
<Huge mess of letters>
", "expires_in":2112, "id_token":"<insert your ridiculously long string here>
",...}
getAuthResponse(true) 对象
{ "token_type":"Bearer", "access_token":"
<an actual access token goes here>
", "scope":"<whatever scopes you have authorized>
", "login_hint":"<another mess of letters>
", "expires_in":2112, "id_token":"<Insert your ridiculously long string here>
", ...}