Redirect_uri在抓取和间隙中不匹配

时间:2019-01-15 21:03:22

标签: google-oauth2 google-api-js-client

致力于将用户连接到Google,我们正在尝试从Google api获取他们的访问权限并刷新令牌,并且在交换OAuth2代码以获取令牌时遇到了问题。两组代码都有相同的错误。

我初始化gapi客户端并按如下所示填写所需的信息:

gapi.load('client:auth2', _ => {
        gapi.client.init({
            'apiKey': 'omitted for security',
            clientId: 'omitted for security',
            'scope': 'https://www.googleapis.com/auth/drive',
            'discoveryDocs': ['https://www.googleapis.com/discovery/v1/apis/drive/v3/rest']    
        }).then(_ => {
            gapi.auth2.getAuthInstance().grantOfflineAccess().then(resp => {
                if(resp.code){
                    gapi.client.request({
                        path: 'https://www.googleapis.com/oauth2/v4/token',
                        method: 'post',
                        params: {code: resp.code},
                        body: {
                            code: resp.code,
                            client_id: opts.clientId,
                            client_secret: 'omitted for security',
                            grant_type: 'authorization_code',
                            redirect_uri: 'omitted for security',
                            access_type: 'offline'
                        },
                    }).then((onfulfill, onreject, context) => {
                        console.log('fulfilled', onfulfill);
                        console.log('rejected: ', onreject);
                        console.log('context', context);
                    }).catch(err => console.error(err.body));
                }
            });

        });
    });

我要在.then()中执行的操作是调用令牌端点,以在响应中交换代码以获取刷新和访问令牌,以存储在我的后端和用户的本地存储中。

我从两个版本的代码中都得到了这个错误响应。 (这里提供了更好,更可靠的代码。)

  

{“错误”:“ redirect_uri_mismatch”,“错误说明”:“错误   请求”}

我还有一个作为最后手段的后端设置,它接受来自gapi.auth2.getAuthInstance().grantOfflineAccess()的代码,调用令牌端点,并将access_tokenrefresh_token返回给客户端。

此代码相似,但不完全相同。而不是使用google api库,我使用了fetch,它工作正常。 (前端的Fetch和XHR与gapi.client.request函数具有相同的问题。...)

const gConfig = require('./basic.json');
const scopes = ['https://www.googleapis.com/auth/drive'];

const { client_id, client_secret, redirect_uris } = gConfig.web;
const authClient = new google.auth.OAuth2(client_id, client_secret, redirect_uris[0]);

app.post('/', (req, res) => {
    const { code } = req.body;
    console.log('Received Code From Request: ', code);

    let data = { code , client_id, client_secret,redirect_uri: redirect_uris[0], grant_type: 'refresh_token'};

    let encodedParams = Object.keys(data).map(k => encodeURIComponent(k) + '=' + encodeURIComponent(data[k])).join('&');


    fetch(
        `https://www.googleapis.com/oauth2/v4/token?code=${code}`,
        { method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded' }, body: encodedParams }
    ).then((res) => {
        console.log('called the api with fetch');
        console.dir(res.json());
    });

    authClient.getToken(code, (err, token) => {
        if (err) {
            console.error(err);
            res.status(500).json(err);
        }
        // console.dir(token);
        console.log('TOKEN: =>', token);
        res.json(token);
    });
});

在前端成功完成此操作的人吗?

1 个答案:

答案 0 :(得分:0)

您无法在浏览器中获得刷新令牌。您的示例代码只能在服务器上运行。要在客户端执行oauth,您应该请求“令牌”而不是“代码”。