> ## Documentation Index
> Fetch the complete documentation index at: https://docs.beeos.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# OAuth 2.1 流程

> MCP 客户端的 OAuth 2.1 + PKCE 鉴权。

MCP Gateway 为符合 spec 的 MCP 客户端实现 **OAuth 2.1 + PKCE**。
这是 Claude Desktop、MCP Inspector 这类交互式桌面应用的推荐鉴权方式。

<Note>
  OAuth 2.1 不是唯一路径。MCP Gateway 同样接受 BeeOS 其他部分用的 bearer token：

  * **`Authorization: Bearer bak_…`** —— 绑定到目标智能体的
    [Agent API Key](/zh/authentication)。最适合 server-to-server 集成
    和无头 worker；不用浏览器跳转。
  * **`Authorization: Bearer oag_…`** —— 用户拥有的智能体可用
    [User API Key](/zh/authentication)。智能体创建者跑的脚本很合适。

  调用方是交互式终端用户驱动的 MCP 客户端（Claude Desktop、ChatGPT 桌面、
  MCP Inspector）就用 OAuth；其他场合用 API key。
</Note>

## 流程概览

```mermaid theme={null}
sequenceDiagram
    participant Client as MCP Client
    participant GW as MCP Gateway
    participant Web as BeeOS Web App
    participant Auth as Auth Service

    Client->>GW: POST /oauth/register
    GW-->>Client: client_id

    Client->>GW: GET /oauth/authorize
    Note over Client,GW: code_challenge, redirect_uri, state
    GW->>Web: 302 redirect to /mcp-login
    Web->>Auth: user authenticates
    Auth-->>Web: login_ticket
    Web->>GW: redirect with _bt=ticket
    GW-->>Client: 302 redirect with ?code=...&state=...

    Client->>GW: POST /oauth/token
    Note over Client,GW: code, code_verifier
    GW-->>Client: access_token (HS256 JWT)

    Client->>GW: POST /{agentId}/mcp
    Note over Client,GW: Authorization: Bearer token
```

## Step 1：动态客户端注册

注册新 OAuth 客户端。按 MCP Authorization spec，只支持 public client
（无 `client_secret`）。

```bash theme={null}
curl -s -X POST "https://mcp.beeos.ai/oauth/register" \
  -H "Content-Type: application/json" \
  -d '{
    "client_name": "my-mcp-client",
    "redirect_uris": ["http://localhost:5173/callback"]
  }' | jq
```

响应：

```json theme={null}
{
  "client_id": "mcp_client_abc123",
  "client_name": "my-mcp-client",
  "redirect_uris": ["http://localhost:5173/callback"]
}
```

## Step 2：授权请求

生成 PKCE code verifier 和 challenge，然后跳转用户：

```
GET https://mcp.beeos.ai/oauth/authorize
  ?client_id=mcp_client_abc123
  &redirect_uri=http://localhost:5173/callback
  &response_type=code
  &code_challenge=E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM
  &code_challenge_method=S256
  &state=random_state_value
```

Gateway 把浏览器重定向到 BeeOS web app 登录页。用户认证后浏览器被
重定向回你的 `redirect_uri`，带授权码：

```
http://localhost:5173/callback?code=auth_code_xyz&state=random_state_value
```

## Step 3：换 token

用授权码换 access token：

```bash theme={null}
curl -s -X POST "https://mcp.beeos.ai/oauth/token" \
  -H "Content-Type: application/x-www-form-urlencoded" \
  -d "grant_type=authorization_code" \
  -d "code=auth_code_xyz" \
  -d "client_id=mcp_client_abc123" \
  -d "redirect_uri=http://localhost:5173/callback" \
  -d "code_verifier=dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk" | jq
```

响应：

```json theme={null}
{
  "access_token": "eyJhbGciOiJIUzI1NiIs...",
  "token_type": "Bearer",
  "expires_in": 3600
}
```

## Step 4：用 token

MCP 请求带上 access token：

```bash theme={null}
curl -s -X POST "https://mcp.beeos.ai/${AGENT_ID}/mcp" \
  -H "Authorization: Bearer eyJhbGciOiJIUzI1NiIs..." \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/list"}'
```

## 发现端点

MCP 客户端用这些 well-known 端点发现 OAuth 服务器：

| 端点                                            | 用途                                     |
| --------------------------------------------- | -------------------------------------- |
| `GET /.well-known/oauth-authorization-server` | OAuth 2.1 授权服务器元数据（RFC 8414）           |
| `GET /.well-known/oauth-protected-resource`   | MCP Protected Resource Metadata（指向 AS） |

```bash theme={null}
curl -s "https://mcp.beeos.ai/.well-known/oauth-authorization-server" | jq
```

## Token 细节

| 属性      | 值                          |
| ------- | -------------------------- |
| 算法      | HS256                      |
| 默认 TTL  | 60 分钟                      |
| 授权码 TTL | 120 秒                      |
| 客户端类型   | 仅 public（无 client\_secret） |

<Warning>
  授权码 120 秒过期。重定向回调后尽快换。
</Warning>

## 401 响应行为

请求鉴权失败时，gateway 返回：

```
HTTP/1.1 401 Unauthorized
WWW-Authenticate: Bearer realm="MCP", resource_metadata="/.well-known/oauth-protected-resource"
```

符合 spec 的 MCP 客户端用 `resource_metadata` URL 发现授权服务器并
自动启动 OAuth 流程。
