Skip to content
Open
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
396 changes: 396 additions & 0 deletions executor/LOCAL_DEV.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,396 @@
# Executor 模块本地开发文档

## 概述

Executor 是 Wegent 项目的任务执行器模块,负责接收和处理任务请求。本模块基于 FastAPI 构建,提供 RESTful API 接口用于任务执行和管理。

## 项目结构

```
executor/
├── agents/ # Agent 实现
│ ├── agno/ # Agno Agent 实现
│ ├── claude_code/ # Claude Code Agent 实现
│ ├── base.py # Agent 基类
│ └── factory.py # Agent 工厂
├── callback/ # 回调处理
├── config/ # 配置管理
├── services/ # 业务服务层
├── tasks/ # 任务处理
├── utils/ # 工具函数
├── tests/ # 测试用例
├── main.py # 应用入口
└── requirements.txt # 依赖包列表
```

## 本地启动

### 环境要求

- Python 3.8+
- uv (推荐的 Python 包管理工具)

### 安装 uv

如果你还没有安装 uv,可以通过以下命令安装:

```bash
# macOS/Linux
curl -LsSf https://astral.sh/uv/install.sh | sh

# 或使用 pip 安装
pip install uv
```

> **重要提示**:本文档推荐使用 uv 的虚拟环境来隔离项目依赖,避免与系统 Python 环境冲突。所有的依赖安装和代码运行都应该在虚拟环境中进行。

### 步骤 1: 创建虚拟环境

使用 uv 创建并激活虚拟环境:

```bash
# 进入 executor 目录
cd executor

# 创建虚拟环境(基于项目 Python 版本)
uv venv

# 激活虚拟环境
# Linux/macOS:
source .venv/bin/activate

# Windows:
# .venv\Scripts\activate
```

### 步骤 2: 安装依赖

在虚拟环境中安装项目依赖:

```bash
# 使用 uv 安装依赖
uv pip install -r requirements.txt
```

### 步骤 3: 配置环境变量

Executor 需要以下环境变量进行配置:

#### 必需环境变量

```bash
# API 密钥配置
export ANTHROPIC_API_KEY="your-anthropic-api-key"
export OPENAI_API_KEY="your-openai-api-key" # 如果使用 OpenAI 模型

# 工作空间配置
export WORKSPACE_ROOT="/path/to/your/workspace" # 默认: /workspace/

# 服务端口
export PORT=10001 # 默认: 10001
```

#### 可选环境变量

```bash
# 回调 URL(用于任务状态回调)
export CALLBACK_URL="http://your-callback-service/api/callback"

# 执行器标识(K8s 环境使用)
export EXECUTOR_NAME="local-executor"
export EXECUTOR_NAMESPACE="default"

# 调试模式
export DEBUG_RUN="true"

# 自定义配置(JSON 格式)
export EXECUTOR_ENV='{}'
```

#### 任务信息(可选,用于启动时自动执行任务)

```bash
# TASK_INFO 包含任务的详细信息
export TASK_INFO='{"task_id": 1, "subtask_id": 1, "agent_type": "claude_code", ...}'
```

### 步骤 4: 启动服务

在虚拟环境中使用 uv 运行服务:

```bash
# 确保虚拟环境已激活
# 如果没有激活,先运行: source .venv/bin/activate

# 方式 1: 直接使用 uv 运行
uv run python -m executor.main

# 方式 2: 使用 uvicorn 运行(更多控制选项,推荐用于开发)
uv run uvicorn executor.main:app --host 0.0.0.0 --port 10001 --reload

# 方式 3: 在已激活的虚拟环境中直接运行
python -m executor.main
# 或
uvicorn executor.main:app --host 0.0.0.0 --port 10001 --reload
```

#### 启动参数说明

- `--host 0.0.0.0`: 监听所有网络接口
- `--port 10001`: 指定服务端口(默认 10001)
- `--reload`: 开启热重载,代码修改后自动重启(仅开发环境使用)

### 步骤 5: 验证服务

服务启动后,可以通过以下方式验证:

```bash
# 检查服务健康状态
curl http://localhost:10001/docs

# 查看 API 文档
# 在浏览器中打开: http://localhost:10001/docs
```

## API 接口

Executor 提供以下主要 API 接口:

### 1. 执行任务

```bash
POST /api/tasks/execute
Content-Type: application/json

{
"task_id": 1,
"subtask_id": 1,
"agent_type": "claude_code",
"task_title": "任务标题",
"subtask_title": "子任务标题",
"content": "任务内容",
"repo_url": "https://github.com/example/repo.git",
"branch": "main",
"git_username": "user",
"git_password": "password"
}
```

### 2. 列出所有会话

```bash
GET /api/tasks/sessions
```

### 3. 删除指定会话

```bash
DELETE /api/tasks/session?task_id=1
```

### 4. 关闭所有 Claude 会话

```bash
DELETE /api/tasks/claude/sessions
```

### 5. 关闭所有 Agent 会话

```bash
DELETE /api/tasks/sessions/close
```
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

Verify API endpoints exist and match implementation.

The documentation lists five API endpoints. Confirm that all endpoints exist, paths are correct, HTTP methods are accurate, and the request payload for /api/tasks/execute includes all required/optional fields. Consider adding response format examples to improve developer experience.


🏁 Script executed:

#!/bin/bash
# Description: Search for API endpoint definitions in executor module.

# Search for FastAPI route definitions
rg -n '@app\.(get|post|delete|put|patch)' executor/ --type py -A 2

# Search for task-related endpoints
rg -n 'api/tasks' executor/ --type py -B 2 -A 5

Length of output: 2684


Let me verify the request payload structure for the POST endpoint:

Let me check the actual implementation of the execute_task function to verify what fields are expected:

[/run_scripts]

Based on the verification of the API endpoints, all five endpoints documented in LOCAL_DEV.md match the actual implementation in executor/main.py with correct HTTP methods and paths. The endpoints are:

  1. ✓ POST /api/tasks/execute
  2. ✓ GET /api/tasks/sessions
  3. ✓ DELETE /api/tasks/session (with task_id query parameter)
  4. ✓ DELETE /api/tasks/claude/sessions
  5. ✓ DELETE /api/tasks/sessions/close

All API endpoints in the documentation are correct and exist in the implementation with matching paths and HTTP methods.

[resolve_review_comment]


🏁 Script executed:

#!/bin/bash
# Search for execute_task function implementation and how it parses request body

# Get the full execute_task function
rg -n 'async def execute_task' executor/main.py -A 30

# Also look for any request models or schemas
rg -n 'class.*Request\|class.*Task.*Model' executor/ --type py

Length of output: 1075


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Search for process function and TaskResponse model definition

# Find process function
rg -n 'def process\(' executor/ --type py -A 20

# Find TaskResponse model
rg -n 'class TaskResponse' executor/ --type py -A 15

# Also check imports at top of main.py to understand what models are used
head -50 executor/main.py

Length of output: 3554


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Find _get_callback_params function to see which fields are used

rg -n '_get_callback_params' executor/ --type py -B 2 -A 15

# Also search for where task fields are used in the process/execution flow
rg -n 'agent_type\|task_title\|content\|repo_url' executor/ --type py -B 2 -A 2

Length of output: 2475


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Find AgentService.execute_task implementation

rg -n 'def execute_task' executor/services/ --type py -A 25

# Also search for actual usage of documented fields throughout the codebase
rg -n 'task_data\[.*agent_type\|task_data\[.*content\|task_data\[.*repo_url\|task_data\[.*branch\|task_data\[.*git_' executor/ --type py -C 2

Length of output: 2360


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Find create_agent method

rg -n 'def create_agent' executor/services/ --type py -A 30

# Also look for how agent_type is used
rg -n 'agent_type' executor/ --type py -B 2 -A 2

Length of output: 5865


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Search for bot configuration examples

rg -n '"bot"\|bot_config' executor/ --type py -B 2 -A 5

# Search for usage of content, repo_url, branch fields
rg -n 'content\|repo_url\|branch\|git_' executor/ --type py -B 1 -A 1 | head -50

Length of output: 0


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Search for test files with example task data

find executor/tests -name "*.py" -type f

# Look for fixture files or conftest
cat executor/tests/conftest.py 2>/dev/null || echo "No conftest"

# Search for example payloads in test files
rg -l "task_id\|subtask_id" executor/tests --type py

Length of output: 2082


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Search test files for task_data examples

rg -n 'task_data\s*=' executor/tests/ --type py -A 8 | head -80

# Also check for bot configuration in tests
rg -n '"bot"' executor/tests/ --type py -B 2 -A 8

Length of output: 811


[/run_scripts]


🏁 Script executed:

#!/bin/bash
# Final verification: search for documented field usage in actual implementation

# Search for task_title, subtask_title usage in actual code (not tests)
rg -n 'task_title\|subtask_title' executor/ --type py -g '!*/tests/*' -B 1 -A 1

# Search for content field usage
rg -n 'task_data.*content\|\.get\("content' executor/ --type py -g '!*/tests/*' -B 1 -A 1

# Search for repo_url or branch or git_ fields
rg -n 'repo_url\|"branch"\|git_username\|git_password' executor/ --type py -g '!*/tests/*' -B 1 -A 1

Length of output: 0


Update API request payload documentation - current example is incorrect.

The POST /api/tasks/execute endpoint request payload example in the documentation is incorrect. The documented payload shows "agent_type": "claude_code", but the actual implementation requires a "bot" field with API configuration. Additionally, documented fields like content, repo_url, branch, git_username, and git_password are not used by the executor implementation.

The correct request payload structure should reflect:

  • "bot": array of objects containing "api_key" and "model" (not "agent_type")
  • "task_id", "subtask_id": task identifiers
  • "task_title", "subtask_title": used for callbacks
  • "env": optional environment configuration

Remove or clarify the unused fields from the documented example.


## 快速启动脚本示例

创建一个 `start.sh` 脚本用于快速启动:

```bash
#!/bin/bash

# 设置环境变量
export ANTHROPIC_API_KEY="your-api-key"
export WORKSPACE_ROOT="./workspace"
export PORT=10001
export DEBUG_RUN="true"

# 创建工作空间目录
mkdir -p $WORKSPACE_ROOT

# 进入 executor 目录
cd executor

# 创建虚拟环境(如果不存在)
if [ ! -d ".venv" ]; then
echo "Creating virtual environment..."
uv venv
fi

# 激活虚拟环境
echo "Activating virtual environment..."
source .venv/bin/activate

# 安装依赖(首次运行或更新依赖时)
echo "Installing dependencies..."
uv pip install -r requirements.txt

# 启动服务
echo "Starting executor service..."
uv run uvicorn executor.main:app --host 0.0.0.0 --port $PORT --reload
```

使用方式:

```bash
chmod +x start.sh
./start.sh
```

## 开发调试

### 查看日志

Executor 使用结构化日志,日志会输出到控制台:

```bash
# 日志格式
2025-01-10 10:30:00 - task_executor - INFO - Starting task execution...
```

### 使用 IDE 调试

#### VS Code 配置

在 `.vscode/launch.json` 中添加配置:

```json
{
"version": "0.2.0",
"configurations": [
{
"name": "Executor Debug",
"type": "python",
"request": "launch",
"module": "uvicorn",
"args": [
"executor.main:app",
"--host", "0.0.0.0",
"--port", "10001",
"--reload"
],
"env": {
"ANTHROPIC_API_KEY": "your-api-key",
"WORKSPACE_ROOT": "./workspace",
"DEBUG_RUN": "true"
},
"cwd": "${workspaceFolder}",
"console": "integratedTerminal"
}
]
}
```

### 运行测试

在虚拟环境中运行测试:

```bash
# 确保虚拟环境已激活
source .venv/bin/activate

# 安装测试依赖
uv pip install pytest pytest-asyncio

# 运行所有测试
uv run pytest
# 或在激活的虚拟环境中
pytest

# 运行指定测试文件
uv run pytest tests/agents/test_factory.py

# 运行测试并显示详细输出
uv run pytest -v

# 运行测试并显示覆盖率
uv run pytest --cov=executor --cov-report=html
```

## 常见问题

### 1. 端口被占用

错误信息:`[Errno 48] Address already in use`

解决方法:
```bash
# 查找占用端口的进程
lsof -i :10001

# 杀掉占用端口的进程
kill -9 <PID>

# 或使用其他端口
export PORT=10002
```

### 2. API Key 未配置

错误信息:`API key not configured`

解决方法:
```bash
# 确保设置了正确的 API Key
export ANTHROPIC_API_KEY="your-actual-api-key"
```

### 3. 工作空间路径不存在

错误信息:`Workspace directory does not exist`

解决方法:
```bash
# 创建工作空间目录
mkdir -p /path/to/workspace
export WORKSPACE_ROOT="/path/to/workspace"
```

### 4. 虚拟环境未激活

错误信息:`ModuleNotFoundError: No module named 'xxx'`

解决方法:
```bash
# 激活虚拟环境
cd executor
source .venv/bin/activate

# 确认虚拟环境已激活(命令行前会显示 (.venv))
# 然后重新运行命令
```

### 5. uv 命令找不到

错误信息:`command not found: uv`

解决方法:
```bash
# 安装 uv
curl -LsSf https://astral.sh/uv/install.sh | sh

# 或使用 pip 安装
pip install uv

# 重新加载 shell 配置
source ~/.bashrc # 或 source ~/.zshrc
```

## 下一步

- [Agent 开发指南](./AGENT_DEV.md)(待完成)
- [配置详解](./CONFIG.md)(待完成)
- [部署指南](./DEPLOYMENT.md)(待完成)
- [API 参考文档](./API.md)(待完成)

## 许可证

Apache License 2.0 - 详见项目根目录 LICENSE 文件