ralph-lisa-loop 0.3.0

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.
package/README.md ADDED
@@ -0,0 +1,234 @@
1
+ # Ralph-Lisa Loop
2
+
3
+ <p align="center">
4
+ <img src="../rll_cat.png" alt="Ralph-Lisa Loop" width="256" />
5
+ </p>
6
+
7
+ Turn-based dual-agent collaboration: Ralph codes, Lisa reviews, consensus required.
8
+
9
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](LICENSE)
10
+ [![npm version](https://img.shields.io/npm/v/ralph-lisa-loop.svg)](https://www.npmjs.com/package/ralph-lisa-loop)
11
+
12
+ ## The Problem
13
+
14
+ Single-agent coding is like grading your own exam. The same model writes code AND decides if it's done. No external validation. No second opinion.
15
+
16
+ ## The Solution
17
+
18
+ **Ralph-Lisa Loop** enforces a strict turn-based workflow:
19
+
20
+ ```
21
+ Ralph writes → Lisa reviews → Consensus → Next step
22
+ ↑ |
23
+ └────────────────────────────────────────┘
24
+ ```
25
+
26
+ - **Ralph** (Claude Code): Lead developer - researches, plans, codes, tests
27
+ - **Lisa** (Codex): Code reviewer - reviews, provides feedback
28
+ - **Turn Control**: Only one agent works at a time
29
+ - **Consensus Required**: Both must agree before proceeding
30
+ - **Research First**: When involving reference implementations/protocols/APIs, Ralph must submit [RESEARCH] before coding
31
+ - **Test Results Required**: [CODE] and [FIX] submissions must include test results
32
+ - **Policy Layer**: Configurable warn/block mode for submission quality checks
33
+
34
+ ## Quick Start
35
+
36
+ ### 1. Install
37
+
38
+ ```bash
39
+ npm i -g ralph-lisa
40
+ ```
41
+
42
+ ### 2. Initialize Project
43
+
44
+ ```bash
45
+ cd your-project
46
+ ralph-lisa init
47
+ ```
48
+
49
+ ### 3. Start Collaboration
50
+
51
+ ```bash
52
+ # Manual mode (recommended)
53
+ ralph-lisa start "implement login feature"
54
+
55
+ # Or auto mode (experimental, requires tmux)
56
+ ralph-lisa auto "implement login feature"
57
+ ```
58
+
59
+ ### 4. Work Flow
60
+
61
+ **Terminal 1 - Ralph (Claude Code)**:
62
+ ```bash
63
+ ralph-lisa whose-turn # Check turn
64
+ # ... do work ...
65
+ ralph-lisa submit-ralph "[PLAN] Login feature design
66
+
67
+ 1. Create login form component
68
+ 2. Add validation
69
+ 3. Connect to API"
70
+ ```
71
+
72
+ **Terminal 2 - Lisa (Codex)**:
73
+ ```bash
74
+ ralph-lisa whose-turn # Check turn
75
+ ralph-lisa read work.md # Read Ralph's work
76
+ ralph-lisa submit-lisa "[PASS] Plan looks good
77
+
78
+ - Clear structure
79
+ - Good separation of concerns"
80
+ ```
81
+
82
+ ## Features
83
+
84
+ ### Turn Control
85
+ Agents must check `whose-turn` before any action. Submissions automatically pass the turn.
86
+
87
+ ### Tag System
88
+ Every submission requires a tag:
89
+
90
+ | Ralph Tags | Lisa Tags | Shared |
91
+ |------------|-----------|--------|
92
+ | `[PLAN]` | `[PASS]` | `[CHALLENGE]` |
93
+ | `[RESEARCH]` | `[NEEDS_WORK]` | `[DISCUSS]` |
94
+ | `[CODE]` | | `[QUESTION]` |
95
+ | `[FIX]` | | `[CONSENSUS]` |
96
+
97
+ - `[RESEARCH]`: Submit research results before coding (when involving reference implementations, protocols, or external APIs)
98
+ - `[CHALLENGE]`: Explicitly disagree with the other agent's suggestion, providing counter-argument
99
+ - `[CODE]`/`[FIX]`: Must include Test Results section
100
+
101
+ ### Consensus Protocol
102
+ Lisa's verdict is advisory. Ralph can agree or use `[CHALLENGE]` to disagree. Both must reach genuine consensus before `/next-step`. Silent acceptance (bare `[FIX]` without reasoning) is not allowed.
103
+
104
+ ### Minimal Init (Zero Intrusion)
105
+
106
+ When using the Claude Code plugin + Codex global config, you don't need project-level role files:
107
+
108
+ ```bash
109
+ ralph-lisa init --minimal
110
+ ```
111
+
112
+ This only creates `.dual-agent/` session state. No CLAUDE.md, CODEX.md, or command files are written. Requires:
113
+ - Claude Code plugin installed (provides Ralph role via hooks)
114
+ - Codex global config at `~/.codex/` (provides Lisa role)
115
+
116
+ `start` and `auto` commands work with both full and minimal init.
117
+
118
+ ### Policy Layer
119
+
120
+ **Inline checks** (during `submit-ralph`/`submit-lisa`):
121
+
122
+ ```bash
123
+ # Enable warn mode (prints warnings, doesn't block)
124
+ export RL_POLICY_MODE=warn
125
+
126
+ # Enable block mode (rejects non-compliant submissions)
127
+ export RL_POLICY_MODE=block
128
+
129
+ # Disable (default)
130
+ export RL_POLICY_MODE=off
131
+ ```
132
+
133
+ **Standalone checks** (for scripts/hooks — always exit non-zero on violations, ignoring `RL_POLICY_MODE`):
134
+
135
+ ```bash
136
+ ralph-lisa policy check ralph # Check Ralph's latest submission
137
+ ralph-lisa policy check lisa # Check Lisa's latest submission
138
+ ralph-lisa policy check-consensus # Both agents submitted [CONSENSUS]?
139
+ ralph-lisa policy check-next-step # Comprehensive: consensus + all policy checks
140
+ ```
141
+
142
+ Policy rules:
143
+ - Ralph's [CODE]/[FIX] must include "Test Results" section
144
+ - Ralph's [RESEARCH] must have substantive content
145
+ - Lisa's [PASS]/[NEEDS_WORK] must include at least 1 reason
146
+
147
+ ### Deadlock Escape
148
+ After 5 rounds without consensus: `[OVERRIDE]` (proceed anyway) or `[HANDOFF]` (escalate to human).
149
+
150
+ ## Commands
151
+
152
+ ```bash
153
+ # Project setup
154
+ ralph-lisa init [dir] # Initialize project (full)
155
+ ralph-lisa init --minimal [dir] # Minimal init (session only, no project files)
156
+ ralph-lisa uninit # Remove from project
157
+ ralph-lisa start "task" # Launch both agents
158
+ ralph-lisa start --full-auto "task" # Launch without permission prompts
159
+ ralph-lisa auto "task" # Auto mode (tmux)
160
+ ralph-lisa auto --full-auto "task" # Auto mode without permission prompts
161
+
162
+ # Turn control
163
+ ralph-lisa whose-turn # Check whose turn
164
+ ralph-lisa submit-ralph "[TAG] ..." # Ralph submits
165
+ ralph-lisa submit-lisa "[TAG] ..." # Lisa submits
166
+
167
+ # Information
168
+ ralph-lisa status # Current status
169
+ ralph-lisa read work.md # Ralph's latest
170
+ ralph-lisa read review.md # Lisa's latest
171
+ ralph-lisa history # Full history
172
+
173
+ # Flow control
174
+ ralph-lisa step "phase-name" # Enter new phase
175
+ ralph-lisa archive [name] # Archive session
176
+ ralph-lisa clean # Clean session
177
+
178
+ # Policy
179
+ ralph-lisa policy check <ralph|lisa> # Check submission (hard gate)
180
+ ralph-lisa policy check-consensus # Check if both [CONSENSUS]
181
+ ralph-lisa policy check-next-step # Comprehensive pre-step check
182
+
183
+ # Diagnostics
184
+ ralph-lisa doctor # Check all dependencies
185
+ ralph-lisa doctor --strict # Exit 1 if any missing (for CI)
186
+ ```
187
+
188
+ ## Project Structure After Init
189
+
190
+ **Full init** (`ralph-lisa init`):
191
+ ```
192
+ your-project/
193
+ ├── CLAUDE.md # Ralph's role (auto-loaded by Claude Code)
194
+ ├── CODEX.md # Lisa's role (loaded via .codex/config.toml)
195
+ ├── .claude/
196
+ │ └── commands/ # Claude slash commands
197
+ ├── .codex/
198
+ │ ├── config.toml # Codex configuration
199
+ │ └── skills/ # Codex skills
200
+ └── .dual-agent/ # Session state
201
+ ├── turn.txt # Current turn
202
+ ├── work.md # Ralph's submissions
203
+ ├── review.md # Lisa's submissions
204
+ └── history.md # Full history
205
+ ```
206
+
207
+ **Minimal init** (`ralph-lisa init --minimal`):
208
+ ```
209
+ your-project/
210
+ └── .dual-agent/ # Session state only (zero project files)
211
+ ```
212
+
213
+ ## Requirements
214
+
215
+ - [Node.js](https://nodejs.org/) >= 18
216
+ - [Claude Code](https://claude.ai/code) - for Ralph
217
+ - [Codex CLI](https://github.com/openai/codex) - for Lisa
218
+
219
+ For auto mode:
220
+ - tmux (required)
221
+ - fswatch (macOS) or inotify-tools (Linux) — optional, speeds up turn detection; falls back to polling without them
222
+
223
+ ## Ecosystem
224
+
225
+ Part of the [TigerHill](https://github.com/Click-Intelligence-LLC/TigerHill) project family.
226
+
227
+ ## See Also
228
+
229
+ - [CONCEPT.md](CONCEPT.md) - Why dual-agent collaboration works
230
+ - [UPGRADE_PLAN_V3.md](UPGRADE_PLAN_V3.md) - V3 design document
231
+
232
+ ## License
233
+
234
+ [MIT](LICENSE)
package/dist/cli.d.ts ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env node
2
+ /**
3
+ * ralph-lisa CLI - Turn-based dual-agent collaboration.
4
+ * Replaces io.sh with Node/TS implementation.
5
+ *
6
+ * Usage: ralph-lisa <command> [args...]
7
+ */
8
+ export {};
package/dist/cli.js ADDED
@@ -0,0 +1,142 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ /**
4
+ * ralph-lisa CLI - Turn-based dual-agent collaboration.
5
+ * Replaces io.sh with Node/TS implementation.
6
+ *
7
+ * Usage: ralph-lisa <command> [args...]
8
+ */
9
+ Object.defineProperty(exports, "__esModule", { value: true });
10
+ const commands_js_1 = require("./commands.js");
11
+ const args = process.argv.slice(2);
12
+ const cmd = args[0] || "";
13
+ const rest = args.slice(1);
14
+ switch (cmd) {
15
+ case "init":
16
+ // If first arg after init looks like a path, use cmdInitProject
17
+ // If it looks like a task description, also use cmdInitProject (with no path)
18
+ (0, commands_js_1.cmdInitProject)(rest);
19
+ break;
20
+ case "uninit":
21
+ (0, commands_js_1.cmdUninit)();
22
+ break;
23
+ case "whose-turn":
24
+ (0, commands_js_1.cmdWhoseTurn)();
25
+ break;
26
+ case "submit-ralph":
27
+ (0, commands_js_1.cmdSubmitRalph)(rest);
28
+ break;
29
+ case "submit-lisa":
30
+ (0, commands_js_1.cmdSubmitLisa)(rest);
31
+ break;
32
+ case "status":
33
+ (0, commands_js_1.cmdStatus)();
34
+ break;
35
+ case "read":
36
+ (0, commands_js_1.cmdRead)(rest);
37
+ break;
38
+ case "recap":
39
+ (0, commands_js_1.cmdRecap)();
40
+ break;
41
+ case "step":
42
+ (0, commands_js_1.cmdStep)(rest);
43
+ break;
44
+ case "history":
45
+ (0, commands_js_1.cmdHistory)();
46
+ break;
47
+ case "archive":
48
+ (0, commands_js_1.cmdArchive)(rest);
49
+ break;
50
+ case "clean":
51
+ (0, commands_js_1.cmdClean)();
52
+ break;
53
+ case "start":
54
+ (0, commands_js_1.cmdStart)(rest);
55
+ break;
56
+ case "auto":
57
+ (0, commands_js_1.cmdAuto)(rest);
58
+ break;
59
+ case "policy":
60
+ (0, commands_js_1.cmdPolicy)(rest);
61
+ break;
62
+ case "doctor":
63
+ (0, commands_js_1.cmdDoctor)(rest);
64
+ break;
65
+ case "logs":
66
+ (0, commands_js_1.cmdLogs)(rest);
67
+ break;
68
+ case "help":
69
+ case "--help":
70
+ case "-h":
71
+ case "":
72
+ showHelp();
73
+ break;
74
+ case "--version":
75
+ case "-v":
76
+ showVersion();
77
+ break;
78
+ default:
79
+ console.error(`Unknown command: ${cmd}`);
80
+ console.error('Run "ralph-lisa --help" for usage.');
81
+ process.exit(1);
82
+ }
83
+ function showHelp() {
84
+ console.log("Ralph Lisa Dual-Agent Loop - CLI");
85
+ console.log("");
86
+ console.log("Project Setup:");
87
+ console.log(" ralph-lisa init [dir] Initialize project");
88
+ console.log(" ralph-lisa init --minimal [dir] Minimal init (session only, no project files)");
89
+ console.log(" ralph-lisa uninit Remove from project");
90
+ console.log(' ralph-lisa start "task" Launch both agents');
91
+ console.log(' ralph-lisa start --full-auto "task" Launch without permission prompts');
92
+ console.log(' ralph-lisa auto "task" Auto mode (tmux)');
93
+ console.log(' ralph-lisa auto --full-auto "task" Auto mode without permission prompts');
94
+ console.log("");
95
+ console.log("Turn Control:");
96
+ console.log(" ralph-lisa whose-turn Check whose turn");
97
+ console.log(' ralph-lisa submit-ralph "[TAG]..." Ralph submits');
98
+ console.log(" ralph-lisa submit-ralph --file <f> Ralph submits from file");
99
+ console.log(' ralph-lisa submit-lisa "[TAG]..." Lisa submits');
100
+ console.log(" ralph-lisa submit-lisa --file <f> Lisa submits from file");
101
+ console.log("");
102
+ console.log("Tags:");
103
+ console.log(" Ralph: [PLAN] [RESEARCH] [CODE] [FIX] [CHALLENGE] [DISCUSS] [QUESTION] [CONSENSUS]");
104
+ console.log(" Lisa: [PASS] [NEEDS_WORK] [CHALLENGE] [DISCUSS] [QUESTION] [CONSENSUS]");
105
+ console.log("");
106
+ console.log("Information:");
107
+ console.log(" ralph-lisa status Show current status");
108
+ console.log(" ralph-lisa read <file> Read work.md/review.md");
109
+ console.log(" ralph-lisa recap Context recovery summary");
110
+ console.log(" ralph-lisa history Show full history");
111
+ console.log("");
112
+ console.log("Flow Control:");
113
+ console.log(' ralph-lisa step "name" Enter new step');
114
+ console.log(" ralph-lisa archive [name] Archive session");
115
+ console.log(" ralph-lisa clean Clean session");
116
+ console.log("");
117
+ console.log("Policy:");
118
+ console.log(" ralph-lisa policy check <ralph|lisa> Check submission (hard gate)");
119
+ console.log(" ralph-lisa policy check-consensus Check if both [CONSENSUS]");
120
+ console.log(" ralph-lisa policy check-next-step Comprehensive pre-step check");
121
+ console.log("");
122
+ console.log(" Standalone policy check always exits non-zero on violations.");
123
+ console.log(" RL_POLICY_MODE (warn|block|off) affects inline submit checks (default: warn).");
124
+ console.log("");
125
+ console.log("Logs:");
126
+ console.log(" ralph-lisa logs List all transcript logs");
127
+ console.log(" ralph-lisa logs cat View live pane logs");
128
+ console.log(" ralph-lisa logs cat <file> View specific log file");
129
+ console.log("");
130
+ console.log("Diagnostics:");
131
+ console.log(" ralph-lisa doctor Check all dependencies");
132
+ console.log(" ralph-lisa doctor --strict Exit 1 if any missing (for CI)");
133
+ }
134
+ function showVersion() {
135
+ try {
136
+ const pkg = require("../package.json");
137
+ console.log(`ralph-lisa-loop v${pkg.version}`);
138
+ }
139
+ catch {
140
+ console.log("ralph-lisa-loop v0.3.0");
141
+ }
142
+ }
@@ -0,0 +1,22 @@
1
+ /**
2
+ * CLI commands for Ralph-Lisa Loop.
3
+ * Direct port of io.sh logic to Node/TS.
4
+ */
5
+ export declare function cmdInit(args: string[]): void;
6
+ export declare function cmdWhoseTurn(): void;
7
+ export declare function cmdSubmitRalph(args: string[]): void;
8
+ export declare function cmdSubmitLisa(args: string[]): void;
9
+ export declare function cmdStatus(): void;
10
+ export declare function cmdRead(args: string[]): void;
11
+ export declare function cmdRecap(): void;
12
+ export declare function cmdStep(args: string[]): void;
13
+ export declare function cmdHistory(): void;
14
+ export declare function cmdArchive(args: string[]): void;
15
+ export declare function cmdClean(): void;
16
+ export declare function cmdUninit(): void;
17
+ export declare function cmdInitProject(args: string[]): void;
18
+ export declare function cmdStart(args: string[]): void;
19
+ export declare function cmdAuto(args: string[]): void;
20
+ export declare function cmdPolicy(args: string[]): void;
21
+ export declare function cmdLogs(args: string[]): void;
22
+ export declare function cmdDoctor(args: string[]): void;