@c-d-cc/reap 0.1.3 → 0.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -4,58 +4,83 @@ description: "REAP Help — Contextual help based on current state"
4
4
 
5
5
  # Help
6
6
 
7
- Provide contextual help to the user based on the current REAP state.
7
+ **ARGUMENTS**: $ARGUMENTS
8
8
 
9
- ## Steps
9
+ ## File Access Rules
10
+ - ONLY read `.reap/life/current.yml` and `.reap/config.yml`. No other files for basic help.
11
+ - For topic help: also read `reap.{name}.md` from the same directory as this file.
12
+ - Do NOT access global node_modules. Do NOT guess file paths.
10
13
 
11
- ### 1. Read Current State
12
- - Read `.reap/life/current.yml`
13
- - Read `.reap/config.yml` for strict mode status
14
+ ## If ARGUMENTS is provided → skip to "Topic Help" section below.
14
15
 
15
- ### 2. Contextual Guidance
16
+ ## Basic Help (no arguments)
16
17
 
17
- **If no active Generation:**
18
- - "No active Generation. To get started:"
19
- - " `/reap.start` — Start a new Generation with a goal"
20
- - " `/reap.evolve` — Start and run the full lifecycle autonomously"
21
- - If there are items in `.reap/life/backlog/`, mention them
18
+ Read `.reap/life/current.yml` and `.reap/config.yml`, then output EXACTLY this format with values filled in. Use markdown formatting. Do NOT add extra explanation.
22
19
 
23
- **If active Generation exists:**
24
- - Show current generation ID, goal, and stage
25
- - Show the next action: "Current stage is [stage]. Run `/reap.[stage]` to proceed, or `/reap.next` to advance."
26
- - If in implementation stage with strict mode, note the planning scope restriction
20
+ ---
21
+
22
+ **REAP** Recursive Evolutionary Autonomous Pipeline
23
+
24
+ AI와 사람이 협업하여 소프트웨어를 세대(Generation) 단위로 진화시키는 개발 파이프라인입니다.
25
+ 각 세대는 5단계 lifecycle을 거칩니다:
26
+
27
+ `Objective` → `Planning` → `Implementation` → `Validation` → `Completion`
28
+
29
+ Genome(`.reap/genome/`)에 프로젝트의 설계 원칙과 규칙을 기록하고, 세대를 거듭하며 점진적으로 진화합니다.
27
30
 
28
- ### 3. Command Reference
31
+ ---
32
+
33
+ [If active generation exists, show:]
34
+ > 🔄 **{id}** — {goal}
35
+ > Stage: `{stage}` → 다음: `/reap.{stage}` 또는 `/reap.next`
36
+
37
+ [If no active generation, show:]
38
+ > No active Generation → `/reap.start` 또는 `/reap.evolve`
39
+
40
+ ---
29
41
 
30
- Show available slash commands with brief descriptions:
42
+ ### 커맨드
31
43
 
32
44
  | Command | Description |
33
45
  |---------|-------------|
34
- | `/reap.start` | Start a new Generation |
35
- | `/reap.evolve` | Run the full lifecycle autonomously |
36
- | `/reap.objective` | Define goal + requirements |
37
- | `/reap.planning` | Task decomposition + plan |
38
- | `/reap.implementation` | Code implementation |
39
- | `/reap.validation` | Run tests + verify |
40
- | `/reap.completion` | Retrospective + genome updates |
41
- | `/reap.next` | Advance to the next stage |
42
- | `/reap.back` | Return to a previous stage |
43
- | `/reap.status` | Show current state |
44
- | `/reap.sync` | Synchronize Genome with source code |
45
- | `/reap.help` | This help |
46
-
47
- ### 4. Topic Help (Optional)
48
-
49
- If the user provides a topic (e.g., `/reap.help workflow`), provide deeper explanation:
50
-
51
- - **workflow** — Explain the 5-stage lifecycle in detail
52
- - **commands** — Explain each slash command with examples
53
- - **strict** — Explain strict mode, how to enable/disable, and escape hatch
54
- - **genome** — Explain genome structure, immutability principle, and how to modify
55
- - **backlog** — Explain backlog types, status management, and archiving rules
56
-
57
- ### 5. Configuration Info
58
-
59
- - Show strict mode status (enabled/disabled)
60
- - Show project name and entry mode
61
- - Show total completed generations
46
+ | `/reap.start` | Generation을 시작하고 goal을 설정 |
47
+ | `/reap.evolve` | 전체 lifecycle 자율적으로 실행 (사람 개입 최소화) |
48
+ | `/reap.objective` | 이번 Generation의 목표, 요구사항, 완료 기준을 정의 |
49
+ | `/reap.planning` | 태스크를 분해하고 구현 계획을 수립 |
50
+ | `/reap.implementation` | 계획에 따라 코드를 구현하고 진행 상황을 기록 |
51
+ | `/reap.validation` | 테스트 실행, 완료 기준 충족 여부를 검증 |
52
+ | `/reap.completion` | 회고, Genome 변경 반영, Generation 마무리 |
53
+ | `/reap.next` | 다음 stage로 전진 (completion archiving + commit) |
54
+ | `/reap.back` | 이전 stage로 회귀 (regression 사유 기록) |
55
+ | `/reap.status` | 프로젝트 상태, Generation 진행도, backlog, Genome 건강도 표시 |
56
+ | `/reap.sync` | 현재 소스코드와 Genome 차이를 분석하고 동기화 |
57
+ | `/reap.update` | REAP 최신 버전 확인 및 업그레이드 |
58
+ | `/reap.help` | 도움말. `/reap.help {topic}`으로 주제별 상세 설명 |
59
+
60
+ 💡 `/reap.help {topic}` — workflow, genome, backlog, strict, agents, hooks, config, evolve, regression, author ...
61
+
62
+ **Config**: Strict: {on/off} · Auto-Update: {on/off} · Language: {value}
63
+
64
+ ---
65
+
66
+ ## Topic Help
67
+
68
+ If ARGUMENTS contains a topic, look up from the list below. **If NOT in the list, respond: "Unknown topic: '{topic}'. `/reap.help`로 available topics를 확인하세요."**
69
+
70
+ For command-name topics: read `reap.{name}.md` from the same directory as this file, then explain.
71
+
72
+ #### Topics
73
+
74
+ - **workflow** / **lifecycle** — 5-stage lifecycle: objective → planning → implementation → validation → completion. Gate → Steps → Artifact. `/reap.next`로 전진, `/reap.back`으로 회귀.
75
+ - **genome** — `.reap/genome/`: principles.md, conventions.md, constraints.md, domain/*.md. 불변 원칙: 현재 세대에서 직접 수정 금지 → backlog → completion에서 반영.
76
+ - **backlog** — `.reap/life/backlog/`. genome-change, environment-change, task. status: pending/consumed. consumed → lineage, pending → 이월.
77
+ - **strict** — `strict: true`: no generation = 코드 수정 차단, non-implementation = 차단, implementation = plan scope만. Escape: "override"/"bypass strict".
78
+ - **agents** — AgentAdapter 추상화. auto-detect (Claude Code, OpenCode). config.yml `agents` 오버라이드.
79
+ - **hooks** — config.yml: onGenerationStart, onStageTransition, onGenerationComplete, onRegression. command/prompt 타입.
80
+ - **config** — `.reap/config.yml`: version, project, entryMode, strict, language, agents, autoUpdate, hooks.
81
+ - **evolve** — `/reap.evolve`: 전체 lifecycle 자율 실행. 사람 확인 없이 objective~completion 순차 진행.
82
+ - **regression** — `/reap.back`: 이전 stage 회귀. timeline + artifact에 Regression 섹션 기록.
83
+ - **minor-fix** — 5분 이내, 설계 변경 없는 수정. stage 전환 없이 현재 artifact에 기록.
84
+ - **compression** — 10,000줄 + 5세대 이상 시 lineage 자동 압축. L1(40줄), L2(60줄).
85
+ - **author** — HyeonIL Choi. Email: hichoi@c-d.cc / Homepage: https://c-d.cc / LinkedIn: https://www.linkedin.com/in/hichoi-dev / GitHub: https://github.com/casamia918
86
+ - **start** / **objective** / **planning** / **implementation** / **validation** / **completion** / **next** / **back** / **sync** / **status** / **update** / **help** — Read `reap.{name}.md` from same directory, explain.
@@ -6,11 +6,19 @@ description: "REAP Status — Show current generation state and project health"
6
6
 
7
7
  Display a comprehensive overview of the current REAP project state.
8
8
 
9
+ ## IMPORTANT: File Access Rules
10
+ - ONLY read files explicitly listed in the steps below. Do NOT guess or infer file paths.
11
+ - If a file read fails or the file does not exist, skip it silently and continue.
12
+ - Do NOT attempt to read files like `reaprc.json`, `.reaprc`, or any file not specified in this command.
13
+ - The REAP project structure uses ONLY: `.reap/config.yml`, `.reap/life/current.yml`, `.reap/life/backlog/`, `.reap/life/0X-*.md`, `.reap/genome/`, `.reap/lineage/`
14
+
9
15
  ## Steps
10
16
 
11
- ### 1. Project Info
12
- - Read `.reap/config.yml` for project name, entryMode, preset, hooks
17
+ ### 1. Project Info (MUST execute all of these)
18
+ - Read `.reap/config.yml` for project name, entryMode, strict, autoUpdate, language
13
19
  - Count completed generations in `.reap/lineage/`
20
+ - **REQUIRED**: Run the shell command `reap --version` to get the installed version. You MUST actually execute this command, do not skip it.
21
+ - Show "REAP: v{installed}" — do NOT run `npm view` here (slow network call). Users can run `/reap.update` to check for updates.
14
22
 
15
23
  ### 2. Current Generation
16
24
  - Read `.reap/life/current.yml`
@@ -48,7 +56,9 @@ Present as a structured summary the human can quickly scan:
48
56
  ```
49
57
  📊 REAP Status
50
58
  ━━━━━━━━━━━━━━━━━━━━━━━━━━━━
59
+ REAP: v[installed] (run `/reap.update` to check for updates)
51
60
  Project: [name] ([entryMode])
61
+ Strict: [on/off] Auto-Update: [on/off] Language: [lang]
52
62
  Genome Version: v[N]
53
63
  Completed Generations: [count]
54
64
 
@@ -0,0 +1,40 @@
1
+ ---
2
+ description: "REAP Update — Check for updates and upgrade REAP"
3
+ ---
4
+
5
+ # Update
6
+
7
+ Check for REAP updates and upgrade to the latest version.
8
+
9
+ ## IMPORTANT: File Access Rules
10
+ - Do NOT access global node_modules or any path outside the project.
11
+ - If a command fails, report the error and stop.
12
+
13
+ ## Steps
14
+
15
+ ### 1. Check Current Version
16
+ - Run `reap --version` to get the installed version
17
+ - Run `npm view @c-d-cc/reap version` to get the latest published version
18
+ - Compare the two versions
19
+
20
+ ### 2. Update Decision
21
+ **If installed == latest:**
22
+ - "REAP v{version} is already up to date. (latest)"
23
+ - Then skip to Step 4.
24
+
25
+ **If installed < latest:**
26
+ - Show: "Update available: v{installed} → v{latest}"
27
+ - Ask the user: "Update now? (yes/no)"
28
+ - If yes: proceed to Step 3
29
+ - If no: "Skipped. Run `/reap.update` anytime to update."
30
+
31
+ ### 3. Perform Update
32
+ - Run: `npm update -g @c-d-cc/reap`
33
+ - If the command fails, suggest: `sudo npm update -g @c-d-cc/reap` or `npm install -g @c-d-cc/reap@latest`
34
+ - After npm update, run: `reap update` to sync commands, templates, and hooks to all detected agents
35
+ - Show the update result summary
36
+
37
+ ### 4. Sync Check
38
+ - Run: `reap update --dry-run` to check if commands/templates need syncing
39
+ - If changes detected: run `reap update` and show results
40
+ - If no changes: "All commands and templates are up to date."
@@ -0,0 +1,206 @@
1
+ // REAP SessionStart plugin for OpenCode
2
+ // Injects REAP guide + Genome + current generation context into every OpenCode session
3
+ // Installed to ~/.config/opencode/plugins/reap-session-start.js
4
+
5
+ const { execSync } = require("child_process");
6
+ const fs = require("fs");
7
+ const path = require("path");
8
+
9
+ module.exports = async (ctx) => {
10
+ return {
11
+ "session.start": async ({ trigger }) => {
12
+ const projectRoot = process.cwd();
13
+ const reapDir = path.join(projectRoot, ".reap");
14
+
15
+ // Check if this is a REAP project
16
+ if (!fs.existsSync(reapDir)) return;
17
+
18
+ // Auto-update check (with PATH resolution for non-shell environments)
19
+ let autoUpdateMessage = "";
20
+ try {
21
+ const autoConfigPath = path.join(reapDir, "config.yml");
22
+ if (fs.existsSync(autoConfigPath)) {
23
+ const configRaw = fs.readFileSync(autoConfigPath, "utf8");
24
+ const autoUpdateMatch = configRaw.match(/^autoUpdate:\s*(.+)$/m);
25
+ if (autoUpdateMatch && autoUpdateMatch[1].trim() === "true") {
26
+ try {
27
+ // Resolve PATH: OpenCode plugin runs in Node.js context which may lack shell PATH
28
+ const userShell = process.env.SHELL || "/bin/bash";
29
+ const shellPath = execSync(`${userShell} -l -c 'echo $PATH' 2>/dev/null`, { encoding: "utf8" }).trim();
30
+ const execOpts = { encoding: "utf8", env: { ...process.env, PATH: shellPath || process.env.PATH } };
31
+
32
+ const installed = execSync("reap --version 2>/dev/null", execOpts).trim();
33
+ const latest = execSync("npm view @c-d-cc/reap version 2>/dev/null", execOpts).trim();
34
+ if (installed && latest && installed !== latest) {
35
+ execSync("npm update -g @c-d-cc/reap >/dev/null 2>&1", { ...execOpts, stdio: "ignore" });
36
+ execSync("reap update >/dev/null 2>&1", { ...execOpts, stdio: "ignore" });
37
+ autoUpdateMessage = `REAP auto-updated: v${installed} → v${latest}`;
38
+ }
39
+ } catch { /* update check failed, skip */ }
40
+ }
41
+ }
42
+ } catch { /* config read failed, skip */ }
43
+
44
+ const scriptDir = __dirname;
45
+ // Look for reap-guide.md relative to the package hooks dir
46
+ // The guide is installed alongside this plugin's source package
47
+ const guideLocations = [
48
+ path.join(scriptDir, "..", "hooks", "reap-guide.md"),
49
+ path.join(scriptDir, "reap-guide.md"),
50
+ ];
51
+
52
+ let reapGuide = "";
53
+ for (const loc of guideLocations) {
54
+ if (fs.existsSync(loc)) {
55
+ reapGuide = fs.readFileSync(loc, "utf8");
56
+ break;
57
+ }
58
+ }
59
+
60
+ // If guide not found from package, try to get it via the reap CLI
61
+ if (!reapGuide) {
62
+ try {
63
+ // Find the package hooks dir by looking up from the plugin location
64
+ const possiblePaths = [
65
+ path.join(require.resolve("@c-d-cc/reap/package.json"), "..", "dist", "templates", "hooks", "reap-guide.md"),
66
+ ];
67
+ for (const p of possiblePaths) {
68
+ if (fs.existsSync(p)) {
69
+ reapGuide = fs.readFileSync(p, "utf8");
70
+ break;
71
+ }
72
+ }
73
+ } catch { /* package not found */ }
74
+ }
75
+
76
+ // Read Genome files
77
+ const genomeDir = path.join(reapDir, "genome");
78
+ let genomeContent = "";
79
+ const L1_LIMIT = 500;
80
+ const L2_LIMIT = 200;
81
+ let l1Lines = 0;
82
+
83
+ if (fs.existsSync(genomeDir)) {
84
+ for (const file of ["principles.md", "conventions.md", "constraints.md"]) {
85
+ const filePath = path.join(genomeDir, file);
86
+ if (fs.existsSync(filePath)) {
87
+ const content = fs.readFileSync(filePath, "utf8");
88
+ const lines = content.split("\n").length;
89
+ l1Lines += lines;
90
+ if (l1Lines <= L1_LIMIT) {
91
+ genomeContent += `\n### ${file}\n${content}\n`;
92
+ } else {
93
+ genomeContent += `\n### ${file} [TRUNCATED]\n${content.split("\n").slice(0, 20).join("\n")}\n...\n`;
94
+ }
95
+ }
96
+ }
97
+
98
+ // L2: domain/ files
99
+ const domainDir = path.join(genomeDir, "domain");
100
+ if (fs.existsSync(domainDir)) {
101
+ let l2Lines = 0;
102
+ let l2Overflow = false;
103
+ const domainFiles = fs.readdirSync(domainDir).filter(f => f.endsWith(".md"));
104
+ for (const file of domainFiles) {
105
+ const filePath = path.join(domainDir, file);
106
+ const content = fs.readFileSync(filePath, "utf8");
107
+ const lines = content.split("\n").length;
108
+ l2Lines += lines;
109
+ if (!l2Overflow && l2Lines <= L2_LIMIT) {
110
+ genomeContent += `\n### domain/${file}\n${content}\n`;
111
+ } else {
112
+ l2Overflow = true;
113
+ const firstLine = content.split("\n").find(l => l.startsWith(">")) || content.split("\n")[0];
114
+ genomeContent += `\n### domain/${file} [summary]\n${firstLine}\n`;
115
+ }
116
+ }
117
+ }
118
+ }
119
+
120
+ // Read config (strict mode + language)
121
+ let strictMode = false;
122
+ let language = "";
123
+ const configPath = path.join(reapDir, "config.yml");
124
+ if (fs.existsSync(configPath)) {
125
+ const configContent = fs.readFileSync(configPath, "utf8");
126
+ const strictMatch = configContent.match(/^strict:\s*(.+)$/m);
127
+ if (strictMatch && strictMatch[1].trim() === "true") {
128
+ strictMode = true;
129
+ }
130
+ const langMatch = configContent.match(/^language:\s*(.+)$/m);
131
+ if (langMatch) {
132
+ language = langMatch[1].trim();
133
+ }
134
+ }
135
+
136
+ // Read current.yml
137
+ const currentPath = path.join(reapDir, "life", "current.yml");
138
+ let genStage = "none";
139
+ let generationContext = "No active Generation. Run `/reap.start` to start one.";
140
+
141
+ if (fs.existsSync(currentPath)) {
142
+ const content = fs.readFileSync(currentPath, "utf8").trim();
143
+ if (content) {
144
+ const idMatch = content.match(/^id:\s*(.+)$/m);
145
+ const goalMatch = content.match(/^goal:\s*(.+)$/m);
146
+ const stageMatch = content.match(/^stage:\s*(.+)$/m);
147
+ if (idMatch && goalMatch && stageMatch) {
148
+ genStage = stageMatch[1].trim();
149
+ generationContext = `Active Generation: ${idMatch[1].trim()} | Goal: ${goalMatch[1].trim()} | Stage: ${genStage}`;
150
+ }
151
+ }
152
+ }
153
+
154
+ // Map stage to command
155
+ const stageCommandMap = {
156
+ objective: "/reap.objective",
157
+ planning: "/reap.planning",
158
+ implementation: "/reap.implementation",
159
+ validation: "/reap.validation",
160
+ completion: "/reap.completion",
161
+ };
162
+ const nextCmd = stageCommandMap[genStage] || "/reap.start";
163
+
164
+ // Build strict mode section
165
+ let strictSection = "";
166
+ if (strictMode) {
167
+ if (genStage === "implementation") {
168
+ strictSection = "\n\n## Strict Mode (ACTIVE — SCOPED MODIFICATION ALLOWED)\n<HARD-GATE>\nStrict mode is enabled. Code modification is ALLOWED only within the scope of the current Generation's plan.\n- You MUST read `.reap/life/02-planning.md` before writing any code.\n- You may ONLY modify files and modules listed in the plan's task list.\n- Changes outside the plan's scope are BLOCKED.\n</HARD-GATE>";
169
+ } else if (genStage === "none") {
170
+ strictSection = "\n\n## Strict Mode (ACTIVE — CODE MODIFICATION BLOCKED)\n<HARD-GATE>\nStrict mode is enabled and there is NO active Generation.\nYou MUST NOT write, edit, or create any source code files.\nAllowed actions: reading files, analyzing code, answering questions, running commands.\nTo start coding, the user must first run `/reap.start` and advance to the implementation stage.\n</HARD-GATE>";
171
+ } else {
172
+ strictSection = `\n\n## Strict Mode (ACTIVE — CODE MODIFICATION BLOCKED)\n<HARD-GATE>\nStrict mode is enabled. Current stage is '${genStage}', which is NOT the implementation stage.\nYou MUST NOT write, edit, or create any source code files.\n</HARD-GATE>`;
173
+ }
174
+ }
175
+
176
+ // Detect genome staleness
177
+ let staleSection = "";
178
+ try {
179
+ const lastCommit = execSync(`git -C "${projectRoot}" log -1 --format="%H" -- ".reap/genome/" 2>/dev/null`, { encoding: "utf8" }).trim();
180
+ if (lastCommit) {
181
+ const commitsSince = parseInt(execSync(`git -C "${projectRoot}" rev-list --count "${lastCommit}..HEAD" 2>/dev/null`, { encoding: "utf8" }).trim(), 10);
182
+ if (commitsSince > 10) {
183
+ staleSection = `\n\n## Genome Staleness\nWARNING: Genome may be stale — ${commitsSince} commits since last Genome update. Consider running /reap.sync.`;
184
+ }
185
+ }
186
+ } catch { /* git not available or not a repo */ }
187
+
188
+ // Build language instruction
189
+ let langSection = "";
190
+ if (language) {
191
+ langSection = `\n\n## Language\nAlways respond in ${language}. Use ${language} for all explanations, comments, and communications with the user. Technical terms and code identifiers should remain in their original form.`;
192
+ }
193
+
194
+ // Build auto-update section
195
+ let updateSection = "";
196
+ if (autoUpdateMessage) {
197
+ updateSection = `\n\n## Auto-Update\n${autoUpdateMessage}. Tell the user: "${autoUpdateMessage}"`;
198
+ }
199
+
200
+ const context = `<REAP_WORKFLOW>\n${reapGuide}\n\n---\n\n## Genome (Project Knowledge)\n${genomeContent}\n\n---\n\n## Current State\n${generationContext}${staleSection}${strictSection}${updateSection}${langSection}\n\n## Rules\n1. ALL development work MUST follow the REAP lifecycle.\n2. Before writing any code, check if a Generation is active and what stage it is in.\n3. If a Generation is active, use \`${nextCmd}\` to proceed with the current stage.\n4. If no Generation is active, use \`/reap.start\` to start a new one.\n5. Do NOT implement features outside of the REAP lifecycle unless explicitly asked.\n6. Genome is the authoritative knowledge source.\n</REAP_WORKFLOW>`;
201
+
202
+ // Inject context into session via return value
203
+ return { systemPrompt: context };
204
+ },
205
+ };
206
+ };
@@ -130,6 +130,10 @@ Only one of `command` or `prompt` should be set per entry.
130
130
 
131
131
  Hooks are executed by the AI agent.
132
132
 
133
+ ## Multi-Agent Support
134
+
135
+ REAP supports multiple AI agents simultaneously through the AgentAdapter abstraction. Currently supported: **Claude Code** and **OpenCode**. Detected agents are listed in `.reap/config.yml` under the `agents` field (managed by `reap init` / `reap update`). Slash commands and session hooks are installed to each detected agent's configuration directory.
136
+
133
137
  ## Role Separation
134
138
 
135
139
  | Component | Role |
@@ -3,6 +3,15 @@
3
3
  # This script runs from the package directory but uses cwd to find the project's .reap/
4
4
  set -euo pipefail
5
5
 
6
+ # Timing (node is guaranteed since REAP is an npm package)
7
+ _reap_ms() { node -e 'process.stdout.write(String(Date.now()))'; }
8
+ _reap_start_time=$(_reap_ms)
9
+ _reap_log() {
10
+ local now=$(_reap_ms)
11
+ local elapsed=$(( now - _reap_start_time ))
12
+ echo "[REAP hook +${elapsed}ms] $1" >&2
13
+ }
14
+
6
15
  # Script directory (package-internal) for guide file
7
16
  SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]:-$0}")" && pwd)"
8
17
 
@@ -13,17 +22,43 @@ CURRENT_YML="${REAP_DIR}/life/current.yml"
13
22
  GUIDE_FILE="${SCRIPT_DIR}/reap-guide.md"
14
23
  GENOME_DIR="${REAP_DIR}/genome"
15
24
 
25
+ _reap_log "Starting..."
26
+
16
27
  # Check if this is a REAP project
17
28
  if [ ! -d "$REAP_DIR" ]; then
29
+ _reap_log "Not a REAP project, exiting"
18
30
  exit 0
19
31
  fi
20
32
 
33
+ _reap_log "REAP project detected"
34
+
35
+ _reap_log "Checking auto-update..."
36
+ CONFIG_FILE="${REAP_DIR}/config.yml"
37
+ auto_update_message=""
38
+ if [ -f "$CONFIG_FILE" ]; then
39
+ auto_update=$(grep "^autoUpdate:" "$CONFIG_FILE" 2>/dev/null | sed 's/^autoUpdate: *//' | tr -d ' ' || true)
40
+ if [ "$auto_update" = "true" ]; then
41
+ installed=$(reap --version 2>/dev/null || echo "")
42
+ latest=$(npm view @c-d-cc/reap version 2>/dev/null || echo "")
43
+ if [ -n "$installed" ] && [ -n "$latest" ] && [ "$installed" != "$latest" ]; then
44
+ if npm update -g @c-d-cc/reap >/dev/null 2>&1; then
45
+ reap update >/dev/null 2>&1 || true
46
+ auto_update_message="REAP auto-updated: v${installed} → v${latest}"
47
+ fi
48
+ fi
49
+ fi
50
+ fi
51
+
52
+ _reap_log "Auto-update check done"
53
+
21
54
  # Read REAP guide
55
+ _reap_log "Loading REAP guide..."
22
56
  reap_guide=""
23
57
  if [ -f "$GUIDE_FILE" ]; then
24
58
  reap_guide=$(cat "$GUIDE_FILE")
25
59
  fi
26
60
 
61
+ _reap_log "Loading Genome..."
27
62
  # Read Genome files with tiered loading
28
63
  # L1 (~500 lines max): principles.md, conventions.md, constraints.md — always full load
29
64
  # L2 (~200 lines max): domain/*.md — full load if within budget, otherwise title+summary only
@@ -74,7 +109,7 @@ genome_stale_warning=""
74
109
  if command -v git &>/dev/null && [ -d "$PROJECT_ROOT/.git" ]; then
75
110
  last_genome_commit=$(git -C "$PROJECT_ROOT" log -1 --format="%H" -- ".reap/genome/" 2>/dev/null || echo "")
76
111
  if [ -n "$last_genome_commit" ]; then
77
- commits_since=$(git -C "$PROJECT_ROOT" rev-list --count "${last_genome_commit}..HEAD" 2>/dev/null || echo "0")
112
+ commits_since=$(git -C "$PROJECT_ROOT" rev-list --count "${last_genome_commit}..HEAD" -- src/ tests/ package.json tsconfig.json scripts/ 2>/dev/null || echo "0")
78
113
  if [ "$commits_since" -gt 10 ]; then
79
114
  genome_stale_warning="WARNING: Genome may be stale — ${commits_since} commits since last Genome update. Consider running /reap.sync to synchronize."
80
115
  fi
@@ -120,13 +155,7 @@ esac
120
155
 
121
156
  # Escape for JSON
122
157
  escape_for_json() {
123
- local s="$1"
124
- s="${s//\\/\\\\}"
125
- s="${s//\"/\\\"}"
126
- s="${s//$'\n'/\\n}"
127
- s="${s//$'\r'/\\r}"
128
- s="${s//$'\t'/\\t}"
129
- printf '%s' "$s"
158
+ printf '%s' "$1" | node -e 'let d="";process.stdin.on("data",c=>d+=c);process.stdin.on("end",()=>process.stdout.write(JSON.stringify(d).slice(1,-1)))'
130
159
  }
131
160
 
132
161
  # Build strict mode section
@@ -147,9 +176,17 @@ if [ -n "$genome_stale_warning" ]; then
147
176
  stale_section="\n\n## Genome Staleness\n${genome_stale_warning}\nIf the user wants to proceed without syncing, ask: \"The Genome may be stale. Would you like to run /reap.sync now, or do it later?\" and respect their choice."
148
177
  fi
149
178
 
150
- reap_context="<REAP_WORKFLOW>\n${reap_guide}\n\n---\n\n## Genome (Project Knowledge — treat as authoritative source of truth)\n${genome_content}\n\n---\n\n## Current State\n${generation_context}${stale_section}${strict_section}\n\n## Rules\n1. ALL development work MUST follow the REAP lifecycle. Do NOT bypass it.\n2. Before writing any code, check if a Generation is active and what stage it is in.\n3. If a Generation is active, use \`${next_cmd}\` to proceed with the current stage.\n4. If no Generation is active, use \`/reap.start\` to start a new one.\n5. Do NOT implement features, fix bugs, or make changes outside of the REAP lifecycle unless the user explicitly asks to bypass it.\n6. When the user says \"reap evolve\", \"next stage\", \"proceed\", or similar — invoke the appropriate REAP skill.\n7. **Genome is the authoritative knowledge source.** When making decisions about architecture, conventions, or constraints, ALWAYS reference the Genome first. If code contradicts Genome, flag it as a potential genome-change backlog item.\n8. If you notice the Genome is outdated or missing information relevant to your current task, inform the user and suggest running \`/reap.sync\`.\n</REAP_WORKFLOW>"
179
+ # Build auto-update section
180
+ update_section=""
181
+ if [ -n "$auto_update_message" ]; then
182
+ update_section="\n\n## Auto-Update\n${auto_update_message}. Tell the user: \"${auto_update_message}\""
183
+ fi
184
+
185
+ reap_context="<REAP_WORKFLOW>\n${reap_guide}\n\n---\n\n## Genome (Project Knowledge — treat as authoritative source of truth)\n${genome_content}\n\n---\n\n## Current State\n${generation_context}${stale_section}${strict_section}${update_section}\n\n## Rules\n1. ALL development work MUST follow the REAP lifecycle. Do NOT bypass it.\n2. Before writing any code, check if a Generation is active and what stage it is in.\n3. If a Generation is active, use \`${next_cmd}\` to proceed with the current stage.\n4. If no Generation is active, use \`/reap.start\` to start a new one.\n5. Do NOT implement features, fix bugs, or make changes outside of the REAP lifecycle unless the user explicitly asks to bypass it.\n6. When the user says \"reap evolve\", \"next stage\", \"proceed\", or similar — invoke the appropriate REAP skill.\n7. **Genome is the authoritative knowledge source.** When making decisions about architecture, conventions, or constraints, ALWAYS reference the Genome first. If code contradicts Genome, flag it as a potential genome-change backlog item.\n8. If you notice the Genome is outdated or missing information relevant to your current task, inform the user and suggest running \`/reap.sync\`.\n</REAP_WORKFLOW>"
151
186
 
187
+ _reap_log "Building context..."
152
188
  escaped_context=$(escape_for_json "$reap_context")
189
+ _reap_log "Done. Outputting JSON."
153
190
 
154
191
  cat <<EOF
155
192
  {
package/package.json CHANGED
@@ -1,10 +1,10 @@
1
1
  {
2
2
  "name": "@c-d-cc/reap",
3
- "version": "0.1.3",
3
+ "version": "0.2.2",
4
4
  "description": "Recursive Evolutionary Autonomous Pipeline — AI and humans evolve software across generations",
5
5
  "type": "module",
6
6
  "license": "MIT",
7
- "author": "HiChoi <hichoi@c-d.cc> (C to D)",
7
+ "author": "HyeonIL Choi <hichoi@c-d.cc> (C to D)",
8
8
  "repository": {
9
9
  "type": "git",
10
10
  "url": "git+https://github.com/c-d-cc/reap.git"