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

如何使用@atproto/oauth-client-browser搭建atproto OAuth客户端回调页?

纯HTML/TypeScript环境下atproto OAuth回调页实现示例

以下是适配你需求的完整回调页实现,基于@atproto/oauth-client-browser和@atproto/api,完全采用纯HTML+TypeScript结构:

1. 回调页HTML结构(redirect.html)

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>登录回调</title>
    <script type="module" src="./callback-handler.ts"></script>
</head>
<body>
    <p>正在处理登录,请稍候...</p>
</body>
</html>

2. TypeScript回调处理逻辑(callback-handler.ts)

import { createOAuthClient } from '@atproto/oauth-client-browser';
import { BskyAgent } from '@atproto/api';

// 初始化OAuth客户端
const oauthClient = createOAuthClient({
  clientId: 'https://hammouda101010.github.io/turbowarp-bsky-api/static/client-metadata.json',
  redirectUri: 'https://hammouda101010.github.io/turbowarp-bsky-api/redirect.html',
  scope: 'atproto transition:generic',
});

async function handleCallback() {
  try {
    // 从URL中提取授权码和状态参数
    const code = new URLSearchParams(window.location.search).get('code');
    const state = new URLSearchParams(window.location.search).get('state');

    if (!code || !state) {
      throw new Error('授权参数缺失');
    }

    // 交换授权码获取访问令牌
    const tokenResponse = await oauthClient.exchangeCodeForToken(code, state);
    
    // 可选:初始化BskyAgent并设置令牌
    const agent = new BskyAgent({ service: 'https://bsky.social' });
    await agent.login({
      accessJwt: tokenResponse.accessToken,
      refreshJwt: tokenResponse.refreshToken,
      handle: tokenResponse.idTokenClaims?.handle || '', // 从ID Token中提取用户handle
    });

    // 向父窗口(弹窗发起页)发送登录成功信息
    window.opener?.postMessage({
      type: 'BSKY_LOGIN_SUCCESS',
      tokens: {
        accessToken: tokenResponse.accessToken,
        refreshToken: tokenResponse.refreshToken,
      },
      userHandle: tokenResponse.idTokenClaims?.handle,
    }, window.origin);

    // 关闭回调弹窗
    window.close();
  } catch (err) {
    console.error('回调处理失败:', err);
    // 向父窗口发送错误信息
    window.opener?.postMessage({
      type: 'BSKY_LOGIN_ERROR',
      error: err instanceof Error ? err.message : '未知错误',
    }, window.origin);
  }
}

// 页面加载后立即处理回调
window.addEventListener('load', handleCallback);

关键注意事项

  • DPOP令牌绑定:你的客户端元数据中开启了dpop_bound_access_tokens,@atproto/oauth-client-browser会自动处理DPOP证明的生成与验证,无需额外编码。
  • 弹窗通信安全:使用window.postMessage时必须指定目标origin,避免跨域安全风险。
  • 令牌存储:建议将获取到的令牌存储在localStorage或会话存储中,供主应用后续调用atproto接口使用。
  • 状态参数验证:state参数用于防止CSRF攻击,客户端会自动验证其有效性,无需手动校验。

内容的提问来源于stack exchange,提问作者Hammouda101010

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.14 17:16:00