botmux 2.21.3 → 2.21.4
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.
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"coco.d.ts","sourceRoot":"","sources":["../../../src/adapters/cli/coco.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"coco.d.ts","sourceRoot":"","sources":["../../../src/adapters/cli/coco.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,UAAU,EAAa,MAAM,YAAY,CAAC;AAyExD,wBAAgB,iBAAiB,CAAC,YAAY,CAAC,EAAE,MAAM,GAAG,UAAU,CA0InE;AAED,eAAO,MAAM,MAAM,0BAAoB,CAAC"}
|
|
@@ -1,8 +1,88 @@
|
|
|
1
|
+
import { existsSync, statSync, openSync, readSync, closeSync } from 'node:fs';
|
|
2
|
+
import { homedir } from 'node:os';
|
|
3
|
+
import { join } from 'node:path';
|
|
1
4
|
import { resolveCommand } from './registry.js';
|
|
2
5
|
import { BOTMUX_SHELL_HINTS } from './shared-hints.js';
|
|
6
|
+
/** Global submit log — CoCo appends one JSON line here on every successful
|
|
7
|
+
* user submit across all sessions (mode:"user"). Format observed:
|
|
8
|
+
* `{"content":"...","mode":"user","timestamp":"..."}`. Used the same way
|
|
9
|
+
* the Codex adapter uses ~/.codex/history.jsonl: write → poll for our
|
|
10
|
+
* marker → retry Enter if missing → return {submitted:false, recheck}
|
|
11
|
+
* on final failure so worker can surface a Lark warning. */
|
|
12
|
+
const HISTORY_PATH = join(homedir(), '.cache', 'coco', 'history.jsonl');
|
|
3
13
|
function delay(ms) {
|
|
4
14
|
return new Promise(resolve => setTimeout(resolve, ms));
|
|
5
15
|
}
|
|
16
|
+
function currentFileSize(path) {
|
|
17
|
+
if (!existsSync(path))
|
|
18
|
+
return 0;
|
|
19
|
+
try {
|
|
20
|
+
return statSync(path).size;
|
|
21
|
+
}
|
|
22
|
+
catch {
|
|
23
|
+
return 0;
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
/** Scan `path` for a JSON line newer than `fromByte` that's a user-submit
|
|
27
|
+
* whose decoded `content` starts with `prefix`. Parses each candidate line
|
|
28
|
+
* with JSON.parse — substring match on the raw bytes is unreliable here
|
|
29
|
+
* because CoCo's Go marshaller HTML-escapes `<`, `>`, `&` into `<`,
|
|
30
|
+
* `>`, `&`, which our string-form prefix won't match. Decoding
|
|
31
|
+
* the field and comparing JS strings sidesteps all of that. */
|
|
32
|
+
function historyDeltaContains(path, fromByte, prefix) {
|
|
33
|
+
if (!existsSync(path))
|
|
34
|
+
return false;
|
|
35
|
+
let size;
|
|
36
|
+
try {
|
|
37
|
+
size = statSync(path).size;
|
|
38
|
+
}
|
|
39
|
+
catch {
|
|
40
|
+
return false;
|
|
41
|
+
}
|
|
42
|
+
if (size <= fromByte)
|
|
43
|
+
return false;
|
|
44
|
+
const len = size - fromByte;
|
|
45
|
+
const buf = Buffer.alloc(len);
|
|
46
|
+
const fd = openSync(path, 'r');
|
|
47
|
+
try {
|
|
48
|
+
readSync(fd, buf, 0, len, fromByte);
|
|
49
|
+
}
|
|
50
|
+
finally {
|
|
51
|
+
closeSync(fd);
|
|
52
|
+
}
|
|
53
|
+
const delta = buf.toString('utf8');
|
|
54
|
+
for (const line of delta.split('\n')) {
|
|
55
|
+
if (!line || !line.includes('"mode":"user"'))
|
|
56
|
+
continue;
|
|
57
|
+
try {
|
|
58
|
+
const parsed = JSON.parse(line);
|
|
59
|
+
if (typeof parsed.content === 'string' && parsed.content.startsWith(prefix)) {
|
|
60
|
+
return true;
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
catch {
|
|
64
|
+
// Truncated tail / non-JSON line — keep scanning the rest.
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
return false;
|
|
68
|
+
}
|
|
69
|
+
async function waitForHistoryAppend(path, fromByte, prefix, timeoutMs) {
|
|
70
|
+
const deadline = Date.now() + timeoutMs;
|
|
71
|
+
while (Date.now() < deadline) {
|
|
72
|
+
if (historyDeltaContains(path, fromByte, prefix))
|
|
73
|
+
return true;
|
|
74
|
+
await delay(100);
|
|
75
|
+
}
|
|
76
|
+
return false;
|
|
77
|
+
}
|
|
78
|
+
/** First 40 chars of the original content — used as a prefix match against
|
|
79
|
+
* the JSON-decoded `content` field of each user-mode line in history.jsonl.
|
|
80
|
+
* Compare against decoded strings, NOT against raw file bytes: CoCo's Go
|
|
81
|
+
* marshaller HTML-escapes `<`, `>`, `&` so a JSON-encoded marker wouldn't
|
|
82
|
+
* match the stored bytes. 40 chars is unique enough across concurrent bots. */
|
|
83
|
+
function submitPrefix(content) {
|
|
84
|
+
return content.slice(0, 40);
|
|
85
|
+
}
|
|
6
86
|
export function createCocoAdapter(pathOverride) {
|
|
7
87
|
const bin = resolveCommand(pathOverride ?? 'coco');
|
|
8
88
|
return {
|
|
@@ -24,16 +104,110 @@ export function createCocoAdapter(pathOverride) {
|
|
|
24
104
|
return `coco --resume ${sessionId}`;
|
|
25
105
|
},
|
|
26
106
|
async writeInput(pty, content) {
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
107
|
+
// CoCo is a Claude Code fork (Ink TUI) and inherits Claude Code's two
|
|
108
|
+
// failure modes when content has embedded newlines:
|
|
109
|
+
// 1. tmux `send-keys -l` treats each \n as Enter, so a raw sendText
|
|
110
|
+
// of multi-line content either submits fragments line-by-line or
|
|
111
|
+
// paste-burst-coalesces with the *trailing* Enter consumed as part
|
|
112
|
+
// of the paste — text just sits in the input box, never submitted.
|
|
113
|
+
// 2. The old adapter had no verification, so the worker never knew
|
|
114
|
+
// and the user stared at Lark waiting for a reply that never came.
|
|
115
|
+
//
|
|
116
|
+
// Fix mirrors claude-code.ts:
|
|
117
|
+
// - split content by \n, type each line via send-keys -l, insert
|
|
118
|
+
// soft-newline (`\` + Enter) between lines — Claude Code's
|
|
119
|
+
// documented idiom to add a newline without submitting.
|
|
120
|
+
// - throttle each tmux call (~30ms) to stay under the paste-burst
|
|
121
|
+
// threshold so soft-newlines aren't silently swallowed as a paste.
|
|
122
|
+
// - submitDelay then a single Enter to actually submit.
|
|
123
|
+
//
|
|
124
|
+
// Verification mirrors codex.ts using ~/.cache/coco/history.jsonl:
|
|
125
|
+
// write → poll for our content prefix in the delta → retry Enter up
|
|
126
|
+
// to 3 times → return {submitted:false, recheck} on final miss so the
|
|
127
|
+
// worker can defer-recheck and otherwise surface a Lark warning.
|
|
128
|
+
const hasImagePath = /\.(jpe?g|png|gif|webp|svg|bmp)\b/i.test(content);
|
|
129
|
+
const submitDelay = hasImagePath ? 800 : 500;
|
|
130
|
+
const TYPING_THROTTLE_MS = 30;
|
|
131
|
+
const tick = () => new Promise(r => setTimeout(r, TYPING_THROTTLE_MS));
|
|
132
|
+
const trySendEnter = () => {
|
|
133
|
+
try {
|
|
134
|
+
if (pty.sendSpecialKeys)
|
|
135
|
+
pty.sendSpecialKeys('Enter');
|
|
136
|
+
else
|
|
137
|
+
pty.write('\r');
|
|
138
|
+
return true;
|
|
139
|
+
}
|
|
140
|
+
catch {
|
|
141
|
+
// tmux session is gone (CLI exited mid-write) — bail cleanly
|
|
142
|
+
// rather than crashing the worker on unhandled execFileSync.
|
|
143
|
+
return false;
|
|
144
|
+
}
|
|
145
|
+
};
|
|
146
|
+
const baseByte = currentFileSize(HISTORY_PATH);
|
|
147
|
+
const prefix = submitPrefix(content);
|
|
148
|
+
try {
|
|
149
|
+
if (pty.sendText && pty.sendSpecialKeys) {
|
|
150
|
+
const lines = content.split('\n');
|
|
151
|
+
for (let i = 0; i < lines.length; i++) {
|
|
152
|
+
if (lines[i].length > 0) {
|
|
153
|
+
pty.sendText(lines[i]);
|
|
154
|
+
await tick();
|
|
155
|
+
}
|
|
156
|
+
if (i < lines.length - 1) {
|
|
157
|
+
// Soft-newline: `\` + Enter inserts a newline without submitting.
|
|
158
|
+
pty.sendText('\\');
|
|
159
|
+
await tick();
|
|
160
|
+
pty.sendSpecialKeys('Enter');
|
|
161
|
+
await tick();
|
|
162
|
+
}
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
else {
|
|
166
|
+
// Non-tmux fallback (raw PTY): bracketed paste is reliable here
|
|
167
|
+
// since we control the markers directly — no send-keys -l \n quirk.
|
|
168
|
+
pty.write('\x1b[200~' + content + '\x1b[201~');
|
|
169
|
+
}
|
|
31
170
|
}
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
171
|
+
catch {
|
|
172
|
+
return { submitted: false };
|
|
173
|
+
}
|
|
174
|
+
await delay(submitDelay);
|
|
175
|
+
if (!trySendEnter())
|
|
176
|
+
return { submitted: false };
|
|
177
|
+
// Fresh-install short-wait: when history.jsonl is absent at submit
|
|
178
|
+
// time, give CoCo up to 1.2s to create it. If our marker shows up →
|
|
179
|
+
// success. If the file is still absent → trust the Enter and return
|
|
180
|
+
// (this is the genuine "first run / coco doesn't write history"
|
|
181
|
+
// case). If the file appeared but our marker isn't there → fall
|
|
182
|
+
// through to the normal retry/failure loop — better to warn than to
|
|
183
|
+
// silently mask a real submit failure on a new install.
|
|
184
|
+
if (!existsSync(HISTORY_PATH) && baseByte === 0) {
|
|
185
|
+
if (await waitForHistoryAppend(HISTORY_PATH, baseByte, prefix, 1200)) {
|
|
186
|
+
return undefined;
|
|
187
|
+
}
|
|
188
|
+
if (!existsSync(HISTORY_PATH)) {
|
|
189
|
+
return undefined;
|
|
190
|
+
}
|
|
191
|
+
// File appeared during the wait but our marker isn't in it — fall
|
|
192
|
+
// through to the retry loop. baseByte stays 0 so the loop scans
|
|
193
|
+
// the whole file.
|
|
194
|
+
}
|
|
195
|
+
for (let attempt = 0; attempt < 3; attempt++) {
|
|
196
|
+
if (await waitForHistoryAppend(HISTORY_PATH, baseByte, prefix, 800)) {
|
|
197
|
+
return undefined;
|
|
198
|
+
}
|
|
199
|
+
if (!trySendEnter())
|
|
200
|
+
return { submitted: false };
|
|
201
|
+
}
|
|
202
|
+
if (await waitForHistoryAppend(HISTORY_PATH, baseByte, prefix, 800)) {
|
|
203
|
+
return undefined;
|
|
36
204
|
}
|
|
205
|
+
// In-band budget exhausted. Hand the worker a recheck closure: a slow
|
|
206
|
+
// CoCo (cold start, large initial prompt, heavy hooks) may still
|
|
207
|
+
// append our marker after retries gave up. Worker re-scans after a
|
|
208
|
+
// delay before deciding whether to warn the user.
|
|
209
|
+
const recheck = () => historyDeltaContains(HISTORY_PATH, baseByte, prefix);
|
|
210
|
+
return { submitted: false, recheck };
|
|
37
211
|
},
|
|
38
212
|
completionPattern: undefined,
|
|
39
213
|
// `⏵⏵` only shows when CoCo runs with --yolo (bypass permissions). Adopted
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"coco.js","sourceRoot":"","sources":["../../../src/adapters/cli/coco.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAC/C,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC;AAGvD,SAAS,KAAK,CAAC,EAAU;IACvB,OAAO,IAAI,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC,UAAU,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC,CAAC;AACzD,CAAC;AAED,MAAM,UAAU,iBAAiB,CAAC,YAAqB;IACrD,MAAM,GAAG,GAAG,cAAc,CAAC,YAAY,IAAI,MAAM,CAAC,CAAC;IACnD,OAAO;QACL,EAAE,EAAE,MAAM;QACV,WAAW,EAAE,GAAG;QAEhB,SAAS,CAAC,EAAE,SAAS,EAAE,MAAM,EAAE;YAC7B,MAAM,IAAI,GAAa,EAAE,CAAC;YAC1B,IAAI,MAAM,EAAE,CAAC;gBACX,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE,SAAS,CAAC,CAAC;YACnC,CAAC;iBAAM,CAAC;gBACN,IAAI,CAAC,IAAI,CAAC,cAAc,EAAE,SAAS,CAAC,CAAC;YACvC,CAAC;YACD,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;YACpB,IAAI,CAAC,IAAI,CAAC,mBAAmB,EAAE,eAAe,EAAE,mBAAmB,EAAE,cAAc,CAAC,CAAC;YACrF,OAAO,IAAI,CAAC;QACd,CAAC;QAED,kBAAkB,CAAC,EAAE,SAAS,EAAE;YAC9B,OAAO,iBAAiB,SAAS,EAAE,CAAC;QACtC,CAAC;QAED,KAAK,CAAC,UAAU,CAAC,GAAc,EAAE,OAAe;YAC9C,IAAI,GAAG,CAAC,QAAQ,IAAI,GAAG,CAAC,eAAe,EAAE,CAAC;
|
|
1
|
+
{"version":3,"file":"coco.js","sourceRoot":"","sources":["../../../src/adapters/cli/coco.ts"],"names":[],"mappings":"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"}
|