mirror of
https://github.com/catlog22/Claude-Code-Workflow.git
synced 2026-02-14 02:42:04 +08:00
feat(docs): add full documentation generation phase and related documentation generation phase
- Implement Phase 4: Full Documentation Generation with multi-layered strategy and tool fallback. - Introduce Phase 5: Related Documentation Generation for incremental updates based on git changes. - Create new utility components for displaying execution status in the terminal panel. - Add helper functions for rendering execution status icons and formatting relative time. - Establish a recent paths configuration for improved path resolution.
This commit is contained in:
@@ -1,18 +1,18 @@
|
|||||||
---
|
---
|
||||||
name: load
|
name: prepare
|
||||||
description: Delegate to universal-executor agent to analyze project via Gemini/Qwen CLI and return JSON core content package for task context
|
description: Delegate to universal-executor agent to analyze project via Gemini/Qwen CLI and return JSON core content package for task context
|
||||||
argument-hint: "[--tool gemini|qwen] \"task context description\""
|
argument-hint: "[--tool gemini|qwen] \"task context description\""
|
||||||
allowed-tools: Task(*), Bash(*)
|
allowed-tools: Task(*), Bash(*)
|
||||||
examples:
|
examples:
|
||||||
- /memory:load "在当前前端基础上开发用户认证功能"
|
- /memory:prepare "在当前前端基础上开发用户认证功能"
|
||||||
- /memory:load --tool qwen "重构支付模块API"
|
- /memory:prepare --tool qwen "重构支付模块API"
|
||||||
---
|
---
|
||||||
|
|
||||||
# Memory Load Command (/memory:load)
|
# Memory Prepare Command (/memory:prepare)
|
||||||
|
|
||||||
## 1. Overview
|
## 1. Overview
|
||||||
|
|
||||||
The `memory:load` command **delegates to a universal-executor agent** to analyze the project and return a structured "Core Content Pack". This pack is loaded into the main thread's memory, providing essential context for subsequent agent operations while minimizing token consumption.
|
The `memory:prepare` command **delegates to a universal-executor agent** to analyze the project and return a structured "Core Content Pack". This pack is loaded into the main thread's memory, providing essential context for subsequent agent operations while minimizing token consumption.
|
||||||
|
|
||||||
**Core Philosophy**:
|
**Core Philosophy**:
|
||||||
- **Agent-Driven**: Fully delegates execution to universal-executor agent
|
- **Agent-Driven**: Fully delegates execution to universal-executor agent
|
||||||
@@ -95,11 +95,11 @@ The command fully delegates to **universal-executor agent**, which autonomously:
|
|||||||
```javascript
|
```javascript
|
||||||
Task(
|
Task(
|
||||||
subagent_type="universal-executor",
|
subagent_type="universal-executor",
|
||||||
description="Load project memory: ${task_description}",
|
description="Prepare project memory: ${task_description}",
|
||||||
prompt=`
|
prompt=`
|
||||||
## Mission: Load Project Memory Context
|
## Mission: Prepare Project Memory Context
|
||||||
|
|
||||||
**Task**: Load project memory context for: "${task_description}"
|
**Task**: Prepare project memory context for: "${task_description}"
|
||||||
**Mode**: analysis
|
**Mode**: analysis
|
||||||
**Tool Preference**: ${tool || 'gemini'}
|
**Tool Preference**: ${tool || 'gemini'}
|
||||||
|
|
||||||
@@ -186,7 +186,7 @@ Before returning:
|
|||||||
### Example 1: Load Context for New Feature
|
### Example 1: Load Context for New Feature
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
/memory:load "在当前前端基础上开发用户认证功能"
|
/memory:prepare "在当前前端基础上开发用户认证功能"
|
||||||
```
|
```
|
||||||
|
|
||||||
**Agent Execution**:
|
**Agent Execution**:
|
||||||
@@ -212,7 +212,7 @@ Before returning:
|
|||||||
### Example 2: Using Qwen Tool
|
### Example 2: Using Qwen Tool
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
/memory:load --tool qwen "重构支付模块API"
|
/memory:prepare --tool qwen "重构支付模块API"
|
||||||
```
|
```
|
||||||
|
|
||||||
Agent uses Qwen CLI for analysis, returns same structured package.
|
Agent uses Qwen CLI for analysis, returns same structured package.
|
||||||
@@ -220,7 +220,7 @@ Agent uses Qwen CLI for analysis, returns same structured package.
|
|||||||
### Example 3: Bug Fix Context
|
### Example 3: Bug Fix Context
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
/memory:load "修复登录验证错误"
|
/memory:prepare "修复登录验证错误"
|
||||||
```
|
```
|
||||||
|
|
||||||
Returns core context related to login validation, including test files and validation logic.
|
Returns core context related to login validation, including test files and validation logic.
|
||||||
@@ -229,7 +229,7 @@ Returns core context related to login validation, including test files and valid
|
|||||||
|
|
||||||
- **Session-Scoped**: Content package valid for current session
|
- **Session-Scoped**: Content package valid for current session
|
||||||
- **Subsequent Reference**: All subsequent agents/commands can access
|
- **Subsequent Reference**: All subsequent agents/commands can access
|
||||||
- **Reload Required**: New sessions need to re-execute /memory:load
|
- **Reload Required**: New sessions need to re-execute /memory:prepare
|
||||||
|
|
||||||
## 8. Notes
|
## 8. Notes
|
||||||
|
|
||||||
229
.claude/skills/memory-manage/SKILL.md
Normal file
229
.claude/skills/memory-manage/SKILL.md
Normal file
@@ -0,0 +1,229 @@
|
|||||||
|
---
|
||||||
|
name: memory-manage
|
||||||
|
description: Unified memory management - CLAUDE.md updates and documentation generation with interactive routing. Triggers on "memory manage", "update claude", "update memory", "generate docs", "更新记忆", "生成文档".
|
||||||
|
allowed-tools: Task(*), Bash(*), AskUserQuestion(*), Read(*)
|
||||||
|
---
|
||||||
|
|
||||||
|
# Memory Management Skill
|
||||||
|
|
||||||
|
Unified entry point for project memory (CLAUDE.md) updates and documentation (API.md/README.md) generation. Routes to specialized sub-commands via arguments or interactive needs assessment.
|
||||||
|
|
||||||
|
## Architecture Overview
|
||||||
|
|
||||||
|
```
|
||||||
|
┌──────────────────────────────────────────────────────┐
|
||||||
|
│ Memory Manage (Router) │
|
||||||
|
│ → Parse input → Detect mode → Route to phase │
|
||||||
|
└───────────────┬──────────────────────────────────────┘
|
||||||
|
│
|
||||||
|
┌───────┴───────┐
|
||||||
|
↓ ↓
|
||||||
|
┌───────────┐ ┌───────────┐
|
||||||
|
│ CLAUDE.md │ │ Docs │
|
||||||
|
│ 管理 │ │ 生成 │
|
||||||
|
└─────┬─────┘ └─────┬─────┘
|
||||||
|
│ │
|
||||||
|
┌────┼────┐ ┌────┴────┐
|
||||||
|
↓ ↓ ↓ ↓ ↓
|
||||||
|
Full Related Single Full Related
|
||||||
|
全量 增量 单模块 全量 增量
|
||||||
|
```
|
||||||
|
|
||||||
|
## Execution Flow
|
||||||
|
|
||||||
|
### Step 1: Parse Input & Route
|
||||||
|
|
||||||
|
Detect execution mode from user input:
|
||||||
|
|
||||||
|
**Auto-Route Rules** (priority order):
|
||||||
|
|
||||||
|
| Signal | Route | Examples |
|
||||||
|
|--------|-------|---------|
|
||||||
|
| Explicit sub-command token | → Direct dispatch | `update-full --tool qwen` |
|
||||||
|
| Keyword: full, 全量, all, entire + update/claude | → update-full | "全量更新claude" |
|
||||||
|
| Keyword: related, changed, 增量, diff + update/claude | → update-related | "更新变更模块" |
|
||||||
|
| Keyword: single, module, 单模块 + path-like token | → update-single | "更新 src/auth 模块" |
|
||||||
|
| Keyword: docs, documentation, 文档 + full/all/全量 | → docs-full | "全量生成文档" |
|
||||||
|
| Keyword: docs, documentation, 文档 + related/changed/增量 | → docs-related | "增量生成文档" |
|
||||||
|
| Ambiguous or no arguments | → **AskUserQuestion** | `/memory-manage` |
|
||||||
|
|
||||||
|
Valid sub-command tokens: `update-full`, `update-related`, `update-single`, `docs-full`, `docs-related`
|
||||||
|
|
||||||
|
**Direct dispatch examples**:
|
||||||
|
```
|
||||||
|
input = "update-full --tool qwen"
|
||||||
|
→ subcommand = "update-full", remainingArgs = "--tool qwen"
|
||||||
|
→ Read phases/01-update-full.md, execute
|
||||||
|
|
||||||
|
input = "update-single src/auth --tool gemini"
|
||||||
|
→ subcommand = "update-single", remainingArgs = "src/auth --tool gemini"
|
||||||
|
→ Read phases/03-update-single.md, execute
|
||||||
|
```
|
||||||
|
|
||||||
|
**When ambiguous or no arguments**, proceed to Step 2.
|
||||||
|
|
||||||
|
### Step 2: Interactive Needs Assessment
|
||||||
|
|
||||||
|
**Q1 — 确定内容类别**:
|
||||||
|
|
||||||
|
```
|
||||||
|
AskUserQuestion({
|
||||||
|
questions: [{
|
||||||
|
question: "你要管理哪类内容?",
|
||||||
|
header: "类别",
|
||||||
|
multiSelect: false,
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
label: "CLAUDE.md (项目记忆)",
|
||||||
|
description: "更新模块指令文件,帮助Claude理解代码库结构和约定"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "项目文档 (API+README)",
|
||||||
|
description: "生成API.md和README.md到.workflow/docs/目录"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}]
|
||||||
|
})
|
||||||
|
```
|
||||||
|
|
||||||
|
**Q2a — CLAUDE.md 管理范围** (用户选了 CLAUDE.md):
|
||||||
|
|
||||||
|
```
|
||||||
|
AskUserQuestion({
|
||||||
|
questions: [{
|
||||||
|
question: "CLAUDE.md 更新范围?",
|
||||||
|
header: "范围",
|
||||||
|
multiSelect: false,
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
label: "增量更新 (Recommended)",
|
||||||
|
description: "仅更新git变更模块及其父级,日常开发首选"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "全量更新",
|
||||||
|
description: "更新所有模块,3层架构bottom-up,适合重大重构后"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "单模块更新",
|
||||||
|
description: "指定一个模块,Explore深度分析后生成说明书式文档"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}]
|
||||||
|
})
|
||||||
|
```
|
||||||
|
|
||||||
|
Route mapping:
|
||||||
|
- "增量更新" → `update-related` → Ref: phases/02-update-related.md
|
||||||
|
- "全量更新" → `update-full` → Ref: phases/01-update-full.md
|
||||||
|
- "单模块更新" → `update-single` → continue to Q3
|
||||||
|
|
||||||
|
**Q2b — 文档生成范围** (用户选了项目文档):
|
||||||
|
|
||||||
|
```
|
||||||
|
AskUserQuestion({
|
||||||
|
questions: [{
|
||||||
|
question: "文档生成范围?",
|
||||||
|
header: "范围",
|
||||||
|
multiSelect: false,
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
label: "增量生成 (Recommended)",
|
||||||
|
description: "仅为git变更模块生成/更新文档,日常开发首选"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "全量生成",
|
||||||
|
description: "所有模块+项目级文档(ARCHITECTURE.md等),适合初始化"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}]
|
||||||
|
})
|
||||||
|
```
|
||||||
|
|
||||||
|
Route mapping:
|
||||||
|
- "增量生成" → `docs-related` → Ref: phases/05-docs-related.md
|
||||||
|
- "全量生成" → `docs-full` → Ref: phases/04-docs-full.md
|
||||||
|
|
||||||
|
**Q3 — 补充路径** (仅 update-single 需要,且无路径参数时):
|
||||||
|
|
||||||
|
```
|
||||||
|
AskUserQuestion({
|
||||||
|
questions: [{
|
||||||
|
question: "请指定要更新的模块路径:",
|
||||||
|
header: "路径",
|
||||||
|
multiSelect: false,
|
||||||
|
options: [
|
||||||
|
{
|
||||||
|
label: "src",
|
||||||
|
description: "src 目录"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: ".",
|
||||||
|
description: "项目根目录"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}]
|
||||||
|
})
|
||||||
|
```
|
||||||
|
|
||||||
|
用户可选 "Other" 输入自定义路径。
|
||||||
|
|
||||||
|
### Step 3: Execute Selected Phase
|
||||||
|
|
||||||
|
Based on routing result, read and execute the corresponding phase:
|
||||||
|
|
||||||
|
**Phase Reference Documents** (read on-demand when phase executes):
|
||||||
|
|
||||||
|
| Mode | Document | Purpose |
|
||||||
|
|------|----------|---------|
|
||||||
|
| update-full | [phases/01-update-full.md](phases/01-update-full.md) | Full CLAUDE.md update, 3-layer architecture, batched agents |
|
||||||
|
| update-related | [phases/02-update-related.md](phases/02-update-related.md) | Git-changed CLAUDE.md update, depth-first |
|
||||||
|
| update-single | [phases/03-update-single.md](phases/03-update-single.md) | Single module CLAUDE.md, Explore + handbook style |
|
||||||
|
| docs-full | [phases/04-docs-full.md](phases/04-docs-full.md) | Full API.md + README.md generation |
|
||||||
|
| docs-related | [phases/05-docs-related.md](phases/05-docs-related.md) | Git-changed docs generation, incremental |
|
||||||
|
|
||||||
|
## Shared Configuration
|
||||||
|
|
||||||
|
### Tool Fallback Hierarchy
|
||||||
|
|
||||||
|
All sub-commands share the same fallback:
|
||||||
|
|
||||||
|
```
|
||||||
|
--tool gemini → [gemini, qwen, codex] // default
|
||||||
|
--tool qwen → [qwen, gemini, codex]
|
||||||
|
--tool codex → [codex, gemini, qwen]
|
||||||
|
```
|
||||||
|
|
||||||
|
### Common Parameters
|
||||||
|
|
||||||
|
| Parameter | Description | Default | Used By |
|
||||||
|
|-----------|-------------|---------|---------|
|
||||||
|
| `--tool <gemini\|qwen\|codex>` | Primary CLI tool | gemini | All |
|
||||||
|
| `--path <dir>` | Target directory | . | update-full, docs-full |
|
||||||
|
| `<path>` (positional) | Module path | _(required)_ | update-single |
|
||||||
|
|
||||||
|
### Batching Thresholds
|
||||||
|
|
||||||
|
| Sub-Command | Direct Execution | Agent Batch | Batch Size |
|
||||||
|
|-------------|-----------------|-------------|------------|
|
||||||
|
| update-full | <20 modules | ≥20 modules | 4/agent |
|
||||||
|
| update-related | <15 modules | ≥15 modules | 4/agent |
|
||||||
|
| update-single | always single | N/A | 1 |
|
||||||
|
| docs-full | <20 modules | ≥20 modules | 4/agent |
|
||||||
|
| docs-related | <15 modules | ≥15 modules | 4/agent |
|
||||||
|
|
||||||
|
## Core Rules
|
||||||
|
|
||||||
|
1. **Route before execute**: Determine sub-command before any execution
|
||||||
|
2. **Phase doc is truth**: All execution logic lives in phase docs, router only dispatches
|
||||||
|
3. **Read on-demand**: Only read the selected phase doc, never load all
|
||||||
|
4. **Pass arguments through**: Forward remaining args unchanged to sub-command
|
||||||
|
5. **User confirmation**: Each sub-command handles its own plan presentation and y/n confirmation
|
||||||
|
|
||||||
|
## Error Handling
|
||||||
|
|
||||||
|
| Error | Resolution |
|
||||||
|
|-------|------------|
|
||||||
|
| Unknown sub-command | Fall through to interactive flow |
|
||||||
|
| Phase doc not found | Abort with file path error |
|
||||||
|
| Missing path for update-single | Prompt via Q3 |
|
||||||
|
| Sub-command execution fails | Follow phase doc's own error handling |
|
||||||
@@ -1,24 +1,26 @@
|
|||||||
---
|
# Phase 1: Full CLAUDE.md Update (update-full)
|
||||||
name: update-full
|
|
||||||
description: Update all CLAUDE.md files using layer-based execution (Layer 3→1) with batched agents (4 modules/agent) and gemini→qwen→codex fallback, <20 modules uses direct parallel
|
|
||||||
argument-hint: "[--tool gemini|qwen|codex] [--path <directory>]"
|
|
||||||
---
|
|
||||||
|
|
||||||
# Full Documentation Update (/memory:update-full)
|
全项目 CLAUDE.md 更新,使用 3 层架构 (Layer 3→1),批量 agent 执行,自动 tool fallback。
|
||||||
|
|
||||||
## Overview
|
## Objective
|
||||||
|
|
||||||
Orchestrates project-wide CLAUDE.md updates using batched agent execution with automatic tool fallback and 3-layer architecture support.
|
- 发现所有项目模块并按深度分层
|
||||||
|
- 按 Layer 3→2→1 顺序 bottom-up 更新所有模块的 CLAUDE.md
|
||||||
|
- <20 模块直接并行,≥20 模块使用 agent 批处理 (4 modules/agent)
|
||||||
|
- 自动 tool fallback (gemini→qwen→codex)
|
||||||
|
|
||||||
|
## Parameters
|
||||||
|
|
||||||
**Parameters**:
|
|
||||||
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
||||||
- `--path <directory>`: Target specific directory (default: entire project)
|
- `--path <directory>`: Target specific directory (default: entire project)
|
||||||
|
|
||||||
|
## Execution
|
||||||
|
|
||||||
**Execution Flow**: Discovery → Plan Presentation → Execution → Safety Verification
|
**Execution Flow**: Discovery → Plan Presentation → Execution → Safety Verification
|
||||||
|
|
||||||
## 3-Layer Architecture & Auto-Strategy Selection
|
### 3-Layer Architecture & Auto-Strategy Selection
|
||||||
|
|
||||||
### Layer Definition & Strategy Assignment
|
#### Layer Definition & Strategy Assignment
|
||||||
|
|
||||||
| Layer | Depth | Strategy | Purpose | Context Pattern |
|
| Layer | Depth | Strategy | Purpose | Context Pattern |
|
||||||
|-------|-------|----------|---------|----------------|
|
|-------|-------|----------|---------|----------------|
|
||||||
@@ -30,20 +32,17 @@ Orchestrates project-wide CLAUDE.md updates using batched agent execution with a
|
|||||||
|
|
||||||
**Strategy Auto-Selection**: Strategies are automatically determined by directory depth - no user configuration needed.
|
**Strategy Auto-Selection**: Strategies are automatically determined by directory depth - no user configuration needed.
|
||||||
|
|
||||||
### Strategy Details
|
|
||||||
|
|
||||||
#### Multi-Layer Strategy (Layer 3 Only)
|
#### Multi-Layer Strategy (Layer 3 Only)
|
||||||
- **Use Case**: Deepest directories with unstructured file layouts
|
- **Use Case**: Deepest directories with unstructured file layouts
|
||||||
- **Behavior**: Generates CLAUDE.md for current directory AND each subdirectory containing files
|
- **Behavior**: Generates CLAUDE.md for current directory AND each subdirectory containing files
|
||||||
- **Context**: All files in current directory tree (`@**/*`)
|
- **Context**: All files in current directory tree (`@**/*`)
|
||||||
|
|
||||||
|
|
||||||
#### Single-Layer Strategy (Layers 1-2)
|
#### Single-Layer Strategy (Layers 1-2)
|
||||||
- **Use Case**: Upper layers that aggregate from existing documentation
|
- **Use Case**: Upper layers that aggregate from existing documentation
|
||||||
- **Behavior**: Generates CLAUDE.md only for current directory
|
- **Behavior**: Generates CLAUDE.md only for current directory
|
||||||
- **Context**: Direct children CLAUDE.md files + current directory code files
|
- **Context**: Direct children CLAUDE.md files + current directory code files
|
||||||
|
|
||||||
### Example Flow
|
#### Example Flow
|
||||||
```
|
```
|
||||||
src/auth/handlers/ (depth 3) → MULTI-LAYER STRATEGY
|
src/auth/handlers/ (depth 3) → MULTI-LAYER STRATEGY
|
||||||
CONTEXT: @**/* (all files in handlers/ and subdirs)
|
CONTEXT: @**/* (all files in handlers/ and subdirs)
|
||||||
@@ -62,7 +61,7 @@ src/ (depth 1) → SINGLE-LAYER STRATEGY
|
|||||||
GENERATES: ./CLAUDE.md only
|
GENERATES: ./CLAUDE.md only
|
||||||
```
|
```
|
||||||
|
|
||||||
## Core Execution Rules
|
### Core Execution Rules
|
||||||
|
|
||||||
1. **Analyze First**: Git cache + module discovery before updates
|
1. **Analyze First**: Git cache + module discovery before updates
|
||||||
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
||||||
@@ -74,7 +73,7 @@ src/ (depth 1) → SINGLE-LAYER STRATEGY
|
|||||||
6. **Safety Check**: Verify only CLAUDE.md files modified
|
6. **Safety Check**: Verify only CLAUDE.md files modified
|
||||||
7. **Layer-based Grouping**: Group modules by LAYER (not depth) for execution
|
7. **Layer-based Grouping**: Group modules by LAYER (not depth) for execution
|
||||||
|
|
||||||
## Tool Fallback Hierarchy
|
### Tool Fallback Hierarchy
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
--tool gemini → [gemini, qwen, codex] // default
|
--tool gemini → [gemini, qwen, codex] // default
|
||||||
@@ -90,9 +89,7 @@ src/ (depth 1) → SINGLE-LAYER STRATEGY
|
|||||||
| qwen | Architecture, system design | gemini → codex |
|
| qwen | Architecture, system design | gemini → codex |
|
||||||
| codex | Implementation, code quality | gemini → qwen |
|
| codex | Implementation, code quality | gemini → qwen |
|
||||||
|
|
||||||
## Execution Phases
|
### Step 1.1: Discovery & Analysis
|
||||||
|
|
||||||
### Phase 1: Discovery & Analysis
|
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Cache git changes
|
// Cache git changes
|
||||||
@@ -109,7 +106,7 @@ Bash({command: "cd <target-path> && ccw tool exec get_modules_by_depth '{\"forma
|
|||||||
|
|
||||||
**Smart filter**: Auto-detect and skip tests/build/config/docs based on project tech stack.
|
**Smart filter**: Auto-detect and skip tests/build/config/docs based on project tech stack.
|
||||||
|
|
||||||
### Phase 2: Plan Presentation
|
### Step 1.2: Plan Presentation
|
||||||
|
|
||||||
**For <20 modules**:
|
**For <20 modules**:
|
||||||
```
|
```
|
||||||
@@ -168,7 +165,7 @@ Update Plan:
|
|||||||
Confirm execution? (y/n)
|
Confirm execution? (y/n)
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 3A: Direct Execution (<20 modules)
|
### Step 1.3A: Direct Execution (<20 modules)
|
||||||
|
|
||||||
**Strategy**: Parallel execution within layer (max 4 concurrent), no agent overhead.
|
**Strategy**: Parallel execution within layer (max 4 concurrent), no agent overhead.
|
||||||
|
|
||||||
@@ -202,7 +199,7 @@ for (let layer of [3, 2, 1]) {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 3B: Agent Batch Execution (≥20 modules)
|
### Step 1.3B: Agent Batch Execution (≥20 modules)
|
||||||
|
|
||||||
**Strategy**: Batch modules into groups of 4, spawn memory-bridge agents per batch.
|
**Strategy**: Batch modules into groups of 4, spawn memory-bridge agents per batch.
|
||||||
|
|
||||||
@@ -284,7 +281,8 @@ REPORTING FORMAT:
|
|||||||
⚠️ path/to/module failed with {tool}, trying next...
|
⚠️ path/to/module failed with {tool}, trying next...
|
||||||
❌ FAILED: path/to/module - all tools exhausted
|
❌ FAILED: path/to/module - all tools exhausted
|
||||||
```
|
```
|
||||||
### Phase 4: Safety Verification
|
|
||||||
|
### Step 1.4: Safety Verification
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Check only CLAUDE.md files modified
|
// Check only CLAUDE.md files modified
|
||||||
@@ -308,25 +306,11 @@ Update Summary:
|
|||||||
**Coordinator**: Invalid path abort, user decline handling, safety check with auto-revert
|
**Coordinator**: Invalid path abort, user decline handling, safety check with auto-revert
|
||||||
**Fallback Triggers**: Non-zero exit code, script timeout, unexpected output
|
**Fallback Triggers**: Non-zero exit code, script timeout, unexpected output
|
||||||
|
|
||||||
## Usage Examples
|
## Output
|
||||||
|
|
||||||
```bash
|
- **Files**: Updated CLAUDE.md files across all project modules
|
||||||
# Full project update (auto-strategy selection)
|
- **Report**: Summary with success/failure counts and tool usage statistics
|
||||||
/memory:update-full
|
|
||||||
|
|
||||||
# Target specific directory
|
## Next Phase
|
||||||
/memory:update-full --path .claude
|
|
||||||
/memory:update-full --path src/features/auth
|
|
||||||
|
|
||||||
# Use specific tool
|
Return to [manage.md](../manage.md) router.
|
||||||
/memory:update-full --tool qwen
|
|
||||||
/memory:update-full --path .claude --tool qwen
|
|
||||||
```
|
|
||||||
|
|
||||||
## Key Advantages
|
|
||||||
|
|
||||||
- **Efficiency**: 30 modules → 8 agents (73% reduction from sequential)
|
|
||||||
- **Resilience**: 3-tier tool fallback per module
|
|
||||||
- **Performance**: Parallel batches, no concurrency limits
|
|
||||||
- **Observability**: Per-module tool usage, batch-level metrics
|
|
||||||
- **Automation**: Zero configuration - strategy auto-selected by directory depth
|
|
||||||
@@ -1,22 +1,23 @@
|
|||||||
---
|
# Phase 2: Related CLAUDE.md Update (update-related)
|
||||||
name: update-related
|
|
||||||
description: Update CLAUDE.md for git-changed modules using batched agent execution (4 modules/agent) with gemini→qwen→codex fallback, <15 modules uses direct execution
|
|
||||||
argument-hint: "[--tool gemini|qwen|codex]"
|
|
||||||
---
|
|
||||||
|
|
||||||
# Related Documentation Update (/memory:update-related)
|
仅更新 git 变更模块的 CLAUDE.md,使用深度优先执行和自动 tool fallback。
|
||||||
|
|
||||||
## Overview
|
## Objective
|
||||||
|
|
||||||
Orchestrates context-aware CLAUDE.md updates for changed modules using batched agent execution with automatic tool fallback (gemini→qwen→codex).
|
- 检测 git 变更,识别受影响模块
|
||||||
|
- 按深度 N→0 顺序更新变更模块及其父级上下文
|
||||||
|
- <15 模块直接并行,≥15 模块使用 agent 批处理
|
||||||
|
- 自动 tool fallback (gemini→qwen→codex)
|
||||||
|
|
||||||
|
## Parameters
|
||||||
|
|
||||||
**Parameters**:
|
|
||||||
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
||||||
|
|
||||||
**Execution Flow**:
|
## Execution
|
||||||
1. Change Detection → 2. Plan Presentation → 3. Batched Agent Execution → 4. Safety Verification
|
|
||||||
|
|
||||||
## Core Rules
|
**Execution Flow**: Change Detection → Plan Presentation → Batched Execution → Safety Verification
|
||||||
|
|
||||||
|
### Core Rules
|
||||||
|
|
||||||
1. **Detect Changes First**: Use git diff to identify affected modules
|
1. **Detect Changes First**: Use git diff to identify affected modules
|
||||||
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
||||||
@@ -27,7 +28,7 @@ Orchestrates context-aware CLAUDE.md updates for changed modules using batched a
|
|||||||
5. **Depth Sequential**: Process depths N→0, parallel batches within depth (both modes)
|
5. **Depth Sequential**: Process depths N→0, parallel batches within depth (both modes)
|
||||||
6. **Related Mode**: Update only changed modules and their parent contexts
|
6. **Related Mode**: Update only changed modules and their parent contexts
|
||||||
|
|
||||||
## Tool Fallback Hierarchy
|
### Tool Fallback Hierarchy
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
--tool gemini → [gemini, qwen, codex] // default
|
--tool gemini → [gemini, qwen, codex] // default
|
||||||
@@ -37,7 +38,7 @@ Orchestrates context-aware CLAUDE.md updates for changed modules using batched a
|
|||||||
|
|
||||||
**Trigger**: Non-zero exit code from update script
|
**Trigger**: Non-zero exit code from update script
|
||||||
|
|
||||||
## Phase 1: Change Detection & Analysis
|
### Step 2.1: Change Detection & Analysis
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Detect changed modules
|
// Detect changed modules
|
||||||
@@ -53,7 +54,7 @@ Bash({command: "git add -A 2>/dev/null || true", run_in_background: false});
|
|||||||
|
|
||||||
**Fallback**: If no changes detected, use recent modules (first 10 by depth).
|
**Fallback**: If no changes detected, use recent modules (first 10 by depth).
|
||||||
|
|
||||||
## Phase 2: Plan Presentation
|
### Step 2.2: Plan Presentation
|
||||||
|
|
||||||
**Present filtered plan**:
|
**Present filtered plan**:
|
||||||
```
|
```
|
||||||
@@ -87,7 +88,7 @@ Related Update Plan:
|
|||||||
- <15 modules: Direct execution
|
- <15 modules: Direct execution
|
||||||
- ≥15 modules: Agent batch execution
|
- ≥15 modules: Agent batch execution
|
||||||
|
|
||||||
## Phase 3A: Direct Execution (<15 modules)
|
### Step 2.3A: Direct Execution (<15 modules)
|
||||||
|
|
||||||
**Strategy**: Parallel execution within depth (max 4 concurrent), no agent overhead.
|
**Strategy**: Parallel execution within depth (max 4 concurrent), no agent overhead.
|
||||||
|
|
||||||
@@ -119,11 +120,9 @@ for (let depth of sorted_depths.reverse()) { // N → 0
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
---
|
### Step 2.3B: Agent Batch Execution (≥15 modules)
|
||||||
|
|
||||||
## Phase 3B: Agent Batch Execution (≥15 modules)
|
#### Batching Strategy
|
||||||
|
|
||||||
### Batching Strategy
|
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Batch modules into groups of 4
|
// Batch modules into groups of 4
|
||||||
@@ -137,7 +136,7 @@ function batch_modules(modules, batch_size = 4) {
|
|||||||
// Examples: 10→[4,4,2] | 8→[4,4] | 3→[3]
|
// Examples: 10→[4,4,2] | 8→[4,4] | 3→[3]
|
||||||
```
|
```
|
||||||
|
|
||||||
### Coordinator Orchestration
|
#### Coordinator Orchestration
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
let modules_by_depth = group_by_depth(changed_modules);
|
let modules_by_depth = group_by_depth(changed_modules);
|
||||||
@@ -161,7 +160,7 @@ for (let depth of sorted_depths.reverse()) { // N → 0
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Batch Worker Prompt Template
|
#### Batch Worker Prompt Template
|
||||||
|
|
||||||
```
|
```
|
||||||
PURPOSE: Update CLAUDE.md for assigned modules with tool fallback (related mode)
|
PURPOSE: Update CLAUDE.md for assigned modules with tool fallback (related mode)
|
||||||
@@ -212,7 +211,7 @@ Report final summary with:
|
|||||||
- Tool usage: {{tool_1}}:X, {{tool_2}}:Y, {{tool_3}}:Z
|
- Tool usage: {{tool_1}}:X, {{tool_2}}:Y, {{tool_3}}:Z
|
||||||
```
|
```
|
||||||
|
|
||||||
## Phase 4: Safety Verification
|
### Step 2.4: Safety Verification
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Check only CLAUDE.md modified
|
// Check only CLAUDE.md modified
|
||||||
@@ -240,16 +239,6 @@ Update Summary:
|
|||||||
4 files changed, 82 insertions(+), 6 deletions(-)
|
4 files changed, 82 insertions(+), 6 deletions(-)
|
||||||
```
|
```
|
||||||
|
|
||||||
## Execution Summary
|
|
||||||
|
|
||||||
**Module Count Threshold**:
|
|
||||||
- **<15 modules**: Coordinator executes Phase 3A (Direct Execution)
|
|
||||||
- **≥15 modules**: Coordinator executes Phase 3B (Agent Batch Execution)
|
|
||||||
|
|
||||||
**Agent Hierarchy** (for ≥15 modules):
|
|
||||||
- **Coordinator**: Handles batch division, spawns worker agents per depth
|
|
||||||
- **Worker Agents**: Each processes 4 modules with tool fallback (related mode)
|
|
||||||
|
|
||||||
## Error Handling
|
## Error Handling
|
||||||
|
|
||||||
**Batch Worker**:
|
**Batch Worker**:
|
||||||
@@ -268,65 +257,11 @@ Update Summary:
|
|||||||
- Script timeout
|
- Script timeout
|
||||||
- Unexpected output
|
- Unexpected output
|
||||||
|
|
||||||
## Tool Reference
|
## Output
|
||||||
|
|
||||||
| Tool | Best For | Fallback To |
|
- **Files**: Updated CLAUDE.md files for changed modules and their parents
|
||||||
|--------|--------------------------------|----------------|
|
- **Report**: Summary with success/failure counts, tool usage, and git diff statistics
|
||||||
| gemini | Documentation, patterns | qwen → codex |
|
|
||||||
| qwen | Architecture, system design | gemini → codex |
|
|
||||||
| codex | Implementation, code quality | gemini → qwen |
|
|
||||||
|
|
||||||
## Usage Examples
|
## Next Phase
|
||||||
|
|
||||||
```bash
|
Return to [manage.md](../manage.md) router.
|
||||||
# Daily development update
|
|
||||||
/memory:update-related
|
|
||||||
|
|
||||||
# After feature work with specific tool
|
|
||||||
/memory:update-related --tool qwen
|
|
||||||
|
|
||||||
# Code quality review after implementation
|
|
||||||
/memory:update-related --tool codex
|
|
||||||
```
|
|
||||||
|
|
||||||
## Key Advantages
|
|
||||||
|
|
||||||
**Efficiency**: 30 modules → 8 agents (73% reduction)
|
|
||||||
**Resilience**: 3-tier fallback per module
|
|
||||||
**Performance**: Parallel batches, no concurrency limits
|
|
||||||
**Context-aware**: Updates based on actual git changes
|
|
||||||
**Fast**: Only affected modules, not entire project
|
|
||||||
|
|
||||||
## Coordinator Checklist
|
|
||||||
|
|
||||||
- Parse `--tool` (default: gemini)
|
|
||||||
- Refresh code index for accurate change detection
|
|
||||||
- Detect changed modules via detect_changed_modules.sh
|
|
||||||
- **Smart filter modules** (auto-detect tech stack, skip tests/build/config/docs)
|
|
||||||
- Cache git changes
|
|
||||||
- Apply fallback if no changes (recent 10 modules)
|
|
||||||
- Construct tool fallback order
|
|
||||||
- **Present filtered plan** with skip reasons and change types
|
|
||||||
- **Wait for y/n confirmation**
|
|
||||||
- Determine execution mode:
|
|
||||||
- **<15 modules**: Direct execution (Phase 3A)
|
|
||||||
- For each depth (N→0): Sequential module updates with tool fallback
|
|
||||||
- **≥15 modules**: Agent batch execution (Phase 3B)
|
|
||||||
- For each depth (N→0): Batch modules (4 per batch), spawn batch workers in parallel
|
|
||||||
- Wait for depth/batch completion
|
|
||||||
- Aggregate results
|
|
||||||
- Safety check (only CLAUDE.md modified)
|
|
||||||
- Display git diff statistics + summary
|
|
||||||
|
|
||||||
## Comparison with Full Update
|
|
||||||
|
|
||||||
| Aspect | Related Update | Full Update |
|
|
||||||
|--------|----------------|-------------|
|
|
||||||
| **Scope** | Changed modules only | All project modules |
|
|
||||||
| **Speed** | Fast (minutes) | Slower (10-30 min) |
|
|
||||||
| **Use case** | Daily development | Major refactoring |
|
|
||||||
| **Mode** | `"related"` | `"full"` |
|
|
||||||
| **Trigger** | After commits | After major changes |
|
|
||||||
| **Batching** | 4 modules/agent | 4 modules/agent |
|
|
||||||
| **Fallback** | gemini→qwen→codex | gemini→qwen→codex |
|
|
||||||
| **Complexity threshold** | ≤15 modules | ≤20 modules |
|
|
||||||
@@ -1,81 +1,47 @@
|
|||||||
---
|
# Phase 3: Single Module CLAUDE.md Update (update-single)
|
||||||
name: update-single
|
|
||||||
description: Update single module CLAUDE.md using Explore agent for deep codebase understanding, producing manual-style documentation (handbook, not API reference)
|
|
||||||
argument-hint: "<path> [--tool gemini|qwen|codex]"
|
|
||||||
allowed-tools: Task(*), Bash(*), AskUserQuestion(*)
|
|
||||||
---
|
|
||||||
|
|
||||||
# Single Module Documentation Update (/memory:update-single)
|
使用 Explore agent 深度分析后,为单个目标模块生成手册式 (说明书) CLAUDE.md。
|
||||||
|
|
||||||
## Overview
|
## Objective
|
||||||
|
|
||||||
Generates a manual-style CLAUDE.md for a single target directory using Explore agent for deep semantic codebase understanding. The output reads like a module handbook — explaining what it does, how to use it, and how it integrates — rather than dry API documentation.
|
- 验证目标路径并扫描结构
|
||||||
|
- 使用 Explore agent 进行 7 维度深度探索
|
||||||
**Core capabilities:**
|
- 交互确认后通过 CLI tool 生成手册式 CLAUDE.md
|
||||||
- Explore agent for semantic codebase exploration (not just file scanning)
|
|
||||||
- Manual/handbook-style output (usage guide, not reference docs)
|
|
||||||
- Interactive confirmation with exploration summary preview
|
|
||||||
- Tool fallback (gemini→qwen→codex)
|
- Tool fallback (gemini→qwen→codex)
|
||||||
|
|
||||||
## Usage
|
## Parameters
|
||||||
|
|
||||||
```bash
|
- `<path>`: Target directory path (required)
|
||||||
/memory:update-single <path> [--tool gemini|qwen|codex]
|
- `--tool <gemini|qwen|codex>`: Primary CLI tool (default: gemini)
|
||||||
|
|
||||||
# Arguments
|
## Execution
|
||||||
<path> Target directory path (required)
|
|
||||||
|
|
||||||
# Options
|
|
||||||
--tool <gemini|qwen|codex> Primary CLI tool (default: gemini)
|
|
||||||
|
|
||||||
# Examples
|
|
||||||
/memory:update-single src/auth
|
|
||||||
/memory:update-single .claude/commands --tool qwen
|
|
||||||
/memory:update-single ccw/frontend/src/components/issue
|
|
||||||
```
|
|
||||||
|
|
||||||
## Output Artifacts
|
|
||||||
|
|
||||||
| Artifact | Description |
|
|
||||||
|----------|-------------|
|
|
||||||
| `<path>/CLAUDE.md` | Manual-style module handbook |
|
|
||||||
|
|
||||||
**CLAUDE.md Style** — "说明书" not "文档":
|
|
||||||
- What this module does (purpose & responsibility)
|
|
||||||
- How to use it (patterns, conventions, examples)
|
|
||||||
- How it integrates (dependencies, exports, data flow)
|
|
||||||
- Important constraints (gotchas, rules, limitations)
|
|
||||||
|
|
||||||
## Execution Process
|
|
||||||
|
|
||||||
```
|
```
|
||||||
Phase 1: Target Validation & Scan
|
Step 3.1: Target Validation & Scan
|
||||||
├─ Parse arguments (path, --tool)
|
├─ Parse arguments (path, --tool)
|
||||||
├─ Validate target directory exists
|
├─ Validate target directory exists
|
||||||
└─ Quick structure scan (file count, types, depth)
|
└─ Quick structure scan (file count, types, depth)
|
||||||
|
|
||||||
Phase 2: Deep Exploration (Explore Agent)
|
Step 3.2: Deep Exploration (Explore Agent)
|
||||||
├─ Launch Explore agent with "very thorough" level
|
├─ Launch Explore agent with "very thorough" level
|
||||||
├─ Analyze purpose, structure, patterns, exports, dependencies
|
├─ Analyze purpose, structure, patterns, exports, dependencies
|
||||||
└─ Build comprehensive module understanding
|
└─ Build comprehensive module understanding
|
||||||
|
|
||||||
Phase 3: Confirmation
|
Step 3.3: Confirmation
|
||||||
├─ Display exploration summary (key findings)
|
├─ Display exploration summary (key findings)
|
||||||
└─ AskUserQuestion: Generate / Cancel
|
└─ AskUserQuestion: Generate / Cancel
|
||||||
|
|
||||||
Phase 4: Generate CLAUDE.md (CLI Tool)
|
Step 3.4: Generate CLAUDE.md (CLI Tool)
|
||||||
├─ Construct manual-style prompt from exploration results
|
├─ Construct manual-style prompt from exploration results
|
||||||
├─ Execute ccw cli with --mode write
|
├─ Execute ccw cli with --mode write
|
||||||
├─ Tool fallback on failure
|
├─ Tool fallback on failure
|
||||||
└─ Write to <path>/CLAUDE.md
|
└─ Write to <path>/CLAUDE.md
|
||||||
|
|
||||||
Phase 5: Verification
|
Step 3.5: Verification
|
||||||
└─ Display generated CLAUDE.md preview + stats
|
└─ Display generated CLAUDE.md preview + stats
|
||||||
```
|
```
|
||||||
|
|
||||||
## Implementation
|
### Step 3.1: Target Validation & Scan
|
||||||
|
|
||||||
### Phase 1: Target Validation & Scan
|
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Parse arguments
|
// Parse arguments
|
||||||
@@ -86,7 +52,7 @@ const primaryTool = toolFlagIdx !== -1 ? parts[toolFlagIdx + 1] : 'gemini'
|
|||||||
const targetPath = parts.find(p => !p.startsWith('--') && p !== primaryTool)
|
const targetPath = parts.find(p => !p.startsWith('--') && p !== primaryTool)
|
||||||
|
|
||||||
if (!targetPath) {
|
if (!targetPath) {
|
||||||
console.log('ERROR: <path> is required. Usage: /memory:update-single <path> [--tool gemini|qwen|codex]')
|
console.log('ERROR: <path> is required. Usage: /memory:manage update-single <path> [--tool gemini|qwen|codex]')
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -112,9 +78,9 @@ Launching deep exploration...
|
|||||||
`)
|
`)
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 2: Deep Exploration (Explore Agent)
|
### Step 3.2: Deep Exploration (Explore Agent)
|
||||||
|
|
||||||
**⚠️ CRITICAL**: Use `run_in_background: false` — exploration results are REQUIRED before generation.
|
**CRITICAL**: Use `run_in_background: false` — exploration results are REQUIRED before generation.
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
const explorationResult = Task(
|
const explorationResult = Task(
|
||||||
@@ -173,7 +139,7 @@ Return a structured summary covering all 7 dimensions above. Include specific fi
|
|||||||
)
|
)
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 3: Confirmation
|
### Step 3.3: Confirmation
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
console.log(`
|
console.log(`
|
||||||
@@ -203,7 +169,7 @@ AskUserQuestion({
|
|||||||
// Cancel → abort
|
// Cancel → abort
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 4: Generate CLAUDE.md (CLI Tool)
|
### Step 3.4: Generate CLAUDE.md (CLI Tool)
|
||||||
|
|
||||||
**Tool fallback hierarchy**:
|
**Tool fallback hierarchy**:
|
||||||
```javascript
|
```javascript
|
||||||
@@ -285,7 +251,7 @@ CONSTRAINTS: Only write CLAUDE.md, no other files" --tool ${tool} --mode write -
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 5: Verification
|
### Step 3.5: Verification
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Check file was created/updated
|
// Check file was created/updated
|
||||||
@@ -311,8 +277,8 @@ console.log(`
|
|||||||
|
|
||||||
The generated CLAUDE.md is a **说明书 (handbook)**, NOT a reference doc:
|
The generated CLAUDE.md is a **说明书 (handbook)**, NOT a reference doc:
|
||||||
|
|
||||||
| Aspect | Handbook Style ✅ | Reference Doc Style ❌ |
|
| Aspect | Handbook Style | Reference Doc Style |
|
||||||
|--------|-------------------|----------------------|
|
|--------|---------------|---------------------|
|
||||||
| Purpose | "This module handles user auth" | "Authentication module" |
|
| Purpose | "This module handles user auth" | "Authentication module" |
|
||||||
| Content | How to work with it | What every function does |
|
| Content | How to work with it | What every function does |
|
||||||
| Patterns | "Always use `createAuthMiddleware()`" | "List of all exports" |
|
| Patterns | "Always use `createAuthMiddleware()`" | "List of all exports" |
|
||||||
@@ -330,18 +296,11 @@ The generated CLAUDE.md is a **说明书 (handbook)**, NOT a reference doc:
|
|||||||
| Empty directory | Abort — nothing to document |
|
| Empty directory | Abort — nothing to document |
|
||||||
| Existing CLAUDE.md | Overwrite entirely (full regeneration) |
|
| Existing CLAUDE.md | Overwrite entirely (full regeneration) |
|
||||||
|
|
||||||
## Usage Examples
|
## Output
|
||||||
|
|
||||||
```bash
|
- **File**: `<path>/CLAUDE.md` — Manual-style module handbook
|
||||||
# Generate handbook for a module
|
- **Preview**: First 30 lines displayed after generation
|
||||||
/memory:update-single src/auth
|
|
||||||
|
|
||||||
# Use specific tool
|
## Next Phase
|
||||||
/memory:update-single .claude/commands --tool qwen
|
|
||||||
|
|
||||||
# Deep nested module
|
Return to [manage.md](../manage.md) router.
|
||||||
/memory:update-single ccw/frontend/src/components/issue
|
|
||||||
|
|
||||||
# Root-level documentation
|
|
||||||
/memory:update-single .
|
|
||||||
```
|
|
||||||
@@ -1,24 +1,27 @@
|
|||||||
---
|
# Phase 4: Full Documentation Generation (docs-full)
|
||||||
name: docs-full-cli
|
|
||||||
description: Generate full project documentation using CLI execution (Layer 3→1) with batched agents (4 modules/agent) and gemini→qwen→codex fallback, <20 modules uses direct parallel
|
|
||||||
argument-hint: "[path] [--tool <gemini|qwen|codex>]"
|
|
||||||
---
|
|
||||||
|
|
||||||
# Full Documentation Generation - CLI Mode (/memory:docs-full-cli)
|
全项目 API.md + README.md 文档生成,使用 CLI 执行、3 层架构和自动 tool fallback,输出到 .workflow/docs/。
|
||||||
|
|
||||||
## Overview
|
## Objective
|
||||||
|
|
||||||
Orchestrates project-wide documentation generation using CLI-based execution with batched agents and automatic tool fallback.
|
- 发现所有项目模块并按深度分层
|
||||||
|
- 按 Layer 3→2→1 顺序生成 API.md + README.md 文档
|
||||||
|
- <20 模块直接并行,≥20 模块使用 agent 批处理
|
||||||
|
- 生成项目级文档 (README.md, ARCHITECTURE.md, EXAMPLES.md)
|
||||||
|
- 自动 tool fallback (gemini→qwen→codex)
|
||||||
|
|
||||||
|
## Parameters
|
||||||
|
|
||||||
**Parameters**:
|
|
||||||
- `path`: Target directory (default: current directory)
|
- `path`: Target directory (default: current directory)
|
||||||
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
||||||
|
|
||||||
**Execution Flow**: Discovery → Plan Presentation → Execution → Verification
|
## Execution
|
||||||
|
|
||||||
## 3-Layer Architecture & Auto-Strategy Selection
|
**Execution Flow**: Discovery → Plan Presentation → Execution → Project-Level Docs → Verification
|
||||||
|
|
||||||
### Layer Definition & Strategy Assignment
|
### 3-Layer Architecture & Auto-Strategy Selection
|
||||||
|
|
||||||
|
#### Layer Definition & Strategy Assignment
|
||||||
|
|
||||||
| Layer | Depth | Strategy | Purpose | Context Pattern |
|
| Layer | Depth | Strategy | Purpose | Context Pattern |
|
||||||
|-------|-------|----------|---------|----------------|
|
|-------|-------|----------|---------|----------------|
|
||||||
@@ -28,24 +31,19 @@ Orchestrates project-wide documentation generation using CLI-based execution wit
|
|||||||
|
|
||||||
**Generation Direction**: Layer 3 → Layer 2 → Layer 1 (bottom-up dependency flow)
|
**Generation Direction**: Layer 3 → Layer 2 → Layer 1 (bottom-up dependency flow)
|
||||||
|
|
||||||
**Strategy Auto-Selection**: Strategies are automatically determined by directory depth - no user configuration needed.
|
|
||||||
|
|
||||||
### Strategy Details
|
|
||||||
|
|
||||||
#### Full Strategy (Layer 3 Only)
|
#### Full Strategy (Layer 3 Only)
|
||||||
- **Use Case**: Deepest directories with comprehensive file coverage
|
- **Use Case**: Deepest directories with comprehensive file coverage
|
||||||
- **Behavior**: Generates API.md + README.md for current directory AND subdirectories containing code
|
- **Behavior**: Generates API.md + README.md for current directory AND subdirectories containing code
|
||||||
- **Context**: All files in current directory tree (`@**/*`)
|
- **Context**: All files in current directory tree (`@**/*`)
|
||||||
- **Output**: `.workflow/docs/{project_name}/{path}/API.md` + `README.md`
|
- **Output**: `.workflow/docs/{project_name}/{path}/API.md` + `README.md`
|
||||||
|
|
||||||
|
|
||||||
#### Single Strategy (Layers 1-2)
|
#### Single Strategy (Layers 1-2)
|
||||||
- **Use Case**: Upper layers that aggregate from existing documentation
|
- **Use Case**: Upper layers that aggregate from existing documentation
|
||||||
- **Behavior**: Generates API.md + README.md only in current directory
|
- **Behavior**: Generates API.md + README.md only in current directory
|
||||||
- **Context**: Direct children docs + current directory code files
|
- **Context**: Direct children docs + current directory code files
|
||||||
- **Output**: `.workflow/docs/{project_name}/{path}/API.md` + `README.md`
|
- **Output**: `.workflow/docs/{project_name}/{path}/API.md` + `README.md`
|
||||||
|
|
||||||
### Example Flow
|
#### Example Flow
|
||||||
```
|
```
|
||||||
src/auth/handlers/ (depth 3) → FULL STRATEGY
|
src/auth/handlers/ (depth 3) → FULL STRATEGY
|
||||||
CONTEXT: @**/* (all files in handlers/ and subdirs)
|
CONTEXT: @**/* (all files in handlers/ and subdirs)
|
||||||
@@ -64,7 +62,7 @@ src/ (depth 1) → SINGLE STRATEGY
|
|||||||
GENERATES: .workflow/docs/project/{API.md,README.md} only
|
GENERATES: .workflow/docs/project/{API.md,README.md} only
|
||||||
```
|
```
|
||||||
|
|
||||||
## Core Execution Rules
|
### Core Execution Rules
|
||||||
|
|
||||||
1. **Analyze First**: Module discovery + folder classification before generation
|
1. **Analyze First**: Module discovery + folder classification before generation
|
||||||
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
||||||
@@ -76,7 +74,7 @@ src/ (depth 1) → SINGLE STRATEGY
|
|||||||
6. **Safety Check**: Verify only docs files modified in .workflow/docs/
|
6. **Safety Check**: Verify only docs files modified in .workflow/docs/
|
||||||
7. **Layer-based Grouping**: Group modules by LAYER (not depth) for execution
|
7. **Layer-based Grouping**: Group modules by LAYER (not depth) for execution
|
||||||
|
|
||||||
## Tool Fallback Hierarchy
|
### Tool Fallback Hierarchy
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
--tool gemini → [gemini, qwen, codex] // default
|
--tool gemini → [gemini, qwen, codex] // default
|
||||||
@@ -84,17 +82,7 @@ src/ (depth 1) → SINGLE STRATEGY
|
|||||||
--tool codex → [codex, gemini, qwen]
|
--tool codex → [codex, gemini, qwen]
|
||||||
```
|
```
|
||||||
|
|
||||||
**Trigger**: Non-zero exit code from generation script
|
### Step 4.1: Discovery & Analysis
|
||||||
|
|
||||||
| Tool | Best For | Fallback To |
|
|
||||||
|--------|--------------------------------|----------------|
|
|
||||||
| gemini | Documentation, patterns | qwen → codex |
|
|
||||||
| qwen | Architecture, system design | gemini → codex |
|
|
||||||
| codex | Implementation, code quality | gemini → qwen |
|
|
||||||
|
|
||||||
## Execution Phases
|
|
||||||
|
|
||||||
### Phase 1: Discovery & Analysis
|
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Get project metadata
|
// Get project metadata
|
||||||
@@ -111,7 +99,7 @@ Bash({command: "cd <target-path> && ccw tool exec get_modules_by_depth '{\"forma
|
|||||||
|
|
||||||
**Smart filter**: Auto-detect and skip tests/build/config/vendor based on project tech stack.
|
**Smart filter**: Auto-detect and skip tests/build/config/vendor based on project tech stack.
|
||||||
|
|
||||||
### Phase 2: Plan Presentation
|
### Step 4.2: Plan Presentation
|
||||||
|
|
||||||
**For <20 modules**:
|
**For <20 modules**:
|
||||||
```
|
```
|
||||||
@@ -139,7 +127,6 @@ Documentation Generation Plan:
|
|||||||
|
|
||||||
Auto-skipped: ./tests, __pycache__, node_modules (15 paths)
|
Auto-skipped: ./tests, __pycache__, node_modules (15 paths)
|
||||||
Execution order: Layer 2 → Layer 1
|
Execution order: Layer 2 → Layer 1
|
||||||
Estimated time: ~5-10 minutes
|
|
||||||
|
|
||||||
Confirm execution? (y/n)
|
Confirm execution? (y/n)
|
||||||
```
|
```
|
||||||
@@ -176,12 +163,10 @@ Documentation Generation Plan:
|
|||||||
- Layer 2 (15 modules, depth 1-2): 4 agents [4, 4, 4, 3]
|
- Layer 2 (15 modules, depth 1-2): 4 agents [4, 4, 4, 3]
|
||||||
- Layer 1 (2 modules, depth 0): 1 agent [2]
|
- Layer 1 (2 modules, depth 0): 1 agent [2]
|
||||||
|
|
||||||
Estimated time: ~15-25 minutes
|
|
||||||
|
|
||||||
Confirm execution? (y/n)
|
Confirm execution? (y/n)
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 3A: Direct Execution (<20 modules)
|
### Step 4.3A: Direct Execution (<20 modules)
|
||||||
|
|
||||||
**Strategy**: Parallel execution within layer (max 4 concurrent), no agent overhead.
|
**Strategy**: Parallel execution within layer (max 4 concurrent), no agent overhead.
|
||||||
|
|
||||||
@@ -217,7 +202,7 @@ for (let layer of [3, 2, 1]) {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 3B: Agent Batch Execution (≥20 modules)
|
### Step 4.3B: Agent Batch Execution (≥20 modules)
|
||||||
|
|
||||||
**Strategy**: Batch modules into groups of 4, spawn memory-bridge agents per batch.
|
**Strategy**: Batch modules into groups of 4, spawn memory-bridge agents per batch.
|
||||||
|
|
||||||
@@ -290,7 +275,6 @@ EXECUTION FLOW (for each module):
|
|||||||
2. Handle complete failure (all tools failed):
|
2. Handle complete failure (all tools failed):
|
||||||
if [ $exit_code -ne 0 ]; then
|
if [ $exit_code -ne 0 ]; then
|
||||||
report "❌ FAILED: {{module_path}} - all tools exhausted"
|
report "❌ FAILED: {{module_path}} - all tools exhausted"
|
||||||
# Continue to next module (do not abort batch)
|
|
||||||
fi
|
fi
|
||||||
|
|
||||||
FOLDER TYPE HANDLING:
|
FOLDER TYPE HANDLING:
|
||||||
@@ -310,7 +294,7 @@ REPORTING FORMAT:
|
|||||||
❌ FAILED: path/to/module - all tools exhausted
|
❌ FAILED: path/to/module - all tools exhausted
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 4: Project-Level Documentation
|
### Step 4.4: Project-Level Documentation
|
||||||
|
|
||||||
**After all module documentation is generated, create project-level documentation files.**
|
**After all module documentation is generated, create project-level documentation files.**
|
||||||
|
|
||||||
@@ -370,7 +354,7 @@ Project-Level Documentation:
|
|||||||
✅ api/README.md (HTTP API reference) [optional]
|
✅ api/README.md (HTTP API reference) [optional]
|
||||||
```
|
```
|
||||||
|
|
||||||
### Phase 5: Verification
|
### Step 4.5: Verification
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Check documentation files created
|
// Check documentation files created
|
||||||
@@ -398,12 +382,6 @@ Documentation Generation Summary:
|
|||||||
└── README.md
|
└── README.md
|
||||||
```
|
```
|
||||||
|
|
||||||
## Error Handling
|
|
||||||
|
|
||||||
**Batch Worker**: Tool fallback per module, batch isolation, clear status reporting
|
|
||||||
**Coordinator**: Invalid path abort, user decline handling, verification with cleanup
|
|
||||||
**Fallback Triggers**: Non-zero exit code, script timeout, unexpected output
|
|
||||||
|
|
||||||
## Output Structure
|
## Output Structure
|
||||||
|
|
||||||
```
|
```
|
||||||
@@ -426,36 +404,18 @@ Documentation Generation Summary:
|
|||||||
│ └── core/
|
│ └── core/
|
||||||
│ ├── API.md
|
│ ├── API.md
|
||||||
│ └── README.md
|
│ └── README.md
|
||||||
├── README.md # ✨ Project root overview (auto-generated)
|
├── README.md # Project root overview (auto-generated)
|
||||||
├── ARCHITECTURE.md # ✨ System design (auto-generated)
|
├── ARCHITECTURE.md # System design (auto-generated)
|
||||||
├── EXAMPLES.md # ✨ Usage examples (auto-generated)
|
├── EXAMPLES.md # Usage examples (auto-generated)
|
||||||
└── api/ # ✨ Optional (auto-generated if HTTP API detected)
|
└── api/ # Optional (auto-generated if HTTP API detected)
|
||||||
└── README.md # HTTP API reference
|
└── README.md # HTTP API reference
|
||||||
```
|
```
|
||||||
|
|
||||||
## Usage Examples
|
## Error Handling
|
||||||
|
|
||||||
```bash
|
**Batch Worker**: Tool fallback per module, batch isolation, clear status reporting
|
||||||
# Full project documentation generation
|
**Coordinator**: Invalid path abort, user decline handling, verification with cleanup
|
||||||
/memory:docs-full-cli
|
**Fallback Triggers**: Non-zero exit code, script timeout, unexpected output
|
||||||
|
|
||||||
# Target specific directory
|
|
||||||
/memory:docs-full-cli src/features/auth
|
|
||||||
/memory:docs-full-cli .claude
|
|
||||||
|
|
||||||
# Use specific tool
|
|
||||||
/memory:docs-full-cli --tool qwen
|
|
||||||
/memory:docs-full-cli src --tool qwen
|
|
||||||
```
|
|
||||||
|
|
||||||
## Key Advantages
|
|
||||||
|
|
||||||
- **Efficiency**: 30 modules → 8 agents (73% reduction from sequential)
|
|
||||||
- **Resilience**: 3-tier tool fallback per module
|
|
||||||
- **Performance**: Parallel batches, no concurrency limits
|
|
||||||
- **Observability**: Per-module tool usage, batch-level metrics
|
|
||||||
- **Automation**: Zero configuration - strategy auto-selected by directory depth
|
|
||||||
- **Path Mirroring**: Clear 1:1 mapping between source and documentation structure
|
|
||||||
|
|
||||||
## Template Reference
|
## Template Reference
|
||||||
|
|
||||||
@@ -464,8 +424,12 @@ Templates used from `~/.ccw/workflows/cli-templates/prompts/documentation/`:
|
|||||||
- `module-readme.txt`: Module purpose, usage, dependencies
|
- `module-readme.txt`: Module purpose, usage, dependencies
|
||||||
- `folder-navigation.txt`: Navigation README for folders with subdirectories
|
- `folder-navigation.txt`: Navigation README for folders with subdirectories
|
||||||
|
|
||||||
## Related Commands
|
## Output
|
||||||
|
|
||||||
- `/memory:docs` - Agent-based documentation planning workflow
|
- **Directory**: `.workflow/docs/{project_name}/` — Complete documentation tree
|
||||||
- `/memory:docs-related-cli` - Update docs for changed modules only
|
- **Project-Level**: README.md, ARCHITECTURE.md, EXAMPLES.md, api/README.md (optional)
|
||||||
- `/workflow:execute` - Execute documentation tasks (when using agent mode)
|
- **Report**: Summary with success/failure counts and tool usage statistics
|
||||||
|
|
||||||
|
## Next Phase
|
||||||
|
|
||||||
|
Return to [manage.md](../manage.md) router.
|
||||||
@@ -1,22 +1,24 @@
|
|||||||
---
|
# Phase 5: Related Documentation Generation (docs-related)
|
||||||
name: docs-related-cli
|
|
||||||
description: Generate/update documentation for git-changed modules using CLI execution with batched agents (4 modules/agent) and gemini→qwen→codex fallback, <15 modules uses direct parallel
|
|
||||||
argument-hint: "[--tool <gemini|qwen|codex>]"
|
|
||||||
---
|
|
||||||
|
|
||||||
# Related Documentation Generation - CLI Mode (/memory:docs-related-cli)
|
仅为 git 变更模块生成/更新 API.md + README.md 文档,使用增量策略和自动 tool fallback。
|
||||||
|
|
||||||
## Overview
|
## Objective
|
||||||
|
|
||||||
Orchestrates context-aware documentation generation/update for changed modules using CLI-based execution with batched agents and automatic tool fallback (gemini→qwen→codex).
|
- 检测 git 变更,识别受影响模块
|
||||||
|
- 按深度 N→0 顺序为变更模块生成/更新文档
|
||||||
|
- <15 模块直接并行,≥15 模块使用 agent 批处理
|
||||||
|
- 使用 single 策略进行增量更新
|
||||||
|
- 自动 tool fallback (gemini→qwen→codex)
|
||||||
|
|
||||||
|
## Parameters
|
||||||
|
|
||||||
**Parameters**:
|
|
||||||
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
- `--tool <gemini|qwen|codex>`: Primary tool (default: gemini)
|
||||||
|
|
||||||
**Execution Flow**:
|
## Execution
|
||||||
1. Change Detection → 2. Plan Presentation → 3. Batched Execution → 4. Verification
|
|
||||||
|
|
||||||
## Core Rules
|
**Execution Flow**: Change Detection → Plan Presentation → Batched Execution → Verification
|
||||||
|
|
||||||
|
### Core Rules
|
||||||
|
|
||||||
1. **Detect Changes First**: Use git diff to identify affected modules
|
1. **Detect Changes First**: Use git diff to identify affected modules
|
||||||
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
2. **Wait for Approval**: Present plan, no execution without user confirmation
|
||||||
@@ -28,7 +30,7 @@ Orchestrates context-aware documentation generation/update for changed modules u
|
|||||||
6. **Related Mode**: Generate/update only changed modules and their parent contexts
|
6. **Related Mode**: Generate/update only changed modules and their parent contexts
|
||||||
7. **Single Strategy**: Always use `single` strategy (incremental update)
|
7. **Single Strategy**: Always use `single` strategy (incremental update)
|
||||||
|
|
||||||
## Tool Fallback Hierarchy
|
### Tool Fallback Hierarchy
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
--tool gemini → [gemini, qwen, codex] // default
|
--tool gemini → [gemini, qwen, codex] // default
|
||||||
@@ -36,15 +38,7 @@ Orchestrates context-aware documentation generation/update for changed modules u
|
|||||||
--tool codex → [codex, gemini, qwen]
|
--tool codex → [codex, gemini, qwen]
|
||||||
```
|
```
|
||||||
|
|
||||||
**Trigger**: Non-zero exit code from generation script
|
### Step 5.1: Change Detection & Analysis
|
||||||
|
|
||||||
| Tool | Best For | Fallback To |
|
|
||||||
|--------|--------------------------------|----------------|
|
|
||||||
| gemini | Documentation, patterns | qwen → codex |
|
|
||||||
| qwen | Architecture, system design | gemini → codex |
|
|
||||||
| codex | Implementation, code quality | gemini → qwen |
|
|
||||||
|
|
||||||
## Phase 1: Change Detection & Analysis
|
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Get project metadata
|
// Get project metadata
|
||||||
@@ -63,7 +57,7 @@ Bash({command: "git add -A 2>/dev/null || true", run_in_background: false});
|
|||||||
|
|
||||||
**Fallback**: If no changes detected, use recent modules (first 10 by depth).
|
**Fallback**: If no changes detected, use recent modules (first 10 by depth).
|
||||||
|
|
||||||
## Phase 2: Plan Presentation
|
### Step 5.2: Plan Presentation
|
||||||
|
|
||||||
**Present filtered plan**:
|
**Present filtered plan**:
|
||||||
```
|
```
|
||||||
@@ -95,8 +89,6 @@ Related Documentation Generation Plan:
|
|||||||
- Depth 1 (1 module): 1 agent [1]
|
- Depth 1 (1 module): 1 agent [1]
|
||||||
- Depth 0 (1 module): 1 agent [1]
|
- Depth 0 (1 module): 1 agent [1]
|
||||||
|
|
||||||
Estimated time: ~5-10 minutes
|
|
||||||
|
|
||||||
Confirm execution? (y/n)
|
Confirm execution? (y/n)
|
||||||
```
|
```
|
||||||
|
|
||||||
@@ -106,7 +98,7 @@ Related Documentation Generation Plan:
|
|||||||
- <15 modules: Direct execution
|
- <15 modules: Direct execution
|
||||||
- ≥15 modules: Agent batch execution
|
- ≥15 modules: Agent batch execution
|
||||||
|
|
||||||
## Phase 3A: Direct Execution (<15 modules)
|
### Step 5.3A: Direct Execution (<15 modules)
|
||||||
|
|
||||||
**Strategy**: Parallel execution within depth (max 4 concurrent), no agent overhead.
|
**Strategy**: Parallel execution within depth (max 4 concurrent), no agent overhead.
|
||||||
|
|
||||||
@@ -140,9 +132,9 @@ for (let depth of sorted_depths.reverse()) { // N → 0
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
## Phase 3B: Agent Batch Execution (≥15 modules)
|
### Step 5.3B: Agent Batch Execution (≥15 modules)
|
||||||
|
|
||||||
### Batching Strategy
|
#### Batching Strategy
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Batch modules into groups of 4
|
// Batch modules into groups of 4
|
||||||
@@ -156,7 +148,7 @@ function batch_modules(modules, batch_size = 4) {
|
|||||||
// Examples: 10→[4,4,2] | 8→[4,4] | 3→[3]
|
// Examples: 10→[4,4,2] | 8→[4,4] | 3→[3]
|
||||||
```
|
```
|
||||||
|
|
||||||
### Coordinator Orchestration
|
#### Coordinator Orchestration
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
let modules_by_depth = group_by_depth(changed_modules);
|
let modules_by_depth = group_by_depth(changed_modules);
|
||||||
@@ -181,7 +173,7 @@ for (let depth of sorted_depths.reverse()) { // N → 0
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Batch Worker Prompt Template
|
#### Batch Worker Prompt Template
|
||||||
|
|
||||||
```
|
```
|
||||||
PURPOSE: Generate/update documentation for assigned modules with tool fallback (related mode)
|
PURPOSE: Generate/update documentation for assigned modules with tool fallback (related mode)
|
||||||
@@ -239,7 +231,7 @@ Report final summary with:
|
|||||||
- Tool usage: {{tool_1}}:X, {{tool_2}}:Y, {{tool_3}}:Z
|
- Tool usage: {{tool_1}}:X, {{tool_2}}:Y, {{tool_3}}:Z
|
||||||
```
|
```
|
||||||
|
|
||||||
## Phase 4: Verification
|
### Step 5.4: Verification
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
// Check documentation files created/updated
|
// Check documentation files created/updated
|
||||||
@@ -270,15 +262,23 @@ Documentation Generation Summary:
|
|||||||
.workflow/docs/myproject/README.md (updated)
|
.workflow/docs/myproject/README.md (updated)
|
||||||
```
|
```
|
||||||
|
|
||||||
## Execution Summary
|
## Output Structure
|
||||||
|
|
||||||
**Module Count Threshold**:
|
```
|
||||||
- **<15 modules**: Coordinator executes Phase 3A (Direct Execution)
|
.workflow/docs/{project_name}/
|
||||||
- **≥15 modules**: Coordinator executes Phase 3B (Agent Batch Execution)
|
├── src/ # Mirrors source structure
|
||||||
|
│ ├── modules/
|
||||||
**Agent Hierarchy** (for ≥15 modules):
|
│ │ ├── README.md
|
||||||
- **Coordinator**: Handles batch division, spawns worker agents per depth
|
│ │ ├── auth/
|
||||||
- **Worker Agents**: Each processes 4 modules with tool fallback (related mode)
|
│ │ │ ├── API.md # Updated based on code changes
|
||||||
|
│ │ │ └── README.md # Updated based on code changes
|
||||||
|
│ │ └── api/
|
||||||
|
│ │ ├── API.md
|
||||||
|
│ │ └── README.md
|
||||||
|
│ └── utils/
|
||||||
|
│ └── README.md
|
||||||
|
└── README.md
|
||||||
|
```
|
||||||
|
|
||||||
## Error Handling
|
## Error Handling
|
||||||
|
|
||||||
@@ -298,80 +298,6 @@ Documentation Generation Summary:
|
|||||||
- Script timeout
|
- Script timeout
|
||||||
- Unexpected output
|
- Unexpected output
|
||||||
|
|
||||||
## Output Structure
|
|
||||||
|
|
||||||
```
|
|
||||||
.workflow/docs/{project_name}/
|
|
||||||
├── src/ # Mirrors source structure
|
|
||||||
│ ├── modules/
|
|
||||||
│ │ ├── README.md
|
|
||||||
│ │ ├── auth/
|
|
||||||
│ │ │ ├── API.md # Updated based on code changes
|
|
||||||
│ │ │ └── README.md # Updated based on code changes
|
|
||||||
│ │ └── api/
|
|
||||||
│ │ ├── API.md
|
|
||||||
│ │ └── README.md
|
|
||||||
│ └── utils/
|
|
||||||
│ └── README.md
|
|
||||||
└── README.md
|
|
||||||
```
|
|
||||||
|
|
||||||
## Usage Examples
|
|
||||||
|
|
||||||
```bash
|
|
||||||
# Daily development documentation update
|
|
||||||
/memory:docs-related-cli
|
|
||||||
|
|
||||||
# After feature work with specific tool
|
|
||||||
/memory:docs-related-cli --tool qwen
|
|
||||||
|
|
||||||
# Code quality documentation review after implementation
|
|
||||||
/memory:docs-related-cli --tool codex
|
|
||||||
```
|
|
||||||
|
|
||||||
## Key Advantages
|
|
||||||
|
|
||||||
**Efficiency**: 30 modules → 8 agents (73% reduction)
|
|
||||||
**Resilience**: 3-tier fallback per module
|
|
||||||
**Performance**: Parallel batches, no concurrency limits
|
|
||||||
**Context-aware**: Updates based on actual git changes
|
|
||||||
**Fast**: Only affected modules, not entire project
|
|
||||||
**Incremental**: Single strategy for focused updates
|
|
||||||
|
|
||||||
## Coordinator Checklist
|
|
||||||
|
|
||||||
- Parse `--tool` (default: gemini)
|
|
||||||
- Get project metadata (name, root)
|
|
||||||
- Detect changed modules via detect_changed_modules.sh
|
|
||||||
- **Smart filter modules** (auto-detect tech stack, skip tests/build/config/vendor)
|
|
||||||
- Cache git changes
|
|
||||||
- Apply fallback if no changes (recent 10 modules)
|
|
||||||
- Construct tool fallback order
|
|
||||||
- **Present filtered plan** with skip reasons and change types
|
|
||||||
- **Wait for y/n confirmation**
|
|
||||||
- Determine execution mode:
|
|
||||||
- **<15 modules**: Direct execution (Phase 3A)
|
|
||||||
- For each depth (N→0): Sequential module updates with tool fallback
|
|
||||||
- **≥15 modules**: Agent batch execution (Phase 3B)
|
|
||||||
- For each depth (N→0): Batch modules (4 per batch), spawn batch workers in parallel
|
|
||||||
- Wait for depth/batch completion
|
|
||||||
- Aggregate results
|
|
||||||
- Verification check (documentation files created/updated)
|
|
||||||
- Display summary + recent changes
|
|
||||||
|
|
||||||
## Comparison with Full Documentation Generation
|
|
||||||
|
|
||||||
| Aspect | Related Generation | Full Generation |
|
|
||||||
|--------|-------------------|-----------------|
|
|
||||||
| **Scope** | Changed modules only | All project modules |
|
|
||||||
| **Speed** | Fast (minutes) | Slower (10-30 min) |
|
|
||||||
| **Use case** | Daily development | Initial setup, major refactoring |
|
|
||||||
| **Strategy** | `single` (all) | `full` (L3) + `single` (L1-2) |
|
|
||||||
| **Trigger** | After commits | After setup or major changes |
|
|
||||||
| **Batching** | 4 modules/agent | 4 modules/agent |
|
|
||||||
| **Fallback** | gemini→qwen→codex | gemini→qwen→codex |
|
|
||||||
| **Complexity threshold** | ≤15 modules | ≤20 modules |
|
|
||||||
|
|
||||||
## Template Reference
|
## Template Reference
|
||||||
|
|
||||||
Templates used from `~/.ccw/workflows/cli-templates/prompts/documentation/`:
|
Templates used from `~/.ccw/workflows/cli-templates/prompts/documentation/`:
|
||||||
@@ -379,8 +305,11 @@ Templates used from `~/.ccw/workflows/cli-templates/prompts/documentation/`:
|
|||||||
- `module-readme.txt`: Module purpose, usage, dependencies
|
- `module-readme.txt`: Module purpose, usage, dependencies
|
||||||
- `folder-navigation.txt`: Navigation README for folders
|
- `folder-navigation.txt`: Navigation README for folders
|
||||||
|
|
||||||
## Related Commands
|
## Output
|
||||||
|
|
||||||
- `/memory:docs-full-cli` - Full project documentation generation
|
- **Directory**: `.workflow/docs/{project_name}/` — Updated documentation for changed modules
|
||||||
- `/memory:docs` - Agent-based documentation planning workflow
|
- **Report**: Summary with success/failure counts, tool usage, and file change list
|
||||||
- `/memory:update-related` - Update CLAUDE.md for changed modules
|
|
||||||
|
## Next Phase
|
||||||
|
|
||||||
|
Return to [manage.md](../manage.md) router.
|
||||||
5
ccw/.tmp-ccw-path-resolver-home/config/recent-paths.json
Normal file
5
ccw/.tmp-ccw-path-resolver-home/config/recent-paths.json
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
{
|
||||||
|
"paths": [
|
||||||
|
"C:/project/demo"
|
||||||
|
]
|
||||||
|
}
|
||||||
@@ -11,9 +11,7 @@ import {
|
|||||||
Play,
|
Play,
|
||||||
CheckCircle,
|
CheckCircle,
|
||||||
XCircle,
|
XCircle,
|
||||||
Clock,
|
|
||||||
Terminal,
|
Terminal,
|
||||||
Loader2,
|
|
||||||
} from 'lucide-react';
|
} from 'lucide-react';
|
||||||
import { Card } from '@/components/ui/Card';
|
import { Card } from '@/components/ui/Card';
|
||||||
import { Badge } from '@/components/ui/Badge';
|
import { Badge } from '@/components/ui/Badge';
|
||||||
@@ -23,50 +21,9 @@ import {
|
|||||||
selectExecutionStats,
|
selectExecutionStats,
|
||||||
useTerminalPanelStore,
|
useTerminalPanelStore,
|
||||||
} from '@/stores';
|
} from '@/stores';
|
||||||
import type { QueueExecution, QueueExecutionStatus } from '@/stores/queueExecutionStore';
|
import type { QueueExecution } from '@/stores/queueExecutionStore';
|
||||||
import { cn } from '@/lib/utils';
|
import { cn } from '@/lib/utils';
|
||||||
|
import { statusIcon, statusBadgeVariant, formatRelativeTime } from '@/lib/execution-display-utils';
|
||||||
// ========== Helpers ==========
|
|
||||||
|
|
||||||
function statusBadgeVariant(status: QueueExecutionStatus): 'info' | 'success' | 'destructive' | 'secondary' {
|
|
||||||
switch (status) {
|
|
||||||
case 'running':
|
|
||||||
return 'info';
|
|
||||||
case 'completed':
|
|
||||||
return 'success';
|
|
||||||
case 'failed':
|
|
||||||
return 'destructive';
|
|
||||||
case 'pending':
|
|
||||||
default:
|
|
||||||
return 'secondary';
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function statusIcon(status: QueueExecutionStatus) {
|
|
||||||
switch (status) {
|
|
||||||
case 'running':
|
|
||||||
return <Loader2 className="w-3.5 h-3.5 animate-spin" />;
|
|
||||||
case 'completed':
|
|
||||||
return <CheckCircle className="w-3.5 h-3.5" />;
|
|
||||||
case 'failed':
|
|
||||||
return <XCircle className="w-3.5 h-3.5" />;
|
|
||||||
case 'pending':
|
|
||||||
default:
|
|
||||||
return <Clock className="w-3.5 h-3.5" />;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function formatRelativeTime(isoString: string): string {
|
|
||||||
const diff = Date.now() - new Date(isoString).getTime();
|
|
||||||
const seconds = Math.floor(diff / 1000);
|
|
||||||
if (seconds < 60) return `${seconds}s ago`;
|
|
||||||
const minutes = Math.floor(seconds / 60);
|
|
||||||
if (minutes < 60) return `${minutes}m ago`;
|
|
||||||
const hours = Math.floor(minutes / 60);
|
|
||||||
if (hours < 24) return `${hours}h ago`;
|
|
||||||
const days = Math.floor(hours / 24);
|
|
||||||
return `${days}d ago`;
|
|
||||||
}
|
|
||||||
|
|
||||||
// ========== Empty State ==========
|
// ========== Empty State ==========
|
||||||
|
|
||||||
|
|||||||
@@ -38,6 +38,7 @@ import {
|
|||||||
} from '@/components/shared/CliExecutionSettings';
|
} from '@/components/shared/CliExecutionSettings';
|
||||||
import { buildQueueItemContext } from '@/lib/queue-prompt';
|
import { buildQueueItemContext } from '@/lib/queue-prompt';
|
||||||
import { useQueueExecutionStore, type QueueExecution } from '@/stores/queueExecutionStore';
|
import { useQueueExecutionStore, type QueueExecution } from '@/stores/queueExecutionStore';
|
||||||
|
import type { Flow } from '@/types/flow';
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------
|
// ---------------------------------------------------------------------------
|
||||||
// Types
|
// Types
|
||||||
@@ -70,7 +71,7 @@ export function QueueItemExecutor({ item, className }: QueueItemExecutorProps) {
|
|||||||
// Resolve the parent issue for context building
|
// Resolve the parent issue for context building
|
||||||
const { issues } = useIssues();
|
const { issues } = useIssues();
|
||||||
const issue = useMemo(
|
const issue = useMemo(
|
||||||
() => issues.find((i) => i.id === item.issue_id) as any,
|
() => issues.find((i) => i.id === item.issue_id),
|
||||||
[issues, item.issue_id]
|
[issues, item.issue_id]
|
||||||
);
|
);
|
||||||
|
|
||||||
@@ -203,13 +204,13 @@ export function QueueItemExecutor({ item, className }: QueueItemExecutorProps) {
|
|||||||
throw new Error('Failed to create flow');
|
throw new Error('Failed to create flow');
|
||||||
}
|
}
|
||||||
|
|
||||||
// Hydrate Orchestrator stores
|
// Hydrate Orchestrator stores -- convert OrchestratorFlowDto to Flow
|
||||||
const flowDto = created.data as any;
|
const flowDto = created.data;
|
||||||
const parsedVersion = parseInt(String(flowDto.version ?? '1'), 10);
|
const parsedVersion = parseInt(String(flowDto.version ?? '1'), 10);
|
||||||
const flowForStore = {
|
const flowForStore: Flow = {
|
||||||
...flowDto,
|
...flowDto,
|
||||||
version: Number.isFinite(parsedVersion) ? parsedVersion : 1,
|
version: Number.isFinite(parsedVersion) ? parsedVersion : 1,
|
||||||
} as any;
|
} as Flow;
|
||||||
useFlowStore.getState().setCurrentFlow(flowForStore);
|
useFlowStore.getState().setCurrentFlow(flowForStore);
|
||||||
|
|
||||||
// Execute the flow
|
// Execute the flow
|
||||||
|
|||||||
@@ -59,7 +59,7 @@ export interface CcwConfig {
|
|||||||
enabledTools: string[];
|
enabledTools: string[];
|
||||||
projectRoot?: string;
|
projectRoot?: string;
|
||||||
allowedDirs?: string;
|
allowedDirs?: string;
|
||||||
disableSandbox?: boolean;
|
enableSandbox?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -75,7 +75,7 @@ export interface CcwToolsMcpCardProps {
|
|||||||
/** Comma-separated list of allowed directories */
|
/** Comma-separated list of allowed directories */
|
||||||
allowedDirs?: string;
|
allowedDirs?: string;
|
||||||
/** Whether sandbox is disabled */
|
/** Whether sandbox is disabled */
|
||||||
disableSandbox?: boolean;
|
enableSandbox?: boolean;
|
||||||
/** Callback when a tool is toggled */
|
/** Callback when a tool is toggled */
|
||||||
onToggleTool: (tool: string, enabled: boolean) => void;
|
onToggleTool: (tool: string, enabled: boolean) => void;
|
||||||
/** Callback when configuration is updated */
|
/** Callback when configuration is updated */
|
||||||
@@ -110,7 +110,7 @@ export function CcwToolsMcpCard({
|
|||||||
enabledTools,
|
enabledTools,
|
||||||
projectRoot,
|
projectRoot,
|
||||||
allowedDirs,
|
allowedDirs,
|
||||||
disableSandbox,
|
enableSandbox,
|
||||||
onToggleTool,
|
onToggleTool,
|
||||||
onUpdateConfig,
|
onUpdateConfig,
|
||||||
onInstall,
|
onInstall,
|
||||||
@@ -123,7 +123,7 @@ export function CcwToolsMcpCard({
|
|||||||
// Local state for config inputs
|
// Local state for config inputs
|
||||||
const [projectRootInput, setProjectRootInput] = useState(projectRoot || '');
|
const [projectRootInput, setProjectRootInput] = useState(projectRoot || '');
|
||||||
const [allowedDirsInput, setAllowedDirsInput] = useState(allowedDirs || '');
|
const [allowedDirsInput, setAllowedDirsInput] = useState(allowedDirs || '');
|
||||||
const [disableSandboxInput, setDisableSandboxInput] = useState(disableSandbox || false);
|
const [enableSandboxInput, setEnableSandboxInput] = useState(enableSandbox || false);
|
||||||
const [isExpanded, setIsExpanded] = useState(false);
|
const [isExpanded, setIsExpanded] = useState(false);
|
||||||
const [installScope, setInstallScope] = useState<'global' | 'project'>('global');
|
const [installScope, setInstallScope] = useState<'global' | 'project'>('global');
|
||||||
|
|
||||||
@@ -193,7 +193,7 @@ export function CcwToolsMcpCard({
|
|||||||
updateConfigMutation.mutate({
|
updateConfigMutation.mutate({
|
||||||
projectRoot: projectRootInput || undefined,
|
projectRoot: projectRootInput || undefined,
|
||||||
allowedDirs: allowedDirsInput || undefined,
|
allowedDirs: allowedDirsInput || undefined,
|
||||||
disableSandbox: disableSandboxInput,
|
enableSandbox: enableSandboxInput,
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -387,22 +387,22 @@ export function CcwToolsMcpCard({
|
|||||||
</p>
|
</p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{/* Disable Sandbox */}
|
{/* Enable Sandbox */}
|
||||||
<div className="flex items-center gap-2">
|
<div className="flex items-center gap-2">
|
||||||
<input
|
<input
|
||||||
type="checkbox"
|
type="checkbox"
|
||||||
id="ccw-disable-sandbox"
|
id="ccw-enable-sandbox"
|
||||||
checked={disableSandboxInput}
|
checked={enableSandboxInput}
|
||||||
onChange={(e) => setDisableSandboxInput(e.target.checked)}
|
onChange={(e) => setEnableSandboxInput(e.target.checked)}
|
||||||
disabled={!isInstalled}
|
disabled={!isInstalled}
|
||||||
className="w-4 h-4"
|
className="w-4 h-4"
|
||||||
/>
|
/>
|
||||||
<label
|
<label
|
||||||
htmlFor="ccw-disable-sandbox"
|
htmlFor="ccw-enable-sandbox"
|
||||||
className="text-sm text-foreground flex items-center gap-1 cursor-pointer"
|
className="text-sm text-foreground flex items-center gap-1 cursor-pointer"
|
||||||
>
|
>
|
||||||
<Shield className="w-4 h-4" />
|
<Shield className="w-4 h-4" />
|
||||||
{formatMessage({ id: 'mcp.ccw.paths.disableSandbox' })}
|
{formatMessage({ id: 'mcp.ccw.paths.enableSandbox' })}
|
||||||
</label>
|
</label>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,133 @@
|
|||||||
|
// ========================================
|
||||||
|
// QueueExecutionListView Component
|
||||||
|
// ========================================
|
||||||
|
// Compact execution list for TerminalPanel queue view.
|
||||||
|
// Subscribes to queueExecutionStore and renders execution entries
|
||||||
|
// with status badges, tool/mode labels, and relative timestamps.
|
||||||
|
// Click navigates to terminal view (session) or orchestrator page.
|
||||||
|
|
||||||
|
import { useMemo } from 'react';
|
||||||
|
import { useIntl } from 'react-intl';
|
||||||
|
import { useNavigate } from 'react-router-dom';
|
||||||
|
import { ClipboardList } from 'lucide-react';
|
||||||
|
import { Badge } from '@/components/ui/Badge';
|
||||||
|
import { cn } from '@/lib/utils';
|
||||||
|
import { useQueueExecutionStore } from '@/stores/queueExecutionStore';
|
||||||
|
import { useTerminalPanelStore } from '@/stores/terminalPanelStore';
|
||||||
|
import type { QueueExecution } from '@/stores/queueExecutionStore';
|
||||||
|
import { ROUTES } from '@/router';
|
||||||
|
import { statusIcon, statusBadgeVariant, formatRelativeTime } from '@/lib/execution-display-utils';
|
||||||
|
|
||||||
|
// ========== Execution Item ==========
|
||||||
|
|
||||||
|
function QueueExecutionItem({
|
||||||
|
execution,
|
||||||
|
onClick,
|
||||||
|
}: {
|
||||||
|
execution: QueueExecution;
|
||||||
|
onClick: () => void;
|
||||||
|
}) {
|
||||||
|
const { formatMessage } = useIntl();
|
||||||
|
|
||||||
|
const typeLabel = execution.type === 'session'
|
||||||
|
? formatMessage({ id: 'home.terminalPanel.queueView.session' })
|
||||||
|
: formatMessage({ id: 'home.terminalPanel.queueView.orchestrator' });
|
||||||
|
|
||||||
|
return (
|
||||||
|
<button
|
||||||
|
type="button"
|
||||||
|
className={cn(
|
||||||
|
'w-full text-left px-3 py-2.5 rounded-md transition-colors',
|
||||||
|
'hover:bg-muted/60 focus:outline-none focus:ring-1 focus:ring-primary/30'
|
||||||
|
)}
|
||||||
|
onClick={onClick}
|
||||||
|
>
|
||||||
|
<div className="flex items-center justify-between gap-2">
|
||||||
|
<div className="flex items-center gap-2 min-w-0">
|
||||||
|
{statusIcon(execution.status)}
|
||||||
|
<span className="text-sm font-medium font-mono text-foreground truncate">
|
||||||
|
{execution.queueItemId}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
<Badge variant={statusBadgeVariant(execution.status)} className="shrink-0 text-[10px] px-1.5 py-0">
|
||||||
|
{formatMessage({ id: `home.terminalPanel.status.${execution.status}` })}
|
||||||
|
</Badge>
|
||||||
|
</div>
|
||||||
|
<div className="mt-1 flex items-center gap-2 text-xs text-muted-foreground">
|
||||||
|
<span className="font-mono">{execution.tool}</span>
|
||||||
|
<span className="text-border">|</span>
|
||||||
|
<span>{execution.mode}</span>
|
||||||
|
<span className="text-border">|</span>
|
||||||
|
<span>{typeLabel}</span>
|
||||||
|
<span className="ml-auto shrink-0">{formatRelativeTime(execution.startedAt)}</span>
|
||||||
|
</div>
|
||||||
|
</button>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// ========== Empty State ==========
|
||||||
|
|
||||||
|
function QueueEmptyState() {
|
||||||
|
const { formatMessage } = useIntl();
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="flex-1 flex items-center justify-center text-muted-foreground">
|
||||||
|
<div className="text-center">
|
||||||
|
<ClipboardList className="h-12 w-12 mx-auto mb-4 opacity-50" />
|
||||||
|
<p className="text-sm">{formatMessage({ id: 'home.terminalPanel.queueView.emptyTitle' })}</p>
|
||||||
|
<p className="text-xs mt-1">{formatMessage({ id: 'home.terminalPanel.queueView.emptyDesc' })}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
// ========== Main Component ==========
|
||||||
|
|
||||||
|
export function QueueExecutionListView() {
|
||||||
|
const navigate = useNavigate();
|
||||||
|
const executions = useQueueExecutionStore((s) => s.executions);
|
||||||
|
const setPanelView = useTerminalPanelStore((s) => s.setPanelView);
|
||||||
|
const openTerminal = useTerminalPanelStore((s) => s.openTerminal);
|
||||||
|
|
||||||
|
// Sort: running first, then pending, then failed, then completed; within same status by startedAt desc
|
||||||
|
const sortedExecutions = useMemo(() => {
|
||||||
|
const all = Object.values(executions);
|
||||||
|
const statusOrder: Record<string, number> = {
|
||||||
|
running: 0,
|
||||||
|
pending: 1,
|
||||||
|
failed: 2,
|
||||||
|
completed: 3,
|
||||||
|
};
|
||||||
|
return all.sort((a, b) => {
|
||||||
|
const sa = statusOrder[a.status] ?? 4;
|
||||||
|
const sb = statusOrder[b.status] ?? 4;
|
||||||
|
if (sa !== sb) return sa - sb;
|
||||||
|
return new Date(b.startedAt).getTime() - new Date(a.startedAt).getTime();
|
||||||
|
});
|
||||||
|
}, [executions]);
|
||||||
|
|
||||||
|
const handleClick = (exec: QueueExecution) => {
|
||||||
|
if (exec.type === 'session' && exec.sessionKey) {
|
||||||
|
setPanelView('terminal');
|
||||||
|
openTerminal(exec.sessionKey);
|
||||||
|
} else {
|
||||||
|
navigate(ROUTES.ORCHESTRATOR);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (sortedExecutions.length === 0) {
|
||||||
|
return <QueueEmptyState />;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className="flex-1 flex flex-col min-h-0 overflow-y-auto p-2 space-y-0.5">
|
||||||
|
{sortedExecutions.map((exec) => (
|
||||||
|
<QueueExecutionItem
|
||||||
|
key={exec.id}
|
||||||
|
execution={exec}
|
||||||
|
onClick={() => handleClick(exec)}
|
||||||
|
/>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -201,8 +201,9 @@ export function TerminalMainArea({ onClose }: TerminalMainAreaProps) {
|
|||||||
category: 'user',
|
category: 'user',
|
||||||
}, projectPath || undefined);
|
}, projectPath || undefined);
|
||||||
setPrompt('');
|
setPrompt('');
|
||||||
} catch {
|
} catch (err) {
|
||||||
// Error shown in terminal output
|
// Error shown in terminal output; log for DevTools debugging
|
||||||
|
console.error('[TerminalMainArea] executeInCliSession failed:', err);
|
||||||
} finally {
|
} finally {
|
||||||
setIsExecuting(false);
|
setIsExecuting(false);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -22,6 +22,8 @@ export interface UseCliSessionCoreOptions {
|
|||||||
autoSelectLast?: boolean;
|
autoSelectLast?: boolean;
|
||||||
/** Default resumeKey used when creating sessions via ensureSession/handleCreateSession. */
|
/** Default resumeKey used when creating sessions via ensureSession/handleCreateSession. */
|
||||||
resumeKey?: string;
|
resumeKey?: string;
|
||||||
|
/** Shell to use when creating new sessions. Defaults to 'bash'. */
|
||||||
|
preferredShell?: string;
|
||||||
/** Additional createCliSession fields (cols, rows, tool, model). */
|
/** Additional createCliSession fields (cols, rows, tool, model). */
|
||||||
createSessionDefaults?: {
|
createSessionDefaults?: {
|
||||||
cols?: number;
|
cols?: number;
|
||||||
@@ -60,6 +62,7 @@ export function useCliSessionCore(options: UseCliSessionCoreOptions = {}): UseCl
|
|||||||
const {
|
const {
|
||||||
autoSelectLast = true,
|
autoSelectLast = true,
|
||||||
resumeKey,
|
resumeKey,
|
||||||
|
preferredShell = 'bash',
|
||||||
createSessionDefaults,
|
createSessionDefaults,
|
||||||
} = options;
|
} = options;
|
||||||
|
|
||||||
@@ -92,7 +95,7 @@ export function useCliSessionCore(options: UseCliSessionCoreOptions = {}): UseCl
|
|||||||
setError(null);
|
setError(null);
|
||||||
try {
|
try {
|
||||||
const r = await fetchCliSessions(projectPath || undefined);
|
const r = await fetchCliSessions(projectPath || undefined);
|
||||||
setSessions(r.sessions as unknown as CliSession[]);
|
setSessions(r.sessions);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
setError(e instanceof Error ? e.message : String(e));
|
setError(e instanceof Error ? e.message : String(e));
|
||||||
} finally {
|
} finally {
|
||||||
@@ -120,16 +123,16 @@ export function useCliSessionCore(options: UseCliSessionCoreOptions = {}): UseCl
|
|||||||
const created = await createCliSession(
|
const created = await createCliSession(
|
||||||
{
|
{
|
||||||
workingDir: projectPath,
|
workingDir: projectPath,
|
||||||
preferredShell: 'bash',
|
preferredShell,
|
||||||
resumeKey,
|
resumeKey,
|
||||||
...createSessionDefaults,
|
...createSessionDefaults,
|
||||||
},
|
},
|
||||||
projectPath
|
projectPath
|
||||||
);
|
);
|
||||||
upsertSession(created.session as unknown as CliSession);
|
upsertSession(created.session);
|
||||||
setSelectedSessionKey(created.session.sessionKey);
|
setSelectedSessionKey(created.session.sessionKey);
|
||||||
return created.session.sessionKey;
|
return created.session.sessionKey;
|
||||||
}, [selectedSessionKey, projectPath, resumeKey, createSessionDefaults, upsertSession]);
|
}, [selectedSessionKey, projectPath, resumeKey, preferredShell, createSessionDefaults, upsertSession]);
|
||||||
|
|
||||||
// ------- handleCreateSession -------
|
// ------- handleCreateSession -------
|
||||||
const handleCreateSession = useCallback(async () => {
|
const handleCreateSession = useCallback(async () => {
|
||||||
@@ -139,21 +142,21 @@ export function useCliSessionCore(options: UseCliSessionCoreOptions = {}): UseCl
|
|||||||
const created = await createCliSession(
|
const created = await createCliSession(
|
||||||
{
|
{
|
||||||
workingDir: projectPath,
|
workingDir: projectPath,
|
||||||
preferredShell: 'bash',
|
preferredShell,
|
||||||
resumeKey,
|
resumeKey,
|
||||||
...createSessionDefaults,
|
...createSessionDefaults,
|
||||||
},
|
},
|
||||||
projectPath
|
projectPath
|
||||||
);
|
);
|
||||||
upsertSession(created.session as unknown as CliSession);
|
upsertSession(created.session);
|
||||||
setSelectedSessionKey(created.session.sessionKey);
|
setSelectedSessionKey(created.session.sessionKey);
|
||||||
// Refresh full list so store stays consistent
|
// Refresh full list so store stays consistent
|
||||||
const r = await fetchCliSessions(projectPath || undefined);
|
const r = await fetchCliSessions(projectPath || undefined);
|
||||||
setSessions(r.sessions as unknown as CliSession[]);
|
setSessions(r.sessions);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
setError(e instanceof Error ? e.message : String(e));
|
setError(e instanceof Error ? e.message : String(e));
|
||||||
}
|
}
|
||||||
}, [projectPath, resumeKey, createSessionDefaults, upsertSession, setSessions]);
|
}, [projectPath, resumeKey, preferredShell, createSessionDefaults, upsertSession, setSessions]);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
sessions,
|
sessions,
|
||||||
|
|||||||
65
ccw/frontend/src/lib/execution-display-utils.ts
Normal file
65
ccw/frontend/src/lib/execution-display-utils.ts
Normal file
@@ -0,0 +1,65 @@
|
|||||||
|
// ========================================
|
||||||
|
// Execution Display Utilities
|
||||||
|
// ========================================
|
||||||
|
// Shared helpers for rendering queue execution status across
|
||||||
|
// ExecutionPanel and QueueExecutionListView components.
|
||||||
|
|
||||||
|
import type { ReactElement } from 'react';
|
||||||
|
import { createElement } from 'react';
|
||||||
|
import {
|
||||||
|
Loader2,
|
||||||
|
CheckCircle,
|
||||||
|
XCircle,
|
||||||
|
Clock,
|
||||||
|
} from 'lucide-react';
|
||||||
|
import type { QueueExecutionStatus } from '@/stores/queueExecutionStore';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Map execution status to Badge variant.
|
||||||
|
*/
|
||||||
|
export function statusBadgeVariant(status: QueueExecutionStatus): 'info' | 'success' | 'destructive' | 'secondary' {
|
||||||
|
switch (status) {
|
||||||
|
case 'running':
|
||||||
|
return 'info';
|
||||||
|
case 'completed':
|
||||||
|
return 'success';
|
||||||
|
case 'failed':
|
||||||
|
return 'destructive';
|
||||||
|
case 'pending':
|
||||||
|
default:
|
||||||
|
return 'secondary';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Map execution status to a small icon element.
|
||||||
|
*/
|
||||||
|
export function statusIcon(status: QueueExecutionStatus): ReactElement {
|
||||||
|
const base = 'w-3.5 h-3.5';
|
||||||
|
switch (status) {
|
||||||
|
case 'running':
|
||||||
|
return createElement(Loader2, { className: `${base} animate-spin text-info` });
|
||||||
|
case 'completed':
|
||||||
|
return createElement(CheckCircle, { className: `${base} text-success` });
|
||||||
|
case 'failed':
|
||||||
|
return createElement(XCircle, { className: `${base} text-destructive` });
|
||||||
|
case 'pending':
|
||||||
|
default:
|
||||||
|
return createElement(Clock, { className: `${base} text-muted-foreground` });
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Format an ISO date string as a human-readable relative time.
|
||||||
|
*/
|
||||||
|
export function formatRelativeTime(isoString: string): string {
|
||||||
|
const diff = Date.now() - new Date(isoString).getTime();
|
||||||
|
const seconds = Math.floor(diff / 1000);
|
||||||
|
if (seconds < 60) return `${seconds}s ago`;
|
||||||
|
const minutes = Math.floor(seconds / 60);
|
||||||
|
if (minutes < 60) return `${minutes}m ago`;
|
||||||
|
const hours = Math.floor(minutes / 60);
|
||||||
|
if (hours < 24) return `${hours}h ago`;
|
||||||
|
const days = Math.floor(hours / 24);
|
||||||
|
return `${days}d ago`;
|
||||||
|
}
|
||||||
@@ -7,6 +7,34 @@
|
|||||||
|
|
||||||
import type { QueueItem } from '@/lib/api';
|
import type { QueueItem } from '@/lib/api';
|
||||||
|
|
||||||
|
// ---------------------------------------------------------------------------
|
||||||
|
// Minimal interfaces for the issue data consumed by buildQueueItemContext.
|
||||||
|
// The backend may return solution.tasks[] which is not part of the core
|
||||||
|
// IssueSolution interface, so we define a local superset here.
|
||||||
|
// ---------------------------------------------------------------------------
|
||||||
|
|
||||||
|
/** A lightweight task entry nested inside a solution from the backend. */
|
||||||
|
interface SolutionTask {
|
||||||
|
id: string;
|
||||||
|
title?: string;
|
||||||
|
description?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Solution shape as consumed by the prompt builder (superset of IssueSolution). */
|
||||||
|
interface PromptSolution {
|
||||||
|
id: string;
|
||||||
|
description?: string;
|
||||||
|
approach?: string;
|
||||||
|
tasks?: SolutionTask[];
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Minimal issue shape consumed by the prompt builder. */
|
||||||
|
export interface QueueItemIssue {
|
||||||
|
title?: string;
|
||||||
|
context?: string;
|
||||||
|
solutions?: PromptSolution[];
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Build a context string for executing a queue item.
|
* Build a context string for executing a queue item.
|
||||||
*
|
*
|
||||||
@@ -18,7 +46,7 @@ import type { QueueItem } from '@/lib/api';
|
|||||||
*/
|
*/
|
||||||
export function buildQueueItemContext(
|
export function buildQueueItemContext(
|
||||||
item: QueueItem,
|
item: QueueItem,
|
||||||
issue: any | undefined
|
issue: QueueItemIssue | undefined
|
||||||
): string {
|
): string {
|
||||||
const lines: string[] = [];
|
const lines: string[] = [];
|
||||||
|
|
||||||
@@ -38,7 +66,7 @@ export function buildQueueItemContext(
|
|||||||
}
|
}
|
||||||
|
|
||||||
const solution = Array.isArray(issue.solutions)
|
const solution = Array.isArray(issue.solutions)
|
||||||
? issue.solutions.find((s: any) => s?.id === item.solution_id)
|
? issue.solutions.find((s) => s?.id === item.solution_id)
|
||||||
: undefined;
|
: undefined;
|
||||||
|
|
||||||
if (solution) {
|
if (solution) {
|
||||||
@@ -54,7 +82,7 @@ export function buildQueueItemContext(
|
|||||||
// Include matched task from solution.tasks when available
|
// Include matched task from solution.tasks when available
|
||||||
const tasks = Array.isArray(solution.tasks) ? solution.tasks : [];
|
const tasks = Array.isArray(solution.tasks) ? solution.tasks : [];
|
||||||
const task = item.task_id
|
const task = item.task_id
|
||||||
? tasks.find((t: any) => t?.id === item.task_id)
|
? tasks.find((t) => t?.id === item.task_id)
|
||||||
: undefined;
|
: undefined;
|
||||||
if (task) {
|
if (task) {
|
||||||
lines.push('');
|
lines.push('');
|
||||||
|
|||||||
@@ -153,7 +153,7 @@
|
|||||||
"allowedDirs": "Allowed Directories",
|
"allowedDirs": "Allowed Directories",
|
||||||
"allowedDirsPlaceholder": "dir1,dir2,dir3",
|
"allowedDirsPlaceholder": "dir1,dir2,dir3",
|
||||||
"allowedDirsHint": "Comma-separated list of allowed directories",
|
"allowedDirsHint": "Comma-separated list of allowed directories",
|
||||||
"disableSandbox": "Disable Sandbox"
|
"enableSandbox": "Enable Sandbox (restrict to workspace files only)"
|
||||||
},
|
},
|
||||||
"actions": {
|
"actions": {
|
||||||
"enableAll": "Enable All",
|
"enableAll": "Enable All",
|
||||||
|
|||||||
@@ -153,7 +153,7 @@
|
|||||||
"allowedDirs": "允许的目录",
|
"allowedDirs": "允许的目录",
|
||||||
"allowedDirsPlaceholder": "目录1,目录2,目录3",
|
"allowedDirsPlaceholder": "目录1,目录2,目录3",
|
||||||
"allowedDirsHint": "逗号分隔的允许目录列表",
|
"allowedDirsHint": "逗号分隔的允许目录列表",
|
||||||
"disableSandbox": "禁用沙箱"
|
"enableSandbox": "启用沙箱(仅允许修改工作空间下的文件)"
|
||||||
},
|
},
|
||||||
"actions": {
|
"actions": {
|
||||||
"enableAll": "全部启用",
|
"enableAll": "全部启用",
|
||||||
|
|||||||
@@ -349,7 +349,7 @@ export function McpManagerPage() {
|
|||||||
enabledTools: [],
|
enabledTools: [],
|
||||||
projectRoot: undefined,
|
projectRoot: undefined,
|
||||||
allowedDirs: undefined,
|
allowedDirs: undefined,
|
||||||
disableSandbox: undefined,
|
enableSandbox: undefined,
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleToggleCcwTool = async (tool: string, enabled: boolean) => {
|
const handleToggleCcwTool = async (tool: string, enabled: boolean) => {
|
||||||
@@ -407,7 +407,7 @@ export function McpManagerPage() {
|
|||||||
enabledTools: [],
|
enabledTools: [],
|
||||||
projectRoot: undefined,
|
projectRoot: undefined,
|
||||||
allowedDirs: undefined,
|
allowedDirs: undefined,
|
||||||
disableSandbox: undefined,
|
enableSandbox: undefined,
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleToggleCcwToolCodex = async (tool: string, enabled: boolean) => {
|
const handleToggleCcwToolCodex = async (tool: string, enabled: boolean) => {
|
||||||
@@ -721,7 +721,7 @@ export function McpManagerPage() {
|
|||||||
enabledTools={ccwConfig.enabledTools}
|
enabledTools={ccwConfig.enabledTools}
|
||||||
projectRoot={ccwConfig.projectRoot}
|
projectRoot={ccwConfig.projectRoot}
|
||||||
allowedDirs={ccwConfig.allowedDirs}
|
allowedDirs={ccwConfig.allowedDirs}
|
||||||
disableSandbox={ccwConfig.disableSandbox}
|
enableSandbox={ccwConfig.enableSandbox}
|
||||||
onToggleTool={handleToggleCcwTool}
|
onToggleTool={handleToggleCcwTool}
|
||||||
onUpdateConfig={handleUpdateCcwConfig}
|
onUpdateConfig={handleUpdateCcwConfig}
|
||||||
onInstall={handleCcwInstall}
|
onInstall={handleCcwInstall}
|
||||||
@@ -734,7 +734,7 @@ export function McpManagerPage() {
|
|||||||
enabledTools={ccwCodexConfig.enabledTools}
|
enabledTools={ccwCodexConfig.enabledTools}
|
||||||
projectRoot={ccwCodexConfig.projectRoot}
|
projectRoot={ccwCodexConfig.projectRoot}
|
||||||
allowedDirs={ccwCodexConfig.allowedDirs}
|
allowedDirs={ccwCodexConfig.allowedDirs}
|
||||||
disableSandbox={ccwCodexConfig.disableSandbox}
|
enableSandbox={ccwCodexConfig.enableSandbox}
|
||||||
onToggleTool={handleToggleCcwToolCodex}
|
onToggleTool={handleToggleCcwToolCodex}
|
||||||
onUpdateConfig={handleUpdateCcwConfigCodex}
|
onUpdateConfig={handleUpdateCcwConfigCodex}
|
||||||
onInstall={handleCcwInstallCodex}
|
onInstall={handleCcwInstallCodex}
|
||||||
|
|||||||
@@ -1191,8 +1191,8 @@ export async function handleMcpRoutes(ctx: RouteContext): Promise<boolean> {
|
|||||||
return { error: 'projectPath is required', status: 400 };
|
return { error: 'projectPath is required', status: 400 };
|
||||||
}
|
}
|
||||||
|
|
||||||
// Check if sandbox should be disabled
|
// Check if sandbox should be enabled
|
||||||
const disableSandbox = body.disableSandbox === true;
|
const enableSandbox = body.enableSandbox === true;
|
||||||
|
|
||||||
// Parse enabled tools from request body
|
// Parse enabled tools from request body
|
||||||
const enabledTools = Array.isArray(body.enabledTools) && body.enabledTools.length > 0
|
const enabledTools = Array.isArray(body.enabledTools) && body.enabledTools.length > 0
|
||||||
@@ -1207,7 +1207,7 @@ export async function handleMcpRoutes(ctx: RouteContext): Promise<boolean> {
|
|||||||
args: isWin ? ["/c", "npx", "-y", "ccw-mcp"] : ["-y", "ccw-mcp"],
|
args: isWin ? ["/c", "npx", "-y", "ccw-mcp"] : ["-y", "ccw-mcp"],
|
||||||
env: {
|
env: {
|
||||||
CCW_ENABLED_TOOLS: enabledTools,
|
CCW_ENABLED_TOOLS: enabledTools,
|
||||||
...(disableSandbox && { CCW_DISABLE_SANDBOX: "1" })
|
...(enableSandbox && { CCW_ENABLE_SANDBOX: "1" })
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ import {
|
|||||||
} from '@modelcontextprotocol/sdk/types.js';
|
} from '@modelcontextprotocol/sdk/types.js';
|
||||||
import { getAllToolSchemas, executeTool, executeToolWithProgress } from '../tools/index.js';
|
import { getAllToolSchemas, executeTool, executeToolWithProgress } from '../tools/index.js';
|
||||||
import type { ToolSchema, ToolResult } from '../types/tool.js';
|
import type { ToolSchema, ToolResult } from '../types/tool.js';
|
||||||
import { getProjectRoot, getAllowedDirectories, isSandboxDisabled } from '../utils/path-validator.js';
|
import { getProjectRoot, getAllowedDirectories, isSandboxEnabled } from '../utils/path-validator.js';
|
||||||
|
|
||||||
const SERVER_NAME = 'ccw-tools';
|
const SERVER_NAME = 'ccw-tools';
|
||||||
const SERVER_VERSION = '6.2.0';
|
const SERVER_VERSION = '6.2.0';
|
||||||
@@ -178,13 +178,14 @@ async function main(): Promise<void> {
|
|||||||
// Log server start (to stderr to not interfere with stdio protocol)
|
// Log server start (to stderr to not interfere with stdio protocol)
|
||||||
const projectRoot = getProjectRoot();
|
const projectRoot = getProjectRoot();
|
||||||
const allowedDirs = getAllowedDirectories();
|
const allowedDirs = getAllowedDirectories();
|
||||||
const sandboxDisabled = isSandboxDisabled();
|
const sandboxEnabled = isSandboxEnabled();
|
||||||
console.error(`${SERVER_NAME} v${SERVER_VERSION} started`);
|
console.error(`${SERVER_NAME} v${SERVER_VERSION} started`);
|
||||||
console.error(`Project root: ${projectRoot}`);
|
console.error(`Project root: ${projectRoot}`);
|
||||||
if (sandboxDisabled) {
|
if (sandboxEnabled) {
|
||||||
console.error(`Sandbox: DISABLED (CCW_DISABLE_SANDBOX=true)`);
|
console.error(`Sandbox: ENABLED (CCW_ENABLE_SANDBOX=true)`);
|
||||||
} else {
|
|
||||||
console.error(`Allowed directories: ${allowedDirs.join(', ')}`);
|
console.error(`Allowed directories: ${allowedDirs.join(', ')}`);
|
||||||
|
} else {
|
||||||
|
console.error(`Sandbox: DISABLED (default)`);
|
||||||
}
|
}
|
||||||
if (!process.env[ENV_PROJECT_ROOT]) {
|
if (!process.env[ENV_PROJECT_ROOT]) {
|
||||||
console.error(`[Warning] ${ENV_PROJECT_ROOT} not set, using process.cwd()`);
|
console.error(`[Warning] ${ENV_PROJECT_ROOT} not set, using process.cwd()`);
|
||||||
|
|||||||
Reference in New Issue
Block a user