Luxx/assets/ARCHITECTURE.md

27 KiB
Raw Blame History

Luxx 项目架构

技术栈

  • 框架: FastAPI 0.109+
  • 数据库: SQLAlchemy 2.0+ (同步模式)
  • 认证: JWT (PyJWT)
  • HTTP客户端: httpx, requests
  • 配置: YAML (PyYAML)
  • 代码执行: Python 原生执行
  • 网页爬虫:
    • httpx - HTTP 客户端
    • beautifulsoup4 - HTML 解析
    • lxml - XML/HTML 解析器

目录结构

luxx/
├── __init__.py              # FastAPI 应用工厂
├── config.py                # 配置管理YAML
├── database.py              # 数据库连接
├── models.py                # ORM 模型
├── routes/                  # API 路由层
│   ├── __init__.py         # 路由聚合
│   ├── auth.py             # 认证 (登录/注册)
│   ├── agents.py          # Agent 模板管理 (CRUD)
│   ├── chat_rooms.py      # 聊天室管理 (多 Agent 协作)
│   ├── conversations.py    # 会话管理 (CRUD)
│   ├── messages.py         # 消息处理 (流式/同步)
│   ├── providers.py        # LLM 提供商管理
│   ├── agents.py          # Agent 模板管理 (CRUD)
│   └── tools.py            # 工具管理
├── services/               # 服务层
│   ├── __init__.py        # 服务导出
│   ├── chat.py            # 聊天服务门面
│   ├── chat_room.py       # 多 Agent 聊天室编排器
│   ├── agentic_loop.py    # Agentic Loop 执行器
│   ├── stream_context.py  # 流式状态管理
│   ├── events.py          # SSE 事件工具
│   ├── llm_response.py     # LLM 响应数据类
│   ├── task.py            # 任务系统 (Task/TaskGraph/TaskService)
│   ├── llm_client.py      # LLM 客户端
│   └── llm_adapters/      # LLM API 适配器
│       ├── __init__.py    # 适配器导出
│       ├── base.py        # ProviderAdapter 基类
│       ├── openai_adapter.py  # OpenAI/DeepSeek/GLM 适配器
│       └── anthropic_adapter.py  # Anthropic Claude 适配器
├── tools/                  # 工具系统
│   ├── __init__.py        # 工具注册入口
│   ├── core.py            # 核心类 (ToolRegistry, ToolDefinition, ToolResult, ToolContext)
│   ├── factory.py         # @tool 装饰器
│   ├── executor.py        # 工具执行器 (缓存/并行)
│   ├── services.py        # 工具服务层
│   └── builtin/           # 内置工具
│       ├── __init__.py    # 工具注册入口
│       ├── code.py        # 代码执行 (python_execute, python_eval)
│       ├── crawler.py     # 网页爬虫 (web_search, web_fetch, batch_fetch)
│       ├── data.py        # 数据处理 (process_data)
│       ├── file.py        # 文件操作 (file_read, file_write, file_list, file_exists, file_grep)
│       └── shell.py       # Shell 命令 (shell_execute)
└── utils/                  # 工具函数
    ├── __init__.py
    └── helpers.py         # 密码哈希、ID生成、响应封装

run.py                    # 应用入口文件
config.yaml                # 配置文件

核心组件

1. 应用工厂 (__init__.py)

FastAPI 应用入口,使用 lifespan 管理生命周期:

  • 启动:初始化数据库、注册内置工具、创建默认管理员用户
  • 关闭:清理资源
# 默认管理员账号
username: admin
password: admin123

2. 配置管理 (config.py)

使用 YAML 文件管理配置:

  • 配置文件:config.yaml
  • 环境变量替换:${VAR_NAME}
  • 单例模式全局访问
  • 默认值支持
# config.yaml 示例
app:
  secret_key: ${APP_SECRET_KEY}
  debug: true
  host: 0.0.0.0
  port: 8000

database:
  type: sqlite
  url: sqlite:///./chat.db

workspace:
  root: ./workspaces          # 用户工作空间根目录
  auto_create: true           # 自动创建用户目录

llm:
  provider: deepseek
  api_key: ${DEEPSEEK_API_KEY}
  api_url: https://api.deepseek.com/v1

tools:
  enable_cache: true
  cache_ttl: 300
  max_workers: 4
  max_iterations: 10

logging:
  level: INFO

工作空间隔离机制:

  • 每个用户的工作空间路径基于 user_id 的 SHA256 哈希值
  • 格式:{workspace_root}/{hash_of_user_id}
  • 所有文件操作必须在用户工作空间内,防止路径穿越攻击

### 3. 数据库 (`database.py`)
- SQLAlchemy 同步支持
- SQLite 默认数据库
- 依赖注入获取会话

### 4. ORM 模型 (`models.py`)

```mermaid
erDiagram
    USER {
        int id PK
        string username UK
        string email UK
        string password_hash
        string role
        int permission_level "1=READ_ONLY, 2=WRITE, 3=EXECUTE, 4=ADMIN"
        string workspace_path "用户工作空间路径"
        boolean is_active
        datetime created_at
    }

    USER_SETTINGS {
        int id PK
        int user_id FK UK
        int default_provider_id FK "optional"
        float temperature
        int max_tokens
        boolean thinking_enabled
        text system_prompt
        datetime created_at
        datetime updated_at
    }

    PROJECT {
        string id PK
        int user_id FK
        string name
        text description
        datetime created_at
        datetime updated_at
    }

    CONVERSATION {
        string id PK
        int user_id FK
        int provider_id FK "optional"
        string project_id FK "optional"
        string title
        string model
        text system_prompt
        float temperature
        int max_tokens
        boolean thinking_enabled
        datetime created_at
        datetime updated_at
    }

    MESSAGE {
        string id PK
        string conversation_id FK "optional"
        string room_id FK "optional"
        string role
        longtext content "JSON 格式"
        int token_count
        text usage "JSON 格式"
        string sender_name "聊天室: 发送者名称"
        string sender_color "聊天室: 发送者颜色"
        int round_number "聊天室: 轮次编号"
        datetime created_at
    }

    LLM_PROVIDER {
        int id PK
        int user_id FK
        string name
        string provider_type
        string base_url
        string api_key
        string default_model
        int max_tokens
        boolean is_default
        boolean enabled
        datetime created_at
        datetime updated_at
    }

    AGENT {
        int id PK
        int user_id FK
        string name
        string role
        int provider_id FK "optional"
        string model
        text system_prompt
        string color
        datetime created_at
        datetime updated_at
    }

    CHAT_ROOM {
        string id PK
        int user_id FK
        string title
        text task
        string status "idle/running/paused/completed/error"
        int max_rounds
        int current_round
        datetime created_at
        datetime updated_at
    }

    ROOM_AGENT {
        int id PK
        string room_id FK
        int agent_id FK "optional"
        string name
        string role
        int provider_id FK "optional"
        string model
        text system_prompt
        string color
        int turn_order
    }

    USER ||--|| USER_SETTINGS : "has"
    USER ||--o{ PROJECT : "has"
    USER ||--o{ CONVERSATION : "has"
    USER ||--o{ LLM_PROVIDER : "configures"
    USER ||--o{ AGENT : "creates"
    USER ||--o{ CHAT_ROOM : "creates"
    PROJECT ||--o{ CONVERSATION : "contains"
    LLM_PROVIDER ||--o{ CONVERSATION : "uses"
    LLM_PROVIDER ||--o{ AGENT : "used_by"
    LLM_PROVIDER ||--o{ ROOM_AGENT : "used_by"
    CONVERSATION ||--o{ MESSAGE : "has"
    CHAT_ROOM ||--o{ MESSAGE : "has"
    CHAT_ROOM ||--o{ ROOM_AGENT : "contains"
    AGENT ||--o{ ROOM_AGENT : "linked_to"

用户权限级别 (permission_level)

级别 名称 说明
1 READ_ONLY 只读权限
2 WRITE 写入权限(文件写入)
3 EXECUTE 执行权限代码执行、Shell命令
4 ADMIN 管理员权限

Message Content JSON 结构

content 字段统一使用 JSON 格式存储:

User 消息:

{
  "text": "用户输入的文本内容",
  "attachments": [
    {"name": "utils.py", "extension": "py", "content": "..."}
  ]
}

Assistant 消息:

{
  "steps": [
    {"id": "step-0", "index": 0, "type": "thinking", "content": "..."},
    {"id": "step-1", "index": 1, "type": "text", "content": "..."},
    {"id": "step-2", "index": 2, "type": "tool_call", "id_ref": "call_xxx", "name": "...", "arguments": "..."},
    {"id": "step-3", "index": 3, "type": "tool_result", "id_ref": "call_xxx", "name": "...", "content": "...", "success": true}
  ]
}

steps 字段是唯一数据源,按 index 顺序排列。thinking、text、tool_call、tool_result 可以在多轮迭代中穿插出现。

注意textcontent 字段通过解析 steps 中所有 type: "text" 的内容动态计算得出。

5. 工具系统

classDiagram
    class ToolDefinition {
        +str name
        +str description
        +dict parameters
        +Callable handler
        +str category
        +CommandPermission required_permission
        +to_openai_format() dict
    }

    class ToolContext {
        +int user_id
        +str username
        +str workspace
        +int user_permission_level
    }

    class CommandPermission {
        <<enumeration>>
        READ_ONLY = 1
        WRITE = 2
        EXECUTE = 3
        ADMIN = 4
    }

    class ToolResult {
        +bool success
        +Any data
        +str error
        +to_dict() dict
        +ok(data) ToolResult$
        +fail(error) ToolResult$
    }

    class ToolRegistry {
        +_tools: Dict
        +register(tool) void
        +get(name) ToolDefinition?
        +list_all() List~dict~
        +list_by_category(category) List~dict~
        +execute(name, arguments, context) dict
        +remove(name) bool
    }

    class ToolExecutor {
        +enable_cache: bool
        +cache_ttl: int
        +max_workers: int
        +_cache: Dict
        +_call_history: List
        +process_tool_calls(tool_calls, context) list
        +process_tool_calls_parallel(tool_calls, context) list
        +clear_cache() void
        +get_history(limit) List
    }

内置工具

代码执行 (code.py)

工具 功能 权限
python_execute 执行 Python 代码 EXECUTE
python_eval 计算表达式 EXECUTE

文件操作 (file.py)

工具 功能 权限
file_read 读取文件内容 READ_ONLY
file_write 写入文件内容 WRITE
file_list 列出目录内容 READ_ONLY
file_exists 检查文件是否存在 READ_ONLY
file_grep 正则搜索文件内容 READ_ONLY

Shell 命令 (shell.py)

工具 功能 权限
shell_execute 执行 Shell 命令 EXECUTE

网页爬虫 (crawler.py)

工具 功能 权限
web_search DuckDuckGo HTML 搜索 READ_ONLY
web_fetch 网页抓取 READ_ONLY
batch_fetch 批量并发抓取 READ_ONLY

数据处理 (data.py)

工具 功能 权限
process_data JSON 转换、格式化 READ_ONLY

权限检查机制

工具执行时自动检查用户权限:

工具要求的权限 <= 用户拥有的权限 → 允许执行
工具要求的权限 >  用户拥有的权限 → 拒绝执行

工具开发规范

所有工具必须遵循统一的开发规范,确保错误处理和返回格式一致。

核心原则:装饰器自动处理一切,工具函数只写业务逻辑

from luxx.tools.factory import tool

@tool(
    name="my_tool",
    description="工具描述",
    parameters={...},
    required_params=["arg1"],  # 自动验证
    category="my_category"
)
def my_tool(arguments: dict):
    # 业务逻辑 - 只管返回数据
    data = fetch_data(arguments["arg1"])
    return {"items": data, "count": len(data)}
    
    # 或者直接抛出异常(装饰器自动捕获并转换)
    if invalid:
        raise ValueError("Invalid input")

装饰器自动处理:

  1. 必需参数验证(required_params
  2. 所有异常捕获和转换
  3. 结果格式统一包装

返回格式转换

工具函数返回/抛出 装饰器转换为
return {"result": "ok"} {"success": true, "data": {...}, "error": null}
raise ValueError("msg") {"success": false, "data": null, "error": "ValueError: msg"}
raise Exception() {"success": false, "data": null, "error": "..."}

工具调用流程

LLM 请求
    ↓
ToolRegistry.execute(name, args)
    ↓
@tool 装饰器
    ├─ 验证 required_params
    ├─ 执行工具函数 (try-except 包裹)
    ├─ 捕获异常 → 转换为 error
    ├─ 包装返回格式
    └─ 返回 ToolResult
    ↓
ToolExecutor 返回结果
    ↓
前端 ProcessBlock 显示

6. 服务层

LLM 适配器 (services/llm_adapters/)

适配器模式统一处理不同 LLM API 格式:

classDiagram
    class ProviderAdapter {
        <<abstract>>
        +str provider_type
        +build_request() tuple
        +parse_stream_chunk() AsyncGenerator
        +parse_response() Dict
        +supports_thinking() bool
        +supports_tools() bool
    }

    class OpenAIAdapter {
        +str provider_type = "openai"
        +build_request() tuple
        +parse_stream_chunk() AsyncGenerator
        +parse_response() Dict
        +supports_tools() bool
    }

    class AnthropicAdapter {
        +str provider_type = "anthropic"
        +build_request() tuple
        +parse_stream_chunk() AsyncGenerator
        +parse_response() Dict
        +supports_thinking() bool
        +supports_tools() bool
    }

    ProviderAdapter <|-- OpenAIAdapter
    ProviderAdapter <|-- AnthropicAdapter

支持的功能对比:

适配器 工具调用 Thinking/Reasoning 流式响应
OpenAI (DeepSeek)
Anthropic

LLM 响应数据类 (services/llm_response.py)

class StepType:
    """步骤类型常量"""
    THINKING = "thinking"
    TEXT = "text"
    TOOL_CALL = "tool_call"
    TOOL_RESULT = "tool_result"


@dataclass
class Step:
    """单个步骤 - 用于存储和传输"""
    id: str
    index: int
    type: str  # thinking, text, tool_call, tool_result
    content: str = ""
    name: str = ""  # tool_call/tool_result
    arguments: str = ""  # tool_call
    id_ref: str = ""  # tool_result
    success: bool = True


@dataclass
class ParsedDelta:
    """LLM 流式响应增量"""
    thinking: str = ""           # 思考内容(增量)
    text: str = ""               # 文本内容(增量)
    tool_call: Optional[Dict] = None  # 单个工具调用
    usage: Dict[str, int] = {}   # Token 用量
    is_complete: bool = False

ChatService (services/chat.py)

核心聊天服务:

  • Agentic Loop 迭代执行(最多 10 轮)
  • 流式 SSE 响应
  • 工具调用编排(并行执行)
  • 消息历史管理
  • Token 用量追踪
  • 工作空间上下文传递

AgenticLoop (services/agentic_loop.py)

执行 Agentic Loop 的核心循环:

  • 调用 LLM 获取响应(流式)
  • 解析 ParsedDelta更新步骤状态
  • 管理 thinking/text/tool_call/tool_result 步骤
  • 工具并行执行
  • 最大迭代次数10
# 执行流程
async for delta in llm.stream_call(...):
    events = self._process_delta(delta, context, total_usage)
    yield from events

# 工具调用时
tool_results = self.tool_executor.process_tool_calls_parallel(...)
messages.append({"role": "assistant", ...})
messages.extend(tool_results)

StreamContext (services/stream_context.py)

流式状态管理:

  • 追踪当前步骤类型和索引
  • 累积 thinking 和 text 内容
  • 管理 tool_calls 列表和 tool_results
  • 生成 SSE 事件
  • 构建完整消息内容

LLMClient (services/llm_client.py)

LLM API 客户端:

  • 多提供商OpenAI、DeepSeek、Anthropic
  • 自动适配器选择
  • 流式/同步调用
  • 错误处理和重试
  • Token 计数

7. 任务系统 (services/task.py)

用于自主任务执行和依赖管理:

classDiagram
    class Task {
        +str id
        +str name
        +str goal
        +TaskStatus status
        +List~Step~ steps
        +List~Task~ subtasks
    }

    class Step {
        +str id
        +str name
        +List~str~ depends_on
        +StepStatus status
    }

    class TaskGraph {
        +topological_sort() List~Step~
        +get_ready_steps() List~Step~
        +detect_cycles() List~List~str~~
        +validate() tuple
    }

    class TaskService {
        +create_task() Task
        +get_task() Task
        +update_task_status() Task
        +add_steps() List~Step~
        +build_graph() TaskGraph
    }

    Task "1" o-- "*" Step
    Task "1" o-- "*" Task
    TaskService ..> TaskGraph

任务状态 (TaskStatus)

  • PENDING - 待处理
  • READY - 就绪
  • RUNNING - 运行中
  • BLOCK - 阻塞
  • TERMINATED - 已终止

步骤状态 (StepStatus)

  • PENDING - 待执行
  • RUNNING - 执行中
  • COMPLETED - 已完成
  • FAILED - 失败
  • SKIPPED - 跳过

7. 认证系统 (routes/auth.py)

  • JWT Bearer Token
  • Bcrypt 密码哈希
  • 用户注册/登录

8. Agent 系统 (routes/agents.py, models.py)

Agent 是独立的可复用 AI 助手模板,可以在聊天室中使用:

classDiagram
    class Agent {
        +int id
        +int user_id
        +str name
        +str role
        +int provider_id
        +str model
        +str system_prompt
        +str color
        +to_dict() dict
    }

    class LLMProvider {
        +int id
        +str name
        +str api_key
        +str default_model
    }

    Agent --> LLMProvider : uses

Agent 字段说明:

字段 类型 说明
id int Agent 唯一标识
user_id int 所属用户 ID
name string Agent 显示名称
role string Agent 角色描述(如"后端开发"
provider_id int 使用的 LLM 提供商
model string 模型名称
system_prompt string 系统提示词
color string 显示颜色Hex

9. 聊天室系统 (routes/chat_rooms.py, services/chat_room.py)

聊天室支持多个 Agent 同时参与讨论,协作完成复杂任务:

classDiagram
    class ChatRoom {
        +str id
        +int user_id
        +str title
        +str task
        +str status
        +int max_rounds
        +int current_round
        +List~RoomAgent~ agents
    }

    class RoomAgent {
        +int id
        +str room_id
        +int agent_id
        +str name
        +str role
        +str model
        +str system_prompt
        +str color
        +int turn_order
    }

    class ChatRoomOrchestrator {
        -Dict~str, Task~ _running_rooms
        +is_running(room_id) bool
        +cancel(room_id) void
        +run_room(room_id) AsyncGenerator
    }

    ChatRoom "1" o-- "*" RoomAgent : contains
    ChatRoomOrchestrator ..> ChatRoom : orchestrates
    ChatRoomOrchestrator ..> RoomAgent : executes

聊天室状态:

状态 说明
idle 空闲,未开始
running 运行中
paused 已暂停(被手动停止)
completed 已完成(达到最大轮次)
error 错误(执行出错)

聊天室执行流程:

1. 用户调用 /chat-rooms/{id}/start
2. ChatRoomOrchestrator.run_room() 被调用
3. 按 turn_order 顺序执行每个 Agent 的发言轮次
4. 每个 Agent 根据历史消息和系统提示生成回复
5. SSE 流式推送消息块 (message_chunk)
6. 消息结束时推送 message_end
7. 一轮结束后推送 round_end
8. 达到 max_rounds 或被停止时结束

SSE 事件流:

room_started → round_start → (message_start → message_chunk* → message_end → message) × N_agents
           → round_end → (重复下一轮) → room_completed

10. API 路由

路由 方法 说明
/auth/register POST 用户注册
/auth/login POST 用户登录
/auth/logout POST 用户登出
/auth/me GET 当前用户信息
/auth/users GET 用户列表(管理员)
/auth/users/{user_id} PUT 更新用户权限
/conversations GET 会话列表(分页)
/conversations POST 创建会话
/conversations/{id} GET 会话详情
/conversations/{id} PUT 更新会话
/conversations/{id} DELETE 删除会话
/messages GET 消息列表
/messages POST 发送消息(同步)
/messages/stream POST 发送消息(流式 SSE
/messages/{id} DELETE 删除消息
/providers GET LLM 提供商列表
/providers POST 创建提供商
/providers/{id} GET 提供商详情
/providers/{id} PUT 更新提供商
/providers/{id} DELETE 删除提供商
/providers/{id}/test POST 测试提供商连接
/agents GET Agent 列表
/agents POST 创建 Agent
/agents/{id} GET Agent 详情
/agents/{id} PUT 更新 Agent
/agents/{id} DELETE 删除 Agent
/chat-rooms GET 聊天室列表
/chat-rooms POST 创建聊天室
/chat-rooms/{id} GET 聊天室详情
/chat-rooms/{id} PUT 更新聊天室
/chat-rooms/{id} DELETE 删除聊天室
/chat-rooms/{id}/start POST 启动聊天室
/chat-rooms/{id}/stop POST 停止聊天室
/chat-rooms/{id}/reset POST 重置聊天室
/chat-rooms/{id}/messages GET 聊天室消息
/chat-rooms/{id}/agents POST 添加 Agent
/chat-rooms/{id}/agents/{agent_id} PUT 更新 Agent
/chat-rooms/{id}/agents/{agent_id} DELETE 移除 Agent
/tools GET 可用工具列表
/tools/{name} GET 工具详情
/tools/{name}/execute POST 执行工具
/health GET 健康检查
/ GET 服务信息

数据流

消息处理流程

sequenceDiagram
    participant Client
    participant API as POST /messages/stream
    participant CS as ChatService
    participant AL as AgenticLoop
    participant Parser as LLMResponseParser
    participant LLM as LLM API
    participant TE as ToolExecutor
    
    Client->>API: POST {content, tools, thinking_enabled}
    API->>CS: stream_response()
    CS->>AL: execute()
    
    loop MAX_ITERATIONS (10)
        AL->>LLM: stream_call(messages, tools)
        LLM-->>AL: SSE Stream
        
        AL->>Parser: parse_chunk()
        Parser-->>AL: ParsedDelta {thinking, text, tool_calls}
        
        alt tool_calls
            AL->>TE: process_tool_calls_parallel()
            TE-->>AL: tool_results
            AL->>AL: 追加到 messages
        end
    end
    
    AL->>CS: done event
    CS->>CS: _save_message()
    CS->>API: SSE Stream
    API-->>Client: 流式响应

SSE 事件

普通会话 SSE 事件

事件 说明
process_step 结构化步骤thinking/text/tool_call/tool_result携带 idindex 确保渲染顺序
done 响应完成,携带 message_id、token_count、usage
error 错误信息

聊天室 SSE 事件

事件 说明
room_started 聊天室启动,携带 room_id 和 task
round_start 回合开始,携带 round 和 max_rounds
message_start 消息开始,携带 msg_id、sender_name、sender_color、round_number
message_chunk 消息内容增量,携带 content 和 accumulated
message_end 消息结束,携带 msg_id、content、token_count
message 完整消息(用于存储和显示)
round_end 回合结束
room_completed 聊天室完成
room_paused 聊天室暂停
agent_error Agent 执行错误
error 通用错误

process_step 事件格式

{"type": "process_step", "step": {"id": "step-0", "index": 0, "type": "thinking", "content": "..."}}
{"type": "process_step", "step": {"id": "step-1", "index": 1, "type": "text", "content": "回复文本..."}}
{"type": "process_step", "step": {"id": "step-2", "index": 2, "type": "tool_call", "id_ref": "call_abc", "name": "web_search", "arguments": "{\"query\": \"...\"}"}}
{"type": "process_step", "step": {"id": "step-3", "index": 3, "type": "tool_result", "id_ref": "call_abc", "name": "web_search", "content": "{...}", "success": true}}
字段 说明
id 步骤唯一标识(格式 step-{index}
index 步骤序号,确保按正确顺序显示
type 步骤类型:thinking / text / tool_call / tool_result
id_ref 工具调用引用 ID仅 tool_call/tool_result
name 工具名称(仅 tool_call/tool_result
arguments 工具调用参数 JSON 字符串(仅 tool_call
content 内容thinking 的思考内容、text 的文本、tool_result 的返回结果)
success 工具执行是否成功(仅 tool_result

done 事件格式

{"type": "done", "message_id": "uuid", "token_count": 1234, "usage": {"prompt_tokens": 100, "completion_tokens": 200, "total_tokens": 300}}

配置示例

config.yaml

app:
  secret_key: ${APP_SECRET_KEY}
  debug: true
  host: 0.0.0.0
  port: 8000

database:
  type: sqlite
  url: sqlite:///./chat.db

workspace:
  root: ./workspaces          # 用户工作空间根目录
  auto_create: true           # 自动创建用户工作空间

llm:
  provider: deepseek
  api_key: ${DEEPSEEK_API_KEY}
  api_url: https://api.deepseek.com/v1

tools:
  enable_cache: true
  cache_ttl: 300
  max_workers: 4
  max_iterations: 10

logging:
  level: INFO

环境变量

变量 说明 示例
APP_SECRET_KEY 应用密钥 your-secret-key
DEEPSEEK_API_KEY DeepSeek API sk-xxxx
DATABASE_URL 数据库连接 sqlite:///./chat.db

LLM 适配器配置

OpenAI 兼容 (DeepSeek/GLM 等)

llm:
  provider: openai
  api_key: ${API_KEY}
  api_url: https://api.deepseek.com/v1  # 或其他兼容端点

Anthropic Claude

llm:
  provider: anthropic
  api_key: ${ANTHROPIC_API_KEY}
  api_url: https://api.anthropic.com/v1

项目结构说明

入口文件

  • run.py - 启动 Uvicorn 服务器

响应格式

所有 API 统一使用响应封装:

// 成功
{"success": true, "data": {...}, "message": "操作成功"}

// 错误
{"success": false, "error": "错误信息", "code": 404}

工具缓存机制

ToolExecutor 支持结果缓存:

  • TTL: 5 分钟(可配置)
  • 缓存 Key: {tool_name}:{sorted_arguments_json}
  • 调用历史记录最近 1000 条

流式响应特点

  1. 实时返回 thinking_content模型思考过程
  2. 实时返回 text 增量更新
  3. 工具调用并行执行,结果批量返回
  4. 最终 done 事件包含完整 message_id 和 token 用量

工作空间隔离

每个用户的工作空间完全隔离:

  • 用户目录基于 user_id 的 SHA256 哈希生成
  • 所有文件操作强制在用户工作空间内
  • 支持权限级别控制文件操作能力

MessageBuilder

用于构建发送给 LLM 的消息列表:

  • add_system() - 添加系统消息
  • add_user() - 添加用户消息JSON 格式)
  • add_assistant() - 添加助手消息
  • add_tool_result() - 添加工具结果消息
  • extract_text() - 从 JSON 内容中提取文本