@agent-relay/sdk 7.0.0 → 7.1.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 +5 -0
- package/bin/agent-relay-broker-darwin-arm64 +0 -0
- package/bin/agent-relay-broker-darwin-x64 +0 -0
- package/bin/agent-relay-broker-linux-arm64 +0 -0
- package/bin/agent-relay-broker-linux-x64 +0 -0
- package/bin/agent-relay-broker-win32-x64.exe +0 -0
- package/dist/broker-logs.d.ts +80 -0
- package/dist/broker-logs.d.ts.map +1 -0
- package/dist/broker-logs.js +189 -0
- package/dist/broker-logs.js.map +1 -0
- package/dist/client.d.ts +30 -1
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +82 -19
- package/dist/client.js.map +1 -1
- package/dist/event-bus.d.ts +16 -4
- package/dist/event-bus.d.ts.map +1 -1
- package/dist/event-bus.js +8 -0
- package/dist/event-bus.js.map +1 -1
- package/dist/index.d.ts +2 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/lifecycle-hooks.d.ts +4 -3
- package/dist/lifecycle-hooks.d.ts.map +1 -1
- package/dist/lifecycle-hooks.js +2 -2
- package/dist/protocol.d.ts +7 -0
- package/dist/protocol.d.ts.map +1 -1
- package/dist/relay.d.ts +70 -13
- package/dist/relay.d.ts.map +1 -1
- package/dist/relay.js +194 -18
- package/dist/relay.js.map +1 -1
- package/dist/types.d.ts +4 -0
- package/dist/types.d.ts.map +1 -1
- package/dist/workers.d.ts +1 -1
- package/dist/workers.d.ts.map +1 -1
- package/dist/workers.js.map +1 -1
- package/package.json +15 -13
package/README.md
CHANGED
|
@@ -89,6 +89,11 @@ const client = await AgentRelayClient.spawn({
|
|
|
89
89
|
channels: ['general'],
|
|
90
90
|
});
|
|
91
91
|
|
|
92
|
+
const unsubscribeBrokerExit = client.onBrokerExit((info) => {
|
|
93
|
+
console.error('broker exited', info.code, info.signal, info.recentStderr);
|
|
94
|
+
unsubscribeBrokerExit();
|
|
95
|
+
});
|
|
96
|
+
|
|
92
97
|
// Or connect to an already-running broker (reads connection.json)
|
|
93
98
|
// const client = AgentRelayClient.connect({ cwd: '/my/project' });
|
|
94
99
|
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Helpers for the broker's tracing log directory.
|
|
3
|
+
*
|
|
4
|
+
* The Rust broker writes its diagnostic logs to a platform-standard directory
|
|
5
|
+
* with daily rotation (see `crates/broker/src/runtime/util.rs::broker_log_dir`).
|
|
6
|
+
* This module mirrors that path so the TypeScript CLI can list, tail, prune,
|
|
7
|
+
* and clear those files without spawning the broker.
|
|
8
|
+
*/
|
|
9
|
+
export interface BrokerLogFile {
|
|
10
|
+
/** Absolute path to the log file. */
|
|
11
|
+
path: string;
|
|
12
|
+
/** Just the file name, e.g. `myproject.log.2026-05-21`. */
|
|
13
|
+
name: string;
|
|
14
|
+
/** Broker identifier inferred from the filename (the prefix before `.log`). */
|
|
15
|
+
brokerId: string;
|
|
16
|
+
/**
|
|
17
|
+
* The rotation date suffix in `YYYY-MM-DD` form, or `null` for the
|
|
18
|
+
* pre-rotation file laid down before `tracing-appender` rolled over.
|
|
19
|
+
*/
|
|
20
|
+
date: string | null;
|
|
21
|
+
/** File size in bytes. */
|
|
22
|
+
size: number;
|
|
23
|
+
/** Last-modified time. */
|
|
24
|
+
mtime: Date;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Resolve the platform-standard broker log directory. Matches the Rust
|
|
28
|
+
* implementation in `runtime/util.rs::broker_log_dir`.
|
|
29
|
+
*
|
|
30
|
+
* - macOS: `~/Library/Logs/agent-relay`
|
|
31
|
+
* - Linux / other Unix: `$XDG_STATE_HOME/agent-relay/logs` (default
|
|
32
|
+
* `~/.local/state/agent-relay/logs`)
|
|
33
|
+
* - Windows: `%LOCALAPPDATA%\agent-relay\Logs`
|
|
34
|
+
*/
|
|
35
|
+
export declare function getBrokerLogDir(): string;
|
|
36
|
+
/** List all broker log files (current + rotated) in [`getBrokerLogDir`]. */
|
|
37
|
+
export declare function listBrokerLogs(dir?: string): Promise<BrokerLogFile[]>;
|
|
38
|
+
/**
|
|
39
|
+
* Read the last `lines` lines of a broker's log. Picks the most recent file
|
|
40
|
+
* matching `brokerId`. Returns `null` when no log file exists for that id.
|
|
41
|
+
*/
|
|
42
|
+
export declare function tailBrokerLog(brokerId: string, options?: {
|
|
43
|
+
lines?: number;
|
|
44
|
+
dir?: string;
|
|
45
|
+
}): Promise<{
|
|
46
|
+
path: string;
|
|
47
|
+
content: string;
|
|
48
|
+
} | null>;
|
|
49
|
+
export interface PruneBrokerLogsOptions {
|
|
50
|
+
/** Override the log directory. Defaults to [`getBrokerLogDir`]. */
|
|
51
|
+
dir?: string;
|
|
52
|
+
/**
|
|
53
|
+
* Keep rotated files newer than this many days. `0` removes everything
|
|
54
|
+
* except the current (un-suffixed) file. Default: 7.
|
|
55
|
+
*/
|
|
56
|
+
keepDays?: number;
|
|
57
|
+
/** When true, list candidates but don't delete. */
|
|
58
|
+
dryRun?: boolean;
|
|
59
|
+
/** Restrict to a single broker id. */
|
|
60
|
+
brokerId?: string;
|
|
61
|
+
}
|
|
62
|
+
export interface PruneBrokerLogsResult {
|
|
63
|
+
removed: BrokerLogFile[];
|
|
64
|
+
kept: BrokerLogFile[];
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Delete rotated log files older than `keepDays` days. The current
|
|
68
|
+
* un-suffixed file is always kept because `tracing-appender` is writing to it.
|
|
69
|
+
*/
|
|
70
|
+
export declare function pruneBrokerLogs(options?: PruneBrokerLogsOptions): Promise<PruneBrokerLogsResult>;
|
|
71
|
+
export interface ClearBrokerLogsOptions {
|
|
72
|
+
dir?: string;
|
|
73
|
+
/** Restrict to a single broker id. When omitted, removes all log files. */
|
|
74
|
+
brokerId?: string;
|
|
75
|
+
/** When true, list candidates but don't delete. */
|
|
76
|
+
dryRun?: boolean;
|
|
77
|
+
}
|
|
78
|
+
/** Delete every log file (including the current one) matching the filter. */
|
|
79
|
+
export declare function clearBrokerLogs(options?: ClearBrokerLogsOptions): Promise<BrokerLogFile[]>;
|
|
80
|
+
//# sourceMappingURL=broker-logs.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"broker-logs.d.ts","sourceRoot":"","sources":["../src/broker-logs.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAMH,MAAM,WAAW,aAAa;IAC5B,qCAAqC;IACrC,IAAI,EAAE,MAAM,CAAC;IACb,2DAA2D;IAC3D,IAAI,EAAE,MAAM,CAAC;IACb,+EAA+E;IAC/E,QAAQ,EAAE,MAAM,CAAC;IACjB;;;OAGG;IACH,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IACpB,0BAA0B;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,0BAA0B;IAC1B,KAAK,EAAE,IAAI,CAAC;CACb;AAID;;;;;;;;GAQG;AACH,wBAAgB,eAAe,IAAI,MAAM,CAiBxC;AAED,4EAA4E;AAC5E,wBAAsB,cAAc,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC,CAkC3E;AAED;;;GAGG;AACH,wBAAsB,aAAa,CACjC,QAAQ,EAAE,MAAM,EAChB,OAAO,GAAE;IAAE,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,GAAG,CAAC,EAAE,MAAM,CAAA;CAAO,GAC7C,OAAO,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAAC,CAMnD;AAED,MAAM,WAAW,sBAAsB;IACrC,mEAAmE;IACnE,GAAG,CAAC,EAAE,MAAM,CAAC;IACb;;;OAGG;IACH,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,mDAAmD;IACnD,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,sCAAsC;IACtC,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,qBAAqB;IACpC,OAAO,EAAE,aAAa,EAAE,CAAC;IACzB,IAAI,EAAE,aAAa,EAAE,CAAC;CACvB;AAED;;;GAGG;AACH,wBAAsB,eAAe,CAAC,OAAO,GAAE,sBAA2B,GAAG,OAAO,CAAC,qBAAqB,CAAC,CAgC1G;AAED,MAAM,WAAW,sBAAsB;IACrC,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,2EAA2E;IAC3E,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,mDAAmD;IACnD,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,6EAA6E;AAC7E,wBAAsB,eAAe,CAAC,OAAO,GAAE,sBAA2B,GAAG,OAAO,CAAC,aAAa,EAAE,CAAC,CAcpG"}
|
|
@@ -0,0 +1,189 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Helpers for the broker's tracing log directory.
|
|
3
|
+
*
|
|
4
|
+
* The Rust broker writes its diagnostic logs to a platform-standard directory
|
|
5
|
+
* with daily rotation (see `crates/broker/src/runtime/util.rs::broker_log_dir`).
|
|
6
|
+
* This module mirrors that path so the TypeScript CLI can list, tail, prune,
|
|
7
|
+
* and clear those files without spawning the broker.
|
|
8
|
+
*/
|
|
9
|
+
import { homedir, platform } from 'node:os';
|
|
10
|
+
import { join } from 'node:path';
|
|
11
|
+
import { readdir, stat, unlink, open } from 'node:fs/promises';
|
|
12
|
+
const LOG_NAME_PATTERN = /^(?<brokerId>.+)\.log(?:\.(?<date>\d{4}-\d{2}-\d{2}))?$/;
|
|
13
|
+
/**
|
|
14
|
+
* Resolve the platform-standard broker log directory. Matches the Rust
|
|
15
|
+
* implementation in `runtime/util.rs::broker_log_dir`.
|
|
16
|
+
*
|
|
17
|
+
* - macOS: `~/Library/Logs/agent-relay`
|
|
18
|
+
* - Linux / other Unix: `$XDG_STATE_HOME/agent-relay/logs` (default
|
|
19
|
+
* `~/.local/state/agent-relay/logs`)
|
|
20
|
+
* - Windows: `%LOCALAPPDATA%\agent-relay\Logs`
|
|
21
|
+
*/
|
|
22
|
+
export function getBrokerLogDir() {
|
|
23
|
+
const home = homedir();
|
|
24
|
+
switch (platform()) {
|
|
25
|
+
case 'darwin':
|
|
26
|
+
return join(home, 'Library', 'Logs', 'agent-relay');
|
|
27
|
+
case 'win32': {
|
|
28
|
+
const localAppData = process.env.LOCALAPPDATA ?? join(home, 'AppData', 'Local');
|
|
29
|
+
return join(localAppData, 'agent-relay', 'Logs');
|
|
30
|
+
}
|
|
31
|
+
default: {
|
|
32
|
+
const stateHome = process.env.XDG_STATE_HOME && process.env.XDG_STATE_HOME.length > 0
|
|
33
|
+
? process.env.XDG_STATE_HOME
|
|
34
|
+
: join(home, '.local', 'state');
|
|
35
|
+
return join(stateHome, 'agent-relay', 'logs');
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
/** List all broker log files (current + rotated) in [`getBrokerLogDir`]. */
|
|
40
|
+
export async function listBrokerLogs(dir) {
|
|
41
|
+
const logDir = dir ?? getBrokerLogDir();
|
|
42
|
+
let entries;
|
|
43
|
+
try {
|
|
44
|
+
entries = await readdir(logDir);
|
|
45
|
+
}
|
|
46
|
+
catch (err) {
|
|
47
|
+
if (err.code === 'ENOENT')
|
|
48
|
+
return [];
|
|
49
|
+
throw err;
|
|
50
|
+
}
|
|
51
|
+
const files = [];
|
|
52
|
+
for (const name of entries) {
|
|
53
|
+
const match = LOG_NAME_PATTERN.exec(name);
|
|
54
|
+
if (!match || !match.groups)
|
|
55
|
+
continue;
|
|
56
|
+
const fullPath = join(logDir, name);
|
|
57
|
+
let info;
|
|
58
|
+
try {
|
|
59
|
+
info = await stat(fullPath);
|
|
60
|
+
}
|
|
61
|
+
catch {
|
|
62
|
+
continue;
|
|
63
|
+
}
|
|
64
|
+
if (!info.isFile())
|
|
65
|
+
continue;
|
|
66
|
+
files.push({
|
|
67
|
+
path: fullPath,
|
|
68
|
+
name,
|
|
69
|
+
brokerId: match.groups.brokerId,
|
|
70
|
+
date: match.groups.date ?? null,
|
|
71
|
+
size: info.size,
|
|
72
|
+
mtime: info.mtime,
|
|
73
|
+
});
|
|
74
|
+
}
|
|
75
|
+
files.sort((a, b) => b.mtime.getTime() - a.mtime.getTime());
|
|
76
|
+
return files;
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Read the last `lines` lines of a broker's log. Picks the most recent file
|
|
80
|
+
* matching `brokerId`. Returns `null` when no log file exists for that id.
|
|
81
|
+
*/
|
|
82
|
+
export async function tailBrokerLog(brokerId, options = {}) {
|
|
83
|
+
const lines = options.lines ?? 200;
|
|
84
|
+
const files = (await listBrokerLogs(options.dir)).filter((f) => f.brokerId === brokerId);
|
|
85
|
+
if (files.length === 0)
|
|
86
|
+
return null;
|
|
87
|
+
const target = files[0]; // newest first
|
|
88
|
+
return { path: target.path, content: await tailFile(target.path, lines) };
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* Delete rotated log files older than `keepDays` days. The current
|
|
92
|
+
* un-suffixed file is always kept because `tracing-appender` is writing to it.
|
|
93
|
+
*/
|
|
94
|
+
export async function pruneBrokerLogs(options = {}) {
|
|
95
|
+
const keepDays = options.keepDays ?? 7;
|
|
96
|
+
const cutoff = Date.now() - keepDays * 24 * 60 * 60 * 1000;
|
|
97
|
+
const files = await listBrokerLogs(options.dir);
|
|
98
|
+
const removed = [];
|
|
99
|
+
const kept = [];
|
|
100
|
+
for (const file of files) {
|
|
101
|
+
if (options.brokerId && file.brokerId !== options.brokerId) {
|
|
102
|
+
kept.push(file);
|
|
103
|
+
continue;
|
|
104
|
+
}
|
|
105
|
+
// Never delete the current (un-suffixed) file — it's being written to.
|
|
106
|
+
if (file.date === null) {
|
|
107
|
+
kept.push(file);
|
|
108
|
+
continue;
|
|
109
|
+
}
|
|
110
|
+
if (file.mtime.getTime() >= cutoff) {
|
|
111
|
+
kept.push(file);
|
|
112
|
+
continue;
|
|
113
|
+
}
|
|
114
|
+
if (!options.dryRun) {
|
|
115
|
+
try {
|
|
116
|
+
await unlink(file.path);
|
|
117
|
+
}
|
|
118
|
+
catch (err) {
|
|
119
|
+
if (err.code !== 'ENOENT')
|
|
120
|
+
throw err;
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
removed.push(file);
|
|
124
|
+
}
|
|
125
|
+
return { removed, kept };
|
|
126
|
+
}
|
|
127
|
+
/** Delete every log file (including the current one) matching the filter. */
|
|
128
|
+
export async function clearBrokerLogs(options = {}) {
|
|
129
|
+
const files = await listBrokerLogs(options.dir);
|
|
130
|
+
const target = options.brokerId ? files.filter((f) => f.brokerId === options.brokerId) : files;
|
|
131
|
+
if (options.dryRun)
|
|
132
|
+
return target;
|
|
133
|
+
for (const file of target) {
|
|
134
|
+
try {
|
|
135
|
+
await unlink(file.path);
|
|
136
|
+
}
|
|
137
|
+
catch (err) {
|
|
138
|
+
if (err.code !== 'ENOENT')
|
|
139
|
+
throw err;
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
return target;
|
|
143
|
+
}
|
|
144
|
+
async function tailFile(filePath, lines) {
|
|
145
|
+
const CHUNK = 8192;
|
|
146
|
+
let fh;
|
|
147
|
+
try {
|
|
148
|
+
fh = await open(filePath, 'r');
|
|
149
|
+
const { size } = await fh.stat();
|
|
150
|
+
if (size === 0)
|
|
151
|
+
return '';
|
|
152
|
+
if (size <= CHUNK) {
|
|
153
|
+
const buf = Buffer.alloc(size);
|
|
154
|
+
await fh.read(buf, 0, size, 0);
|
|
155
|
+
return tailLines(buf.toString('utf-8'), lines);
|
|
156
|
+
}
|
|
157
|
+
const chunks = [];
|
|
158
|
+
let position = size;
|
|
159
|
+
let newlines = 0;
|
|
160
|
+
while (position > 0 && newlines <= lines) {
|
|
161
|
+
const readSize = Math.min(CHUNK, position);
|
|
162
|
+
position -= readSize;
|
|
163
|
+
const buf = Buffer.alloc(readSize);
|
|
164
|
+
await fh.read(buf, 0, readSize, position);
|
|
165
|
+
chunks.unshift(buf);
|
|
166
|
+
newlines += countNewlines(buf);
|
|
167
|
+
}
|
|
168
|
+
const combined = Buffer.concat(chunks).toString('utf-8');
|
|
169
|
+
return tailLines(combined, lines);
|
|
170
|
+
}
|
|
171
|
+
finally {
|
|
172
|
+
if (fh)
|
|
173
|
+
await fh.close();
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
function tailLines(text, count) {
|
|
177
|
+
const split = text.split('\n');
|
|
178
|
+
if (split.length > 0 && split[split.length - 1] === '')
|
|
179
|
+
split.pop();
|
|
180
|
+
return split.slice(-count).join('\n');
|
|
181
|
+
}
|
|
182
|
+
function countNewlines(buf) {
|
|
183
|
+
let n = 0;
|
|
184
|
+
for (const byte of buf)
|
|
185
|
+
if (byte === 0x0a)
|
|
186
|
+
n++;
|
|
187
|
+
return n;
|
|
188
|
+
}
|
|
189
|
+
//# sourceMappingURL=broker-logs.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"broker-logs.js","sourceRoot":"","sources":["../src/broker-logs.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,SAAS,CAAC;AAC5C,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AACjC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,EAAE,IAAI,EAAmB,MAAM,kBAAkB,CAAC;AAoBhF,MAAM,gBAAgB,GAAG,yDAAyD,CAAC;AAEnF;;;;;;;;GAQG;AACH,MAAM,UAAU,eAAe;IAC7B,MAAM,IAAI,GAAG,OAAO,EAAE,CAAC;IACvB,QAAQ,QAAQ,EAAE,EAAE,CAAC;QACnB,KAAK,QAAQ;YACX,OAAO,IAAI,CAAC,IAAI,EAAE,SAAS,EAAE,MAAM,EAAE,aAAa,CAAC,CAAC;QACtD,KAAK,OAAO,CAAC,CAAC,CAAC;YACb,MAAM,YAAY,GAAG,OAAO,CAAC,GAAG,CAAC,YAAY,IAAI,IAAI,CAAC,IAAI,EAAE,SAAS,EAAE,OAAO,CAAC,CAAC;YAChF,OAAO,IAAI,CAAC,YAAY,EAAE,aAAa,EAAE,MAAM,CAAC,CAAC;QACnD,CAAC;QACD,OAAO,CAAC,CAAC,CAAC;YACR,MAAM,SAAS,GACb,OAAO,CAAC,GAAG,CAAC,cAAc,IAAI,OAAO,CAAC,GAAG,CAAC,cAAc,CAAC,MAAM,GAAG,CAAC;gBACjE,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,cAAc;gBAC5B,CAAC,CAAC,IAAI,CAAC,IAAI,EAAE,QAAQ,EAAE,OAAO,CAAC,CAAC;YACpC,OAAO,IAAI,CAAC,SAAS,EAAE,aAAa,EAAE,MAAM,CAAC,CAAC;QAChD,CAAC;IACH,CAAC;AACH,CAAC;AAED,4EAA4E;AAC5E,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,GAAY;IAC/C,MAAM,MAAM,GAAG,GAAG,IAAI,eAAe,EAAE,CAAC;IACxC,IAAI,OAAiB,CAAC;IACtB,IAAI,CAAC;QACH,OAAO,GAAG,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;IAClC,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,IAAK,GAA6B,CAAC,IAAI,KAAK,QAAQ;YAAE,OAAO,EAAE,CAAC;QAChE,MAAM,GAAG,CAAC;IACZ,CAAC;IAED,MAAM,KAAK,GAAoB,EAAE,CAAC;IAClC,KAAK,MAAM,IAAI,IAAI,OAAO,EAAE,CAAC;QAC3B,MAAM,KAAK,GAAG,gBAAgB,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC1C,IAAI,CAAC,KAAK,IAAI,CAAC,KAAK,CAAC,MAAM;YAAE,SAAS;QACtC,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;QACpC,IAAI,IAAI,CAAC;QACT,IAAI,CAAC;YACH,IAAI,GAAG,MAAM,IAAI,CAAC,QAAQ,CAAC,CAAC;QAC9B,CAAC;QAAC,MAAM,CAAC;YACP,SAAS;QACX,CAAC;QACD,IAAI,CAAC,IAAI,CAAC,MAAM,EAAE;YAAE,SAAS;QAC7B,KAAK,CAAC,IAAI,CAAC;YACT,IAAI,EAAE,QAAQ;YACd,IAAI;YACJ,QAAQ,EAAE,KAAK,CAAC,MAAM,CAAC,QAAQ;YAC/B,IAAI,EAAE,KAAK,CAAC,MAAM,CAAC,IAAI,IAAI,IAAI;YAC/B,IAAI,EAAE,IAAI,CAAC,IAAI;YACf,KAAK,EAAE,IAAI,CAAC,KAAK;SAClB,CAAC,CAAC;IACL,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;IAC5D,OAAO,KAAK,CAAC;AACf,CAAC;AAED;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,aAAa,CACjC,QAAgB,EAChB,UAA4C,EAAE;IAE9C,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,IAAI,GAAG,CAAC;IACnC,MAAM,KAAK,GAAG,CAAC,MAAM,cAAc,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,KAAK,QAAQ,CAAC,CAAC;IACzF,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IACpC,MAAM,MAAM,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,eAAe;IACxC,OAAO,EAAE,IAAI,EAAE,MAAM,CAAC,IAAI,EAAE,OAAO,EAAE,MAAM,QAAQ,CAAC,MAAM,CAAC,IAAI,EAAE,KAAK,CAAC,EAAE,CAAC;AAC5E,CAAC;AAqBD;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,UAAkC,EAAE;IACxE,MAAM,QAAQ,GAAG,OAAO,CAAC,QAAQ,IAAI,CAAC,CAAC;IACvC,MAAM,MAAM,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,QAAQ,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;IAC3D,MAAM,KAAK,GAAG,MAAM,cAAc,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAChD,MAAM,OAAO,GAAoB,EAAE,CAAC;IACpC,MAAM,IAAI,GAAoB,EAAE,CAAC;IAEjC,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,IAAI,OAAO,CAAC,QAAQ,IAAI,IAAI,CAAC,QAAQ,KAAK,OAAO,CAAC,QAAQ,EAAE,CAAC;YAC3D,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAChB,SAAS;QACX,CAAC;QACD,uEAAuE;QACvE,IAAI,IAAI,CAAC,IAAI,KAAK,IAAI,EAAE,CAAC;YACvB,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAChB,SAAS;QACX,CAAC;QACD,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,IAAI,MAAM,EAAE,CAAC;YACnC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAChB,SAAS;QACX,CAAC;QACD,IAAI,CAAC,OAAO,CAAC,MAAM,EAAE,CAAC;YACpB,IAAI,CAAC;gBACH,MAAM,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAC1B,CAAC;YAAC,OAAO,GAAG,EAAE,CAAC;gBACb,IAAK,GAA6B,CAAC,IAAI,KAAK,QAAQ;oBAAE,MAAM,GAAG,CAAC;YAClE,CAAC;QACH,CAAC;QACD,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACrB,CAAC;IAED,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;AAC3B,CAAC;AAUD,6EAA6E;AAC7E,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,UAAkC,EAAE;IACxE,MAAM,KAAK,GAAG,MAAM,cAAc,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAChD,MAAM,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,KAAK,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC;IAE/F,IAAI,OAAO,CAAC,MAAM;QAAE,OAAO,MAAM,CAAC;IAElC,KAAK,MAAM,IAAI,IAAI,MAAM,EAAE,CAAC;QAC1B,IAAI,CAAC;YACH,MAAM,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC1B,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,IAAK,GAA6B,CAAC,IAAI,KAAK,QAAQ;gBAAE,MAAM,GAAG,CAAC;QAClE,CAAC;IACH,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,KAAK,UAAU,QAAQ,CAAC,QAAgB,EAAE,KAAa;IACrD,MAAM,KAAK,GAAG,IAAI,CAAC;IACnB,IAAI,EAA0B,CAAC;IAC/B,IAAI,CAAC;QACH,EAAE,GAAG,MAAM,IAAI,CAAC,QAAQ,EAAE,GAAG,CAAC,CAAC;QAC/B,MAAM,EAAE,IAAI,EAAE,GAAG,MAAM,EAAE,CAAC,IAAI,EAAE,CAAC;QACjC,IAAI,IAAI,KAAK,CAAC;YAAE,OAAO,EAAE,CAAC;QAE1B,IAAI,IAAI,IAAI,KAAK,EAAE,CAAC;YAClB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;YAC/B,MAAM,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;YAC/B,OAAO,SAAS,CAAC,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE,KAAK,CAAC,CAAC;QACjD,CAAC;QAED,MAAM,MAAM,GAAa,EAAE,CAAC;QAC5B,IAAI,QAAQ,GAAG,IAAI,CAAC;QACpB,IAAI,QAAQ,GAAG,CAAC,CAAC;QACjB,OAAO,QAAQ,GAAG,CAAC,IAAI,QAAQ,IAAI,KAAK,EAAE,CAAC;YACzC,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,CAAC,KAAK,EAAE,QAAQ,CAAC,CAAC;YAC3C,QAAQ,IAAI,QAAQ,CAAC;YACrB,MAAM,GAAG,GAAG,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;YACnC,MAAM,EAAE,CAAC,IAAI,CAAC,GAAG,EAAE,CAAC,EAAE,QAAQ,EAAE,QAAQ,CAAC,CAAC;YAC1C,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;YACpB,QAAQ,IAAI,aAAa,CAAC,GAAG,CAAC,CAAC;QACjC,CAAC;QACD,MAAM,QAAQ,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;QACzD,OAAO,SAAS,CAAC,QAAQ,EAAE,KAAK,CAAC,CAAC;IACpC,CAAC;YAAS,CAAC;QACT,IAAI,EAAE;YAAE,MAAM,EAAE,CAAC,KAAK,EAAE,CAAC;IAC3B,CAAC;AACH,CAAC;AAED,SAAS,SAAS,CAAC,IAAY,EAAE,KAAa;IAC5C,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;IAC/B,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,IAAI,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,KAAK,EAAE;QAAE,KAAK,CAAC,GAAG,EAAE,CAAC;IACpE,OAAO,KAAK,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AACxC,CAAC;AAED,SAAS,aAAa,CAAC,GAAW;IAChC,IAAI,CAAC,GAAG,CAAC,CAAC;IACV,KAAK,MAAM,IAAI,IAAI,GAAG;QAAE,IAAI,IAAI,KAAK,IAAI;YAAE,CAAC,EAAE,CAAC;IAC/C,OAAO,CAAC,CAAC;AACX,CAAC"}
|
package/dist/client.d.ts
CHANGED
|
@@ -14,7 +14,7 @@ import { type PtyInputStream, type PtyInputStreamOptions } from './transport.js'
|
|
|
14
14
|
import type { AgentRuntime, BrokerEvent, BrokerStats, BrokerStatus, CrashInsightsResponse, PendingRelayMessage, PtySnapshot, InboundDeliveryMode, SnapshotFormat } from './protocol.js';
|
|
15
15
|
import type { SpawnHeadlessInput, SpawnPtyInput, SpawnProviderInput, SendMessageInput, ListAgent } from './types.js';
|
|
16
16
|
import { EventBus } from './event-bus.js';
|
|
17
|
-
import type { AgentRelayEvents } from './lifecycle-hooks.js';
|
|
17
|
+
import type { AgentRelayEvents, BeforeAgentSpawnHandler } from './lifecycle-hooks.js';
|
|
18
18
|
export interface AgentRelayClientOptions {
|
|
19
19
|
baseUrl: string;
|
|
20
20
|
apiKey?: string;
|
|
@@ -31,6 +31,16 @@ export interface AgentRelayClientOptions {
|
|
|
31
31
|
*/
|
|
32
32
|
eventBus?: EventBus<AgentRelayEvents>;
|
|
33
33
|
}
|
|
34
|
+
export interface BrokerExitInfo {
|
|
35
|
+
/** Exit code, or null when the process was killed by signal. */
|
|
36
|
+
code: number | null;
|
|
37
|
+
/** Terminating signal, or null when the process exited normally. */
|
|
38
|
+
signal: NodeJS.Signals | null;
|
|
39
|
+
/** PID of the managed broker process that exited. */
|
|
40
|
+
pid: number | undefined;
|
|
41
|
+
/** Recent stderr lines captured from the managed broker process. */
|
|
42
|
+
recentStderr: string[];
|
|
43
|
+
}
|
|
34
44
|
export interface AgentRelayBrokerInitArgs {
|
|
35
45
|
/** Optional HTTP API port for dashboard proxy (0 = disabled). */
|
|
36
46
|
apiPort?: number;
|
|
@@ -81,12 +91,15 @@ export interface WorkerStreamSubscriptionOptions {
|
|
|
81
91
|
/** Sequence offset to pass to the broker event stream when connecting. */
|
|
82
92
|
sinceSeq?: number;
|
|
83
93
|
}
|
|
94
|
+
type BrokerExitListener = (info: BrokerExitInfo) => void;
|
|
84
95
|
export declare class AgentRelayClient {
|
|
85
96
|
private readonly transport;
|
|
86
97
|
/** Set after spawn() — the managed child process. */
|
|
87
98
|
private child;
|
|
88
99
|
/** Lease renewal timer (only for spawned brokers). */
|
|
89
100
|
private leaseTimer;
|
|
101
|
+
private brokerExitInfo;
|
|
102
|
+
private brokerExitListeners;
|
|
90
103
|
workspaceKey?: string;
|
|
91
104
|
/** Resolved broker URL — captured so call-site lifecycle contexts can surface it. */
|
|
92
105
|
readonly baseUrl: string;
|
|
@@ -98,9 +111,16 @@ export declare class AgentRelayClient {
|
|
|
98
111
|
* function. Equivalent to `client.eventBus.addListener(...)` but mirrors
|
|
99
112
|
* the `AgentRelay` facade API so direct-client callers don't need to
|
|
100
113
|
* reach through `.eventBus`.
|
|
114
|
+
*
|
|
115
|
+
* `beforeAgentSpawn` is the one event whose handler may return a
|
|
116
|
+
* `SpawnPatch` to mutate the spawn input — the dedicated overload
|
|
117
|
+
* keeps that contract type-safe without forcing other events to accept
|
|
118
|
+
* non-void returns.
|
|
101
119
|
*/
|
|
120
|
+
addListener(event: 'beforeAgentSpawn', handler: BeforeAgentSpawnHandler): () => void;
|
|
102
121
|
addListener<K extends keyof AgentRelayEvents>(event: K, handler: (...args: AgentRelayEvents[K]) => void | Promise<void>): () => void;
|
|
103
122
|
/** Remove a previously-registered listener. */
|
|
123
|
+
removeListener(event: 'beforeAgentSpawn', handler: BeforeAgentSpawnHandler): void;
|
|
104
124
|
removeListener<K extends keyof AgentRelayEvents>(event: K, handler: (...args: AgentRelayEvents[K]) => void | Promise<void>): void;
|
|
105
125
|
/**
|
|
106
126
|
* Fold `beforeAgentSpawn` patches into the input. Listeners run in
|
|
@@ -143,6 +163,13 @@ export declare class AgentRelayClient {
|
|
|
143
163
|
connectEvents(sinceSeq?: number): void;
|
|
144
164
|
disconnectEvents(): void;
|
|
145
165
|
onEvent(listener: (event: BrokerEvent) => void): () => void;
|
|
166
|
+
/**
|
|
167
|
+
* Subscribe to managed broker child-process exit.
|
|
168
|
+
*
|
|
169
|
+
* Clients created with `new AgentRelayClient(...)` or `connect()` do not own a
|
|
170
|
+
* broker child process, so this is a no-op for them.
|
|
171
|
+
*/
|
|
172
|
+
onBrokerExit(listener: BrokerExitListener): () => void;
|
|
146
173
|
queryEvents(filter?: {
|
|
147
174
|
kind?: string;
|
|
148
175
|
name?: string;
|
|
@@ -239,6 +266,8 @@ export declare class AgentRelayClient {
|
|
|
239
266
|
getConfig(): Promise<{
|
|
240
267
|
workspaceKey?: string;
|
|
241
268
|
}>;
|
|
269
|
+
private notifyBrokerExit;
|
|
270
|
+
private installManagedBrokerExitHandler;
|
|
242
271
|
}
|
|
243
272
|
declare function drainBrokerStdioAfterStartup(child: ChildProcess): void;
|
|
244
273
|
/** @internal Test-only hooks; not part of the public SDK API. */
|
package/dist/client.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,OAAO,EAAS,KAAK,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAI9D,OAAO,EAGL,KAAK,cAAc,EACnB,KAAK,qBAAqB,EAC3B,MAAM,gBAAgB,CAAC;AAExB,OAAO,KAAK,EACV,YAAY,EACZ,WAAW,EACX,WAAW,EACX,YAAY,EACZ,qBAAqB,EAErB,mBAAmB,EACnB,WAAW,EACX,mBAAmB,EACnB,cAAc,EACf,MAAM,eAAe,CAAC;AACvB,OAAO,KAAK,EAEV,kBAAkB,EAClB,aAAa,EACb,kBAAkB,EAClB,gBAAgB,EAChB,SAAS,EACV,MAAM,YAAY,CAAC;AACpB,OAAO,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAC1C,OAAO,KAAK,EAGV,gBAAgB,
|
|
1
|
+
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
|
package/dist/client.js
CHANGED
|
@@ -44,6 +44,7 @@ function buildSpawnPtyBody(input) {
|
|
|
44
44
|
...(input.idleThresholdSecs !== undefined ? { idleThresholdSecs: input.idleThresholdSecs } : {}),
|
|
45
45
|
...(input.restartPolicy !== undefined ? { restartPolicy: input.restartPolicy } : {}),
|
|
46
46
|
...(input.skipRelayPrompt !== undefined ? { skipRelayPrompt: input.skipRelayPrompt } : {}),
|
|
47
|
+
...(input.agentResultSchema !== undefined ? { agentResultSchema: input.agentResultSchema } : {}),
|
|
47
48
|
};
|
|
48
49
|
}
|
|
49
50
|
function buildSpawnProviderBody(input, transport) {
|
|
@@ -63,6 +64,7 @@ function buildSpawnProviderBody(input, transport) {
|
|
|
63
64
|
...(input.idleThresholdSecs !== undefined ? { idleThresholdSecs: input.idleThresholdSecs } : {}),
|
|
64
65
|
...(input.restartPolicy !== undefined ? { restartPolicy: input.restartPolicy } : {}),
|
|
65
66
|
...(input.skipRelayPrompt !== undefined ? { skipRelayPrompt: input.skipRelayPrompt } : {}),
|
|
67
|
+
...(input.agentResultSchema !== undefined ? { agentResultSchema: input.agentResultSchema } : {}),
|
|
66
68
|
transport,
|
|
67
69
|
};
|
|
68
70
|
}
|
|
@@ -104,6 +106,8 @@ export class AgentRelayClient {
|
|
|
104
106
|
child = null;
|
|
105
107
|
/** Lease renewal timer (only for spawned brokers). */
|
|
106
108
|
leaseTimer = null;
|
|
109
|
+
brokerExitInfo = null;
|
|
110
|
+
brokerExitListeners = new Set();
|
|
107
111
|
workspaceKey;
|
|
108
112
|
/** Resolved broker URL — captured so call-site lifecycle contexts can surface it. */
|
|
109
113
|
baseUrl;
|
|
@@ -119,16 +123,9 @@ export class AgentRelayClient {
|
|
|
119
123
|
requestTimeoutMs: options.requestTimeoutMs,
|
|
120
124
|
});
|
|
121
125
|
}
|
|
122
|
-
/**
|
|
123
|
-
* Register a listener on the client's event bus. Returns an unsubscribe
|
|
124
|
-
* function. Equivalent to `client.eventBus.addListener(...)` but mirrors
|
|
125
|
-
* the `AgentRelay` facade API so direct-client callers don't need to
|
|
126
|
-
* reach through `.eventBus`.
|
|
127
|
-
*/
|
|
128
126
|
addListener(event, handler) {
|
|
129
127
|
return this.eventBus.addListener(event, handler);
|
|
130
128
|
}
|
|
131
|
-
/** Remove a previously-registered listener. */
|
|
132
129
|
removeListener(event, handler) {
|
|
133
130
|
this.eventBus.removeListener(event, handler);
|
|
134
131
|
}
|
|
@@ -252,6 +249,7 @@ export class AgentRelayClient {
|
|
|
252
249
|
...(options?.eventBus ? { eventBus: options.eventBus } : {}),
|
|
253
250
|
});
|
|
254
251
|
client.child = child;
|
|
252
|
+
client.installManagedBrokerExitHandler(child, stderrLines);
|
|
255
253
|
// The broker prints "API listening on …" the moment its TCP listener is
|
|
256
254
|
// bound, but it still needs to complete a Relaycast handshake before
|
|
257
255
|
// `getSession()` will return. Two failure modes to handle:
|
|
@@ -288,18 +286,13 @@ export class AgentRelayClient {
|
|
|
288
286
|
await new Promise((resolve) => setTimeout(resolve, 1000));
|
|
289
287
|
}
|
|
290
288
|
}
|
|
291
|
-
client.
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
client.
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
if (client.leaseTimer) {
|
|
299
|
-
clearInterval(client.leaseTimer);
|
|
300
|
-
client.leaseTimer = null;
|
|
301
|
-
}
|
|
302
|
-
});
|
|
289
|
+
if (!client.brokerExitInfo) {
|
|
290
|
+
client.connectEvents();
|
|
291
|
+
// Renew the owner lease so the broker doesn't auto-shutdown
|
|
292
|
+
client.leaseTimer = setInterval(() => {
|
|
293
|
+
client.renewLease().catch(() => { });
|
|
294
|
+
}, 60_000);
|
|
295
|
+
}
|
|
303
296
|
return client;
|
|
304
297
|
}
|
|
305
298
|
/** PID of the managed broker process, if spawned locally. */
|
|
@@ -325,6 +318,34 @@ export class AgentRelayClient {
|
|
|
325
318
|
onEvent(listener) {
|
|
326
319
|
return this.transport.onEvent(listener);
|
|
327
320
|
}
|
|
321
|
+
/**
|
|
322
|
+
* Subscribe to managed broker child-process exit.
|
|
323
|
+
*
|
|
324
|
+
* Clients created with `new AgentRelayClient(...)` or `connect()` do not own a
|
|
325
|
+
* broker child process, so this is a no-op for them.
|
|
326
|
+
*/
|
|
327
|
+
onBrokerExit(listener) {
|
|
328
|
+
if (!this.child && !this.brokerExitInfo) {
|
|
329
|
+
return () => { };
|
|
330
|
+
}
|
|
331
|
+
this.brokerExitListeners.add(listener);
|
|
332
|
+
if (this.brokerExitInfo) {
|
|
333
|
+
const info = cloneBrokerExitInfo(this.brokerExitInfo);
|
|
334
|
+
queueMicrotask(() => {
|
|
335
|
+
if (this.brokerExitListeners.has(listener)) {
|
|
336
|
+
try {
|
|
337
|
+
listener(info);
|
|
338
|
+
}
|
|
339
|
+
catch {
|
|
340
|
+
// Listener failures should not interfere with SDK cleanup.
|
|
341
|
+
}
|
|
342
|
+
}
|
|
343
|
+
});
|
|
344
|
+
}
|
|
345
|
+
return () => {
|
|
346
|
+
this.brokerExitListeners.delete(listener);
|
|
347
|
+
};
|
|
348
|
+
}
|
|
328
349
|
queryEvents(filter) {
|
|
329
350
|
return this.transport.queryEvents(filter);
|
|
330
351
|
}
|
|
@@ -650,6 +671,42 @@ export class AgentRelayClient {
|
|
|
650
671
|
async getConfig() {
|
|
651
672
|
return this.transport.request('/api/config');
|
|
652
673
|
}
|
|
674
|
+
notifyBrokerExit(info) {
|
|
675
|
+
if (this.brokerExitInfo)
|
|
676
|
+
return;
|
|
677
|
+
this.brokerExitInfo = cloneBrokerExitInfo(info);
|
|
678
|
+
for (const listener of this.brokerExitListeners) {
|
|
679
|
+
try {
|
|
680
|
+
listener(cloneBrokerExitInfo(info));
|
|
681
|
+
}
|
|
682
|
+
catch {
|
|
683
|
+
// Listener failures should not interfere with SDK cleanup.
|
|
684
|
+
}
|
|
685
|
+
}
|
|
686
|
+
}
|
|
687
|
+
installManagedBrokerExitHandler(child, stderrLines) {
|
|
688
|
+
const handleExit = (code, signal) => {
|
|
689
|
+
this.notifyBrokerExit({
|
|
690
|
+
code,
|
|
691
|
+
signal,
|
|
692
|
+
pid: child.pid,
|
|
693
|
+
recentStderr: [...stderrLines],
|
|
694
|
+
});
|
|
695
|
+
this.disconnectEvents();
|
|
696
|
+
if (this.leaseTimer) {
|
|
697
|
+
clearInterval(this.leaseTimer);
|
|
698
|
+
this.leaseTimer = null;
|
|
699
|
+
}
|
|
700
|
+
if (this.child === child) {
|
|
701
|
+
this.child = null;
|
|
702
|
+
}
|
|
703
|
+
};
|
|
704
|
+
if (child.exitCode !== null || child.signalCode !== null) {
|
|
705
|
+
handleExit(child.exitCode, child.signalCode);
|
|
706
|
+
return;
|
|
707
|
+
}
|
|
708
|
+
child.once('exit', handleExit);
|
|
709
|
+
}
|
|
653
710
|
}
|
|
654
711
|
// ── Helpers ──────────────────────────────────────────────────────────────
|
|
655
712
|
/**
|
|
@@ -727,6 +784,12 @@ function pushBufferedLine(lines, line) {
|
|
|
727
784
|
lines.splice(0, lines.length - 40);
|
|
728
785
|
}
|
|
729
786
|
}
|
|
787
|
+
function cloneBrokerExitInfo(info) {
|
|
788
|
+
return {
|
|
789
|
+
...info,
|
|
790
|
+
recentStderr: [...info.recentStderr],
|
|
791
|
+
};
|
|
792
|
+
}
|
|
730
793
|
function formatBrokerStartupError(message, child, debug) {
|
|
731
794
|
const details = [
|
|
732
795
|
`pid=${child.pid ?? 'unknown'}`,
|