Files
claude-code-mirror/claude-code-中文Wiki/05-服务层详解.md
2026-04-03 13:01:19 +08:00

22 KiB
Raw Permalink Blame History

Claude Code 服务层详解

概述

服务层services/)是 Claude Code 的核心业务逻辑层,提供 API 通信、协议管理、数据处理等功能。本文档详细介绍各服务的职责、实现和协作关系。


1. services/api/ - Anthropic API 客户端

client.ts - API 客户端工厂

文件位置: src/services/api/client.ts

核心功能: 创建配置好的 Anthropic API 客户端实例。

支持的认证方式:

1. 直接 API 访问

// 环境变量: ANTHROPIC_API_KEY

2. AWS Bedrock

// 环境变量配置
AWS_REGION  AWS_DEFAULT_REGION
ANTHROPIC_SMALL_FAST_MODEL_AWS_REGION (可选,用于 Haiku 模型)
  • 支持 AWS_BEARER_TOKEN_BEDROCK 进行 API Key 认证
  • 支持自动凭证刷新

3. Azure Foundry

// 环境变量
ANTHROPIC_FOUNDRY_RESOURCE  ANTHROPIC_FOUNDRY_BASE_URL
ANTHROPIC_FOUNDRY_API_KEY (可选)
  • 支持 Azure AD 认证(DefaultAzureCredential
  • 支持自定义回调端口

4. Google Vertex AI

// 环境变量
VERTEX_REGION_* (模型特定区域)
CLOUD_ML_REGION (默认区域)
ANTHROPIC_VERTEX_PROJECT_ID
  • 支持 google-auth-library 凭证系统
  • 防止元数据服务器超时

关键函数:

export async function getAnthropicClient({
  apiKey,
  maxRetries,
  model,
  fetchOverride,
  source,
}: {
  apiKey?: string
  maxRetries: number
  model?: string
  fetchOverride?: ClientOptions['fetch']
  source?: string
}): Promise<Anthropic>

请求拦截:

  • 注入自定义头:x-app: cli, User-Agent, X-Claude-Code-Session-Id
  • 支持 ANTHROPIC_CUSTOM_HEADERS 环境变量自定义头
  • 支持 x-anthropic-additional-protection
  • 生成客户端请求 ID (x-client-request-id) 用于追踪

代理支持:

fetchOptions: getProxyFetchOptions({ forAnthropicAPI: true })

claude.ts - API 调用封装

文件位置: src/services/api/claude.ts

核心功能:

  • queryModelWithStreaming() - 流式查询模型
  • getMaxOutputTokensForModel() - 获取模型最大输出 token
  • getPromptTooLongTokenGap() - 解析 prompt 太长错误
  • PROMPT_TOO_LONG_ERROR_MESSAGE - 错误消息常量

filesApi.ts - 文件 API

功能: 处理文件上传到 Claude API。

errors.ts - 错误处理

核心类型:

export const PROMPT_TOO_LONG_ERROR_MESSAGE =
  'Conversation too long. Press esc twice to go up a few messages and try again.'

export function startsWithApiErrorPrefix(text: string | null): boolean
export function isPromptTooLongError(error: Error): boolean

withRetry.ts - 重试逻辑

功能: 提供指数退避重试机制。

export async function withRetry<T>(
  fn: () => Promise<T>,
  options: {
    maxRetries?: number
    initialDelayMs?: number
    maxDelayMs?: number
  }
): Promise<T>

usage.ts - 使用量追踪

功能: 追踪 API 调用使用量(输入/输出 token


2. services/mcp/ - Model Context Protocol

类型系统 (types.ts)

配置作用域 (ConfigScope):

z.enum(['local', 'user', 'project', 'dynamic', 'enterprise', 'claudeai', 'managed'])

传输类型 (Transport):

z.enum(['stdio', 'sse', 'sse-ide', 'http', 'ws', 'sdk'])

服务器配置:

// Stdio 配置
McpStdioServerConfigSchema = z.object({
  type: z.literal('stdio'),
  command: z.string(),
  args: z.array(z.string()),
  env: z.record(z.string()),
})

// SSE 配置
McpSSEServerConfigSchema = z.object({
  type: z.literal('sse'),
  url: z.string(),
  headers: z.record(z.string()),
  oauth: McpOAuthConfigSchema,
})

// WebSocket 配置
McpWebSocketServerConfigSchema = z.object({
  type: z.literal('ws'),
  url: z.string(),
  headers: z.record(z.string()),
})

连接状态类型:

ConnectedMCPServer = { client, name, type: 'connected', capabilities, serverInfo, cleanup }
FailedMCPServer = { name, type: 'failed', error }
NeedsAuthMCPServer = { name, type: 'needs-auth' }
PendingMCPServer = { name, type: 'pending', reconnectAttempt }
DisabledMCPServer = { name, type: 'disabled' }

useManageMCPConnections.ts - 连接管理 Hook

文件位置: src/services/mcp/useManageMCPConnections.ts

核心职责:

  1. 初始化 MCP 客户端连接
  2. 设置连接生命周期处理器
  3. 管理自动重连SSE 连接)
  4. 同步 appState

关键特性:

自动重连

  • 最大重试次数: 5
  • 初始退避: 1000ms
  • 最大退避: 30000ms
  • 指数退避策略

通知处理器

// 工具列表变更
client.client.setNotificationHandler(ToolListChangedNotificationSchema, ...)

// 提示列表变更
client.client.setNotificationHandler(PromptListChangedNotificationSchema, ...)

// 资源列表变更
client.client.setNotificationHandler(ResourceListChangedNotificationSchema, ...)

通道推送 (KAIROS 特性)

// 注册通道通知处理器
client.client.setNotificationHandler(ChannelMessageNotificationSchema, async notification => {
  enqueue({
    mode: 'prompt',
    value: wrapChannelMessage(client.name, content, meta),
    priority: 'next',
    isMeta: true,
  })
})

channelNotification.ts - 通道通知

功能: 处理 MCP 服务器的通道消息通知。

channelPermissions.ts - 通道权限

功能: 管理通道权限回调。

auth.ts - MCP 认证

功能: 处理 MCP 服务器的 OAuth 认证流程。

oauthPort.ts - OAuth 端口管理

功能: 管理 OAuth 回调端口。

elicitationHandler.ts - 信息请求处理

功能: 处理 MCP 服务器的信息请求elicitation

normalization.ts - 工具名称规范化

功能: 规范化 MCP 工具名称,避免命名冲突。


3. services/oauth/ - OAuth 2.0 认证

文件位置: src/services/oauth/index.ts

OAuthService 类

核心功能: 实现 OAuth 2.0 授权码流程(支持 PKCE

export class OAuthService {
  async startOAuthFlow(
    authURLHandler: (url: string, automaticUrl?: string) => Promise<void>,
    options?: {
      loginWithClaudeAi?: boolean
      inferenceOnly?: boolean
      expiresIn?: number
      orgUUID?: string
      loginHint?: string
      loginMethod?: string
      skipBrowserOpen?: boolean
    }
  ): Promise<OAuthTokens>
}

两种授权流程:

1. 自动流程

  • 打开浏览器,跳转到授权页面
  • 用户在浏览器中完成授权
  • 回调到本地监听服务器

2. 手动流程

  • 显示手动授权 URL
  • 用户复制 URL 到浏览器
  • 用户复制授权码回来

核心步骤:

  1. 创建本地授权码监听器 (AuthCodeListener)
  2. 生成 PKCE 值(code_verifier, code_challenge
  3. 构建授权 URL
  4. 等待授权码
  5. 交换令牌

client.ts - OAuth 客户端

功能: 与 OAuth 服务器通信。

export async function exchangeCodeForTokens(
  code: string,
  state: string,
  codeVerifier: string,
  port: number,
  isManual: boolean,
  expiresIn?: number
): Promise<OAuthTokenExchangeResponse>

export function buildAuthUrl(opts: {
  codeChallenge: string
  state: string
  port: number
  isManual: boolean
  loginWithClaudeAi?: boolean
  inferenceOnly?: boolean
  orgUUID?: string
  loginHint?: string
  loginMethod?: string
}): string

crypto.ts - 加密工具

功能: PKCE 加密操作。

export function generateCodeVerifier(): string
export function generateCodeChallenge(verifier: string): string
export function generateState(): string

auth-code-listener.ts - 授权码监听

功能: 启动本地 HTTP 服务器监听 OAuth 回调。

export class AuthCodeListener {
  async start(): Promise<number>  // 返回监听端口
  waitForAuthorization(state: string, onReady: () => Promise<void>): Promise<string>
  handleSuccessRedirect(scopes: string[]): void
  handleErrorRedirect(): void
  close(): void
}

4. services/lsp/ - Language Server Protocol

manager.ts - LSP 管理器

文件位置: src/services/lsp/manager.ts

核心接口:

export interface LSPServerManager {
  getAllServers(): Map<string, LSPServerInstance>
  getServer(name: string): LSPServerInstance | undefined
  getServerCapabilities(name: string): ServerCapabilities | undefined
  initialize(): Promise<void>
  shutdown(): Promise<void>
}

初始化流程:

  1. initializeLspServerManager() - 初始化管理器单例
  2. createLSPServerManager() - 创建管理器实例
  3. registerLSPNotificationHandlers() - 注册通知处理器

状态管理:

type InitializationState = 'not-started' | 'pending' | 'success' | 'failed'

关键函数:

export function getLspServerManager(): LSPServerManager | undefined
export function isLspConnected(): boolean
export async function waitForInitialization(): Promise<void>
export function reinitializeLspServerManager(): void  // 用于 /reload-plugins
export async function shutdownLspServerManager(): Promise<void>

LSPServerInstance.ts - 服务器实例

功能: 管理单个 LSP 服务器实例。

LSPClient.ts - LSP 客户端

功能: 实现 LSP 协议客户端逻辑。

LSPDiagnosticRegistry.ts - 诊断注册

功能: 注册和管理 LSP 诊断信息。

passiveFeedback.ts - 被动反馈

功能: 处理 LSP 的被动反馈(如悬停信息、定义跳转)。


5. services/analytics/ - 分析服务

index.ts - 分析服务入口

文件位置: src/services/analytics/index.ts

核心功能:

  • 事件日志记录
  • GrowthBook 特性开关
  • 事件队列管理

事件日志:

export function logEvent(
  eventName: string,
  metadata: Record<string, boolean | number | undefined>
): void

export async function logEventAsync(
  eventName: string,
  metadata: Record<string, boolean | number | undefined>
): Promise<void>

设计原则:

  • 无依赖设计,避免导入循环
  • 事件在 sink 连接前进入队列
  • 支持同步/异步事件记录

GrowthBook 集成:

export function getFeatureValue_CACHED_MAY_BE_STALE(
  featureName: string,
  defaultValue: T
): T

6. services/plugins/ - 插件系统

pluginOperations.ts - 插件操作

文件位置: src/services/plugins/pluginOperations.ts

核心操作:

export async function installPluginOp(
  plugin: string,
  scope: InstallableScope = 'user'
): Promise<PluginOperationResult>

export async function uninstallPluginOp(
  plugin: string,
  scope: InstallableScope = 'user',
  deleteDataDir = true
): Promise<PluginOperationResult>

export async function setPluginEnabledOp(
  plugin: string,
  enabled: boolean,
  scope?: InstallableScope
): Promise<PluginOperationResult>

export async function updatePluginOp(
  plugin: string,
  scope: PluginScope
): Promise<PluginUpdateResult>

安装作用域:

export const VALID_INSTALLABLE_SCOPES = ['user', 'project', 'local'] as const

操作原则:

  1. 搜索市场获取插件信息
  2. 写入设置(声明意图)
  3. 缓存插件并记录版本

PluginInstallationManager.ts - 安装管理

功能: 管理插件的下载、安装、更新。


7. services/compact/ - 对话压缩

compact.ts - 核心压缩逻辑

文件位置: src/services/compact/compact.ts

核心接口:

export interface CompactionResult {
  boundaryMarker: SystemMessage
  summaryMessages: UserMessage[]
  attachments: AttachmentMessage[]
  hookResults: HookResultMessage[]
  messagesToKeep?: Message[]
  userDisplayMessage?: string
  preCompactTokenCount?: number
  postCompactTokenCount?: number
  truePostCompactTokenCount?: number
  compactionUsage?: ReturnType<typeof getTokenUsage>
}

压缩类型:

完整压缩 (compactConversation)

export async function compactConversation(
  messages: Message[],
  context: ToolUseContext,
  cacheSafeParams: CacheSafeParams,
  suppressFollowUpQuestions: boolean,
  customInstructions?: string,
  isAutoCompact: boolean = false,
  recompactionInfo?: RecompactionInfo
): Promise<CompactionResult>

部分压缩 (partialCompactConversation)

export async function partialCompactConversation(
  allMessages: Message[],
  pivotIndex: number,
  context: ToolUseContext,
  cacheSafeParams: CacheSafeParams,
  userFeedback?: string,
  direction: PartialCompactDirection = 'from'
): Promise<CompactionResult>

核心流程:

  1. 执行 PreCompact hooks
  2. 剥离图片/文档(节省 token
  3. 调用 AI 生成摘要
  4. 创建压缩边界标记
  5. 执行 SessionStart hooks
  6. 清理缓存

microCompact.ts - 微压缩

功能: 在调用压缩 API 前减少消息 token 数量。

export async function microcompactMessages(
  messages: Message[],
  context: ToolUseContext
): Promise<{ messages: Message[] }>

sessionMemoryCompact.ts - 会话内存压缩

功能: 快速压缩,无需调用 AI。

autoCompact.ts - 自动压缩

功能: 当上下文即将达到限制时自动触发压缩。


8. services/policyLimits/ - 组织策略限制

文件位置: src/services/policyLimits/index.ts

功能: 获取并应用组织级别的策略限制。

资格条件:

  • Console 用户API Key: 全部符合
  • OAuth 用户Claude.ai: 仅 Team 和 Enterprise 订阅

核心函数:

export function isPolicyLimitsEligible(): boolean
export async function waitForPolicyLimitsToLoad(): Promise<void>
export function isPolicyAllowed(policy: string): boolean
export async function loadPolicyLimits(): Promise<void>
export async function refreshPolicyLimits(): Promise<void>
export async function clearPolicyLimitsCache(): Promise<void>

缓存策略:

  • 文件缓存: ~/.claude/policy-limits.json
  • ETag 校验
  • 后台轮询(每小时)

失败处理: 失败时继续运行fail open


9. services/remoteManagedSettings/ - 远程托管设置

文件位置: src/services/remoteManagedSettings/index.ts

功能: 为企业客户获取和管理远程托管设置。

核心函数:

export function isEligibleForRemoteManagedSettings(): boolean
export async function waitForRemoteManagedSettingsToLoad(): Promise<void>
export async function loadRemoteManagedSettings(): Promise<void>
export async function refreshRemoteManagedSettings(): Promise<void>
export async function clearRemoteManagedSettingsCache(): Promise<void>

安全检查:

export async function checkManagedSettingsSecurity(
  cachedSettings: SettingsJson,
  newSettings: SettingsJson
): Promise<SecurityCheckResult>

10. services/extractMemories/ - 自动记忆提取

文件位置: src/services/extractMemories/extractMemories.ts

功能: 从当前会话中提取持久记忆并写入自动记忆目录。

触发时机: 在查询循环结束时(模型生成最终响应后)

核心接口:

export function initExtractMemories(): void
export async function executeExtractMemories(
  context: REPLHookContext,
  appendSystemMessage?: AppendSystemMessageFn
): Promise<void>
export async function drainPendingExtraction(timeoutMs?: number): Promise<void>

工具权限:

export function createAutoMemCanUseTool(memoryDir: string): CanUseToolFn
// 允许: Read, Grep, Glob, 只读 Bash
// 允许: Edit, Write 仅限 auto-memory 路径

特性开关:

  • tengu_passport_quail - 启用/禁用记忆提取
  • tengu_bramble_lintel - 提取频率控制
  • TEAMMEM - 团队记忆支持

11. services/tokenEstimation.ts - Token 估算

文件位置: src/services/tokenEstimation.ts

核心功能: 估算文本和消息的 token 数量。

主要函数:

export async function countTokensWithAPI(content: string): Promise<number | null>
export async function countMessagesTokensWithAPI(
  messages: Anthropic.Beta.Messages.BetaMessageParam[],
  tools: Anthropic.Beta.Messages.BetaToolUnion[]
): Promise<number | null>

export function roughTokenCountEstimation(
  content: string,
  bytesPerToken: number = 4
): number

export async function countTokensViaHaikuFallback(
  messages: Anthropic.Beta.Messages.BetaMessageParam[],
  tools: Anthropic.Beta.Messages.BetaToolUnion[]
): Promise<number | null>

文件类型估算:

export function bytesPerTokenForFileType(fileExtension: string): number {
  switch (fileExtension) {
    case 'json':
    case 'jsonl':
    case 'jsonc':
      return 2  // JSON 更密集
    default:
      return 4
  }
}

图像 token 估算:

// tokens = (width px * height px) / 750
// 最大 2000x2000 (约 5333 tokens)

12. services/teamMemorySync/ - 团队记忆同步

(参见 extractMemories/ 中的 TEAMMEM 特性)

功能: 在团队成员之间同步记忆文件。


服务层架构图

┌─────────────────────────────────────────────────────────────┐
│                      CLI 入口                                │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│                      命令层 (commands/)                      │
│  /commit /review /compact /mcp /config /doctor 等          │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│                      服务层 (services/)                      │
│                                                             │
│  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐       │
│  │   api/      │  │   mcp/      │  │   lsp/      │       │
│  │ Anthropic   │  │ Model Context│  │ Language    │       │
│  │ API 客户端   │  │ Protocol     │  │ Server      │       │
│  └─────────────┘  └─────────────┘  └─────────────┘       │
│                                                             │
│  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐       │
│  │   oauth/    │  │  analytics/ │  │  plugins/   │       │
│  │ OAuth 2.0  │  │ GrowthBook  │  │  插件系统   │       │
│  └─────────────┘  └─────────────┘  └─────────────┘       │
│                                                             │
│  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐       │
│  │  compact/   │  │policyLimits/│  │remoteManage │       │
│  │ 对话压缩    │  │ 策略限制    │  │ dSettings/  │       │
│  └─────────────┘  └─────────────┘  └─────────────┘       │
│                                                             │
│  ┌─────────────┐  ┌─────────────┐                         │
│  │extractMemories│ │tokenEstim ation│                    │
│  │ 自动记忆提取 │  │ Token 估算  │                         │
│  └─────────────┘  └─────────────┘                         │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│                      工具层 (tools/)                        │
│  Read / Write / Edit / Bash / Grep / Glob 等               │
└─────────────────────────────────────────────────────────────┘

相关源码文件索引

服务 主要文件
API Client src/services/api/client.ts, claude.ts
MCP src/services/mcp/
OAuth src/services/oauth/
LSP src/services/lsp/
Analytics src/services/analytics/
Plugins src/services/plugins/
Compact src/services/compact/
Policy Limits src/services/policyLimits/
Remote Settings src/services/remoteManagedSettings/
Extract Memories src/services/extractMemories/
Token Estimation src/services/tokenEstimation.ts