botmux 2.36.0 → 2.36.1

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":"cursor.d.ts","sourceRoot":"","sources":["../../../src/adapters/cli/cursor.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAa,MAAM,YAAY,CAAC;AAMxD,wBAAgB,mBAAmB,CAAC,YAAY,CAAC,EAAE,MAAM,GAAG,UAAU,CAgDrE;AAED,eAAO,MAAM,MAAM,4BAAsB,CAAC"}
1
+ {"version":3,"file":"cursor.d.ts","sourceRoot":"","sources":["../../../src/adapters/cli/cursor.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,UAAU,EAAa,MAAM,YAAY,CAAC;AAYxD,wBAAgB,mBAAmB,CAAC,YAAY,CAAC,EAAE,MAAM,GAAG,UAAU,CAuFrE;AAED,eAAO,MAAM,MAAM,4BAAsB,CAAC"}
@@ -3,6 +3,11 @@ import { BOTMUX_SHELL_HINTS } from './shared-hints.js';
3
3
  function delay(ms) {
4
4
  return new Promise(resolve => setTimeout(resolve, ms));
5
5
  }
6
+ /** PTYs that have already received a writeInput. The first write lands while
7
+ * cursor-agent's TUI is still doing its startup render, so it needs a longer
8
+ * settle + throttle than later writes. Tracked by identity so the warmup state
9
+ * is shared across adapter instances. Mirrors claude-code's first-write guard. */
10
+ const cursorFirstWriteSeen = new WeakSet();
6
11
  export function createCursorAdapter(pathOverride) {
7
12
  const bin = resolveCommand(pathOverride ?? 'cursor-agent');
8
13
  return {
@@ -31,20 +36,57 @@ export function createCursorAdapter(pathOverride) {
31
36
  return `cursor-agent --resume ${cliSessionId}`;
32
37
  },
33
38
  async writeInput(pty, content) {
34
- // No on-disk submit verification yet cursor stores transcripts as
35
- // JSONL but the path isn't documented. Treat like aiden: paste the
36
- // text, brief settle, send Enter. Worker still gets quiescence-based
37
- // idle and the bridge fallback timer if the model never replies.
38
- if (pty.sendText && pty.sendSpecialKeys) {
39
- pty.sendText(content);
39
+ // Emit line-by-line instead of writing the whole message at once.
40
+ // cursor-agent's paste detector folds a multi-line chunk that arrives in
41
+ // one burst into a `[Pasted text +N lines]` placeholder the model can't
42
+ // read; typing each line with a throttle between keeps it under that
43
+ // threshold so the text lands verbatim. Covers both backends — tmux
44
+ // (send-keys) and raw PTY (write only). Never use bracketed-paste markers
45
+ // (\x1b[200~ … \x1b[201~): they trigger the fold.
46
+ //
47
+ // Soft-newline differs per backend because the detector counts LF (0x0a)
48
+ // bytes arriving densely:
49
+ // - tmux: Ctrl+J, cursor's native soft-newline — renders cleanly and
50
+ // send-keys spaces the bytes out enough to never fold.
51
+ // - raw PTY: a fast write('\n') folds, so send `\` + CR; cursor eats the
52
+ // backslash-before-CR as a soft-newline (not part of the submitted
53
+ // text) and no LF byte hits the stream, making it fold-immune. Costs a
54
+ // cosmetic trailing `\` in the local TUI render only.
55
+ // Submit is always a bare Enter (\r). No on-disk submit verification —
56
+ // cursor's transcript path isn't documented, so the worker relies on
57
+ // idle detection + the bridge fallback timer.
58
+ const useKeys = !!(pty.sendText && pty.sendSpecialKeys);
59
+ const emitText = (s) => (useKeys ? pty.sendText(s) : pty.write(s));
60
+ const emitSoftNewline = () => {
61
+ if (useKeys) {
62
+ pty.sendSpecialKeys('C-j');
63
+ }
64
+ else {
65
+ pty.write('\\');
66
+ pty.write('\r');
67
+ }
68
+ };
69
+ const emitEnter = () => (useKeys ? pty.sendSpecialKeys('Enter') : pty.write('\r'));
70
+ const isFirstWrite = !cursorFirstWriteSeen.has(pty);
71
+ if (isFirstWrite) {
72
+ cursorFirstWriteSeen.add(pty);
40
73
  await delay(200);
41
- pty.sendSpecialKeys('Enter');
42
74
  }
43
- else {
44
- pty.write(content);
45
- await delay(1000);
46
- pty.write('\r');
75
+ const throttleMs = isFirstWrite ? 80 : 30;
76
+ const tick = () => delay(throttleMs);
77
+ const lines = content.split('\n');
78
+ for (let i = 0; i < lines.length; i++) {
79
+ if (lines[i].length > 0) {
80
+ emitText(lines[i]);
81
+ await tick();
82
+ }
83
+ if (i < lines.length - 1) {
84
+ emitSoftNewline();
85
+ await tick();
86
+ }
47
87
  }
88
+ await delay(200);
89
+ emitEnter();
48
90
  },
49
91
  completionPattern: undefined,
50
92
  skillsDir: '~/.cursor/skills',
@@ -1 +1 @@
1
- {"version":3,"file":"cursor.js","sourceRoot":"","sources":["../../../src/adapters/cli/cursor.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,mBAAmB,CAAC,YAAqB;IACvD,MAAM,GAAG,GAAG,cAAc,CAAC,YAAY,IAAI,cAAc,CAAC,CAAC;IAC3D,OAAO;QACL,EAAE,EAAE,QAAQ;QACZ,WAAW,EAAE,GAAG;QAEhB,SAAS,CAAC,EAAE,MAAM,EAAE,eAAe,EAAE;YACnC,wEAAwE;YACxE,yEAAyE;YACzE,0EAA0E;YAC1E,kCAAkC;YAClC,MAAM,IAAI,GAAG,CAAC,SAAS,CAAC,CAAC;YACzB,IAAI,CAAC,MAAM;gBAAE,OAAO,IAAI,CAAC;YACzB,IAAI,eAAe;gBAAE,OAAO,CAAC,GAAG,IAAI,EAAE,UAAU,EAAE,eAAe,CAAC,CAAC;YACnE,qEAAqE;YACrE,wEAAwE;YACxE,OAAO,CAAC,GAAG,IAAI,EAAE,YAAY,CAAC,CAAC;QACjC,CAAC;QAED,kBAAkB,CAAC,EAAE,YAAY,EAAE;YACjC,wEAAwE;YACxE,4EAA4E;YAC5E,sCAAsC;YACtC,IAAI,CAAC,YAAY;gBAAE,OAAO,IAAI,CAAC;YAC/B,OAAO,yBAAyB,YAAY,EAAE,CAAC;QACjD,CAAC;QAED,KAAK,CAAC,UAAU,CAAC,GAAc,EAAE,OAAe;YAC9C,oEAAoE;YACpE,mEAAmE;YACnE,qEAAqE;YACrE,iEAAiE;YACjE,IAAI,GAAG,CAAC,QAAQ,IAAI,GAAG,CAAC,eAAe,EAAE,CAAC;gBACxC,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;gBACtB,MAAM,KAAK,CAAC,GAAG,CAAC,CAAC;gBACjB,GAAG,CAAC,eAAe,CAAC,OAAO,CAAC,CAAC;YAC/B,CAAC;iBAAM,CAAC;gBACN,GAAG,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;gBACnB,MAAM,KAAK,CAAC,IAAI,CAAC,CAAC;gBAClB,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;YAClB,CAAC;QACH,CAAC;QAED,iBAAiB,EAAE,SAAS;QAC5B,SAAS,EAAE,kBAAkB;QAC7B,WAAW,EAAE,kBAAkB;QAC/B,SAAS,EAAE,IAAI;KAChB,CAAC;AACJ,CAAC;AAED,MAAM,CAAC,MAAM,MAAM,GAAG,mBAAmB,CAAC"}
1
+ {"version":3,"file":"cursor.js","sourceRoot":"","sources":["../../../src/adapters/cli/cursor.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "botmux",
3
- "version": "2.36.0",
3
+ "version": "2.36.1",
4
4
  "description": "Bridge between IM platforms and AI coding CLIs — one topic, one CLI session with live streaming",
5
5
  "type": "module",
6
6
  "main": "dist/index-daemon.js",