You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Web应用中Google账号登出功能异常问题求助

问题描述

我开发了一款需通过Google账号登录以查看对应账号日历事件的Web应用,目前遇到登出功能异常问题。使用两个用户账号测试时,登出其中一个账号,另一个账号的会话也无法保持,且两个账号的会话均未正确关闭。

负责登出的函数代码如下:

<!-- Google API -->
<script src="https://apis.google.com/js/api.js"></script>
<script src="https://accounts.google.com/gsi/client" async defer></script>

<script>

<!-- rest of code loadConfig()-->

async function handleLogoutClick() {
            console.log('Signing out of Google...');
            Swal.fire({
                title: 'Signing out of Google...',
                allowOutsideClick: false,
                didOpen: () => {
                    Swal.showLoading();
                },
            });

            try {
                const token = localStorage.getItem('googleAccessToken');
                if (token) {
                    // Revoke access token
                    await fetch(`https://accounts.google.com/o/oauth2/revoke?token=${token}`, {
                        method: 'POST',
                        headers: {
                            'Content-Type': 'application/x-www-form-urlencoded'
                        }
                    });
                    console.log('Token revocado correctamente');
                }

                localStorage.removeItem('googleAccessToken');
                localStorage.setItem('logoutCompletedG', 'true');
                console.log('Google session closed correctly');

                // Disable auto selection if necessary
                if (window.google && window.google.accounts && window.google.accounts.id) {
                    window.google.accounts.id.disableAutoSelect();
                } else {
                    console.error('Google Identity Services is not available.');
                }

                Swal.close();
                window.location.href = 'local.html'; // Redirect to local page after logout

            } catch (error) {
                console.error('Error revoking token:', error);
                Swal.close();
                Swal.fire({
                    icon: 'error',
                    title: 'Logout error',
                    text: 'An error occurred while trying to log out. Please try again later.'
                });
                console.error('Error signing out of Google', error);
            }
        }


<!-- rest of code initializeGapiClient(), fetchEvents(), renderCalendar(events)-->
</script>

控制台返回信息:

Signing out of Google...

Token revoked successfully

Google session closed correctly

Get failed to load: POST "https://accounts.google.com/o/oauth2/revoke?token={token}.
handleLogoutClick @VM162 google.html:26
click @ VM162 google.html:173
p @VM160 index.global.min.js:6
S @ VM160 index.global.min.js:6

补充说明:我尝试将access token撤销URL改为https://oauth2.googleapis.com/revoke,但仍出现400 (Bad Request)错误,问题未解决。这是我首次开发Google API相关应用。


解决方案

1. 修正Token撤销的请求格式

Google OAuth2的Token撤销接口要求参数通过请求体传递,而非URL参数,这是400错误的核心原因。修改撤销请求代码:

if (token) {
    const response = await fetch('https://oauth2.googleapis.com/revoke', {
        method: 'POST',
        headers: {
            'Content-Type': 'application/x-www-form-urlencoded'
        },
        body: `token=${token}` // 参数放在请求体中
    });

    if (!response.ok) {
        throw new Error(`Token revoke failed: ${response.statusText}`);
    }
    console.log('Token revoked successfully');
}

2. 正确终止Google账号会话

仅撤销Token和清理本地存储不足以结束Google账号会话,需调用Google Identity Services的signOut方法,确保当前账号会话被终止,同时不影响其他已登录账号:

if (window.google && window.google.accounts && window.google.accounts.id) {
    window.google.accounts.id.signOut({
        callback: () => {
            console.log('Google account signed out successfully');
        }
    });
} else {
    console.error('Google Identity Services is not available.');
}

3. 清理完整本地状态

移除所有与当前用户相关的本地存储项,避免残留状态干扰后续登录:

localStorage.removeItem('googleAccessToken');
localStorage.removeItem('logoutCompletedG');

4. 处理跨域请求备选方案

若直接使用fetch仍遇跨域问题,可通过gapi客户端调用撤销接口:

if (token) {
    await gapi.auth2.getAuthInstance().disconnect();
    console.log('Token revoked via gapi');
}

完整修正后的登出函数

async function handleLogoutClick() {
    console.log('Signing out of Google...');
    Swal.fire({
        title: 'Signing out of Google...',
        allowOutsideClick: false,
        didOpen: () => {
            Swal.showLoading();
        },
    });

    try {
        const token = localStorage.getItem('googleAccessToken');
        if (token) {
            const response = await fetch('https://oauth2.googleapis.com/revoke', {
                method: 'POST',
                headers: {
                    'Content-Type': 'application/x-www-form-urlencoded'
                },
                body: `token=${token}`
            });

            if (!response.ok) {
                throw new Error(`Token revoke failed: ${response.statusText}`);
            }
            console.log('Token revoked successfully');
        }

        localStorage.removeItem('googleAccessToken');
        localStorage.removeItem('logoutCompletedG');
        console.log('Local session data cleared');

        if (window.google && window.google.accounts && window.google.accounts.id) {
            window.google.accounts.id.signOut({
                callback: () => {
                    console.log('Google account session terminated');
                }
            });
        } else {
            console.error('Google Identity Services is not available.');
        }

        Swal.close();
        window.location.href = 'local.html';

    } catch (error) {
        console.error('Error during logout:', error);
        Swal.close();
        Swal.fire({
            icon: 'error',
            title: 'Logout error',
            text: 'An error occurred while trying to log out. Please try again later.'
        });
    }
}

内容的提问来源于stack exchange,提问作者Hugo Jiménez

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.21 15:40:54