@adhdev/daemon-core 0.9.82-rc.334 → 0.9.82-rc.336
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/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@adhdev/daemon-core",
|
|
3
|
-
"version": "0.9.82-rc.
|
|
3
|
+
"version": "0.9.82-rc.336",
|
|
4
4
|
"description": "ADHDev daemon core — CDP, IDE detection, providers, command execution",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -46,7 +46,7 @@
|
|
|
46
46
|
"author": "vilmire",
|
|
47
47
|
"license": "AGPL-3.0-or-later",
|
|
48
48
|
"dependencies": {
|
|
49
|
-
"@adhdev/mesh-shared": "0.9.82-rc.
|
|
49
|
+
"@adhdev/mesh-shared": "0.9.82-rc.336",
|
|
50
50
|
"@adhdev/session-host-core": "*",
|
|
51
51
|
"@agentclientprotocol/sdk": "^0.16.1",
|
|
52
52
|
"ajv": "^8.20.0",
|
|
@@ -118,6 +118,32 @@ export function appendBoundedText(current: string, chunk: string, maxChars: numb
|
|
|
118
118
|
return current.slice(-keepFromCurrent) + chunk;
|
|
119
119
|
}
|
|
120
120
|
|
|
121
|
+
// Force-send (mesh coordinator dispatch / reconcile redelivery) writes raw
|
|
122
|
+
// keystrokes straight into the PTY, bypassing the normal echo-wait submit
|
|
123
|
+
// pipeline.
|
|
124
|
+
//
|
|
125
|
+
// History of this path's failure modes:
|
|
126
|
+
// 1. Originally it wrote `text + sendKey` in a single PTY write with zero
|
|
127
|
+
// settle time. Injected into an idle TUI input box that was still entering
|
|
128
|
+
// its input-accepting state, the trailing submit key could be swallowed —
|
|
129
|
+
// prompt typed but never submitted ("text injected, Enter not pressed").
|
|
130
|
+
// 2. The first fix split inject from submit: write(text) → echo-gated settle →
|
|
131
|
+
// write(sendKey) as a *separate* PTY write. That broke win32: ConPTY/TUI
|
|
132
|
+
// does not recognize a lone '\r' that arrives in its own PTY chunk
|
|
133
|
+
// 150ms+ after the text as a submit key, and the win32 echo gate never
|
|
134
|
+
// matched (ConPTY echo/parsing differences), so the cap was burned and the
|
|
135
|
+
// same detached lone CR was emitted — adding latency while the Enter still
|
|
136
|
+
// got swallowed.
|
|
137
|
+
//
|
|
138
|
+
// Current behavior: keep a fixed settle gap so the input handler is in its
|
|
139
|
+
// input-accepting state, then write `content + sendKey` as a SINGLE atomic PTY
|
|
140
|
+
// write — the same verified mechanism the normal `immediate` submit strategy
|
|
141
|
+
// uses (submitImmediatePrompt). With the Enter in the same write unit as the
|
|
142
|
+
// text, win32 ConPTY always sees it as a submit and the race that the split was
|
|
143
|
+
// trying to solve cannot happen (the Enter can never be separated from the
|
|
144
|
+
// text). FORCE_SUBMIT_SETTLE_MS is that minimum pre-submit gap.
|
|
145
|
+
const FORCE_SUBMIT_SETTLE_MS = 150;
|
|
146
|
+
|
|
121
147
|
// ─── Adapter ────────────────────────────────────────
|
|
122
148
|
|
|
123
149
|
export class ProviderCliAdapter implements CliAdapter {
|
|
@@ -1298,10 +1324,33 @@ export class ProviderCliAdapter implements CliAdapter {
|
|
|
1298
1324
|
return;
|
|
1299
1325
|
}
|
|
1300
1326
|
LOG.info('CLI', `[${this.cliType}] force-sending prompt while status=${this.engine.currentStatus}`);
|
|
1327
|
+
// Settle, then submit atomically. The previous split-write fix
|
|
1328
|
+
// (write text → settle → write a separate '\r') regressed win32:
|
|
1329
|
+
// ConPTY does not treat a lone CR arriving in its own PTY chunk after a
|
|
1330
|
+
// delay as a submit key, so the Enter was swallowed and the prompt sat
|
|
1331
|
+
// typed-but-unsent. Instead, honor a fixed settle gap so the TUI input
|
|
1332
|
+
// handler is in its input-accepting state, then write `content + sendKey`
|
|
1333
|
+
// as ONE PTY write — the same atomic submit the normal `immediate`
|
|
1334
|
+
// strategy uses. Keeping the Enter in the same write unit as the text is
|
|
1335
|
+
// the invariant that makes win32 ConPTY recognize the submit, and it
|
|
1336
|
+
// also makes the original inject↔submit race impossible (the Enter can
|
|
1337
|
+
// never be separated from the text it submits). The settle still guards
|
|
1338
|
+
// the original concern — that a force-dispatch injected into a freshly
|
|
1339
|
+
// idle session lands before the TUI is ready to accept input.
|
|
1340
|
+
await this.waitForForceSubmitSettle();
|
|
1301
1341
|
await this.writeToPty(content + this.sendKey);
|
|
1302
1342
|
this.onStatusChange?.();
|
|
1303
1343
|
}
|
|
1304
1344
|
|
|
1345
|
+
private async waitForForceSubmitSettle(): Promise<void> {
|
|
1346
|
+
// A fixed minimum gap so the input handler is ready to accept the paste.
|
|
1347
|
+
// We deliberately do NOT echo-gate here: the submit key is written in the
|
|
1348
|
+
// same atomic PTY write as the text (forceSendMessage), so there is no
|
|
1349
|
+
// separate Enter that could race the echo, and on win32 the echo gate
|
|
1350
|
+
// never reliably matched anyway.
|
|
1351
|
+
await new Promise<void>(resolve => setTimeout(resolve, FORCE_SUBMIT_SETTLE_MS));
|
|
1352
|
+
}
|
|
1353
|
+
|
|
1305
1354
|
private enqueuePendingOutboundMessage(text: string, reason: string): void {
|
|
1306
1355
|
const content = String(text || '');
|
|
1307
1356
|
const duplicate = this.pendingOutboundQueue.some((message) => message.content === content);
|