@pulsehub/runner 0.1.14 → 0.1.15
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 +1 -1
- package/src/runtime.js +11 -2
- package/test/integration.test.js +5 -0
package/package.json
CHANGED
package/src/runtime.js
CHANGED
|
@@ -139,11 +139,12 @@ export async function runOnce(config, options = {}) {
|
|
|
139
139
|
let job;
|
|
140
140
|
let jobPhase = 'poll';
|
|
141
141
|
let completionReported = false;
|
|
142
|
+
let agentActive = false;
|
|
142
143
|
const journal = join(paths().root, 'active-job.json');
|
|
143
144
|
const checkActive = async () => {
|
|
144
145
|
controller.signal.throwIfAborted();
|
|
145
146
|
if (Date.parse(job.expiresAt) <= Date.now()) controller.abort();
|
|
146
|
-
const response = await remote(config, 'pulseRunnerHeartbeat', { status: 'busy', jobId: job.id });
|
|
147
|
+
const response = await remote(config, 'pulseRunnerHeartbeat', { status: 'busy', jobId: job.id, agentActive });
|
|
147
148
|
if (response.cancelRequested) controller.abort();
|
|
148
149
|
controller.signal.throwIfAborted();
|
|
149
150
|
};
|
|
@@ -204,7 +205,15 @@ export async function runOnce(config, options = {}) {
|
|
|
204
205
|
controller.signal.throwIfAborted();
|
|
205
206
|
jobPhase = 'run-agent';
|
|
206
207
|
await logEvent('agent.started', { jobId: job.id, repo: primary.repo, mode: job.mode });
|
|
207
|
-
|
|
208
|
+
agentActive = true;
|
|
209
|
+
let result;
|
|
210
|
+
try {
|
|
211
|
+
await checkActive();
|
|
212
|
+
result = await runAgent(agent.kind, job, primary.worktree, checkouts.filter((entry) => entry !== primary), config, delivery.mcpCredential, temp, { signal: controller.signal, profile, onDiagnostic: ({ event, ...details }) => logEvent(event, { jobId: job.id, ...details }) });
|
|
213
|
+
} finally {
|
|
214
|
+
agentActive = false;
|
|
215
|
+
await remote(config, 'pulseRunnerHeartbeat', { status: 'busy', jobId: job.id, agentActive: false }).catch(() => {});
|
|
216
|
+
}
|
|
208
217
|
controller.signal.throwIfAborted();
|
|
209
218
|
await checkActive();
|
|
210
219
|
await logEvent(result.code === 0 ? 'agent.completed' : 'agent.failed', { jobId: job.id, exitCode: result.code, ...(result.code === 0 ? {} : { error: failureDetail(result.output) }) });
|
package/test/integration.test.js
CHANGED
|
@@ -138,6 +138,10 @@ for (const kind of ['claude','codex']) {
|
|
|
138
138
|
assert.equal(await exists(join(paths().root,'tmp',f.job.id)),false);
|
|
139
139
|
const completion = f.calls.find(c=>c.path==='/pulseRunnerComplete').body;
|
|
140
140
|
assert.equal(completion.outcome,'completed');
|
|
141
|
+
const heartbeats = f.calls.filter(c => c.path === '/pulseRunnerHeartbeat' && c.body.jobId);
|
|
142
|
+
assert.equal(heartbeats[0].body.agentActive, false);
|
|
143
|
+
assert(heartbeats.some(c => c.body.agentActive === true));
|
|
144
|
+
assert.equal(heartbeats.at(-1).body.agentActive, false);
|
|
141
145
|
assert.ok(!JSON.stringify(f.calls).includes('pulse_sk_fixture'));
|
|
142
146
|
}));
|
|
143
147
|
test(`integration: ${kind} missing native session rejects before creating worktrees`, () => fixture(kind, async f => {
|
|
@@ -388,6 +392,7 @@ test('integration: publication failure retains commits and retry does not run th
|
|
|
388
392
|
f.job.publicationTargets=[...f.job.publicationTargets.map(t=>({...t,sha:entry.sha}))];f.signJob();
|
|
389
393
|
await f.run();
|
|
390
394
|
assert.equal(await readFile(f.trace,'utf8'),previousTrace);
|
|
395
|
+
assert(f.calls.filter(c => c.path === '/pulseRunnerHeartbeat' && c.body.jobId).every(c => c.body.agentActive === false));
|
|
391
396
|
const retry=f.calls.find(c=>c.path==='/pulseRunnerComplete').body;
|
|
392
397
|
assert.equal(retry.outcome,'completed');assert.equal(retry.publication.repositories[0].sha,entry.sha);
|
|
393
398
|
assert.equal(retry.publication.repositories[0].stage,'linked');assert.equal(publishCalls,1);
|