crewly 1.20.294 → 1.20.296
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/config/skills/_common/lib.sh +6 -0
- package/config/skills/agent/core/complete-task/SKILL.md +4 -2
- package/config/skills/agent/core/complete-task/execute.sh +7 -0
- package/config/skills/agent/core/complete-task/explicit-id.test.sh +56 -0
- package/config/skills/agent/core/poll-tasks/execute.sh +13 -1
- package/config/skills/agent/core/poll-tasks/execute.test.sh +37 -0
- package/config/skills/team-leader/delegate-task/execute.sh +13 -2
- package/config/skills/team-leader/verify-output/SKILL.md +9 -0
- package/dist/backend/backend/src/constants.d.ts +16 -2
- package/dist/backend/backend/src/constants.d.ts.map +1 -1
- package/dist/backend/backend/src/constants.js +16 -2
- package/dist/backend/backend/src/constants.js.map +1 -1
- package/dist/backend/backend/src/controllers/monitoring/terminal.controller.d.ts.map +1 -1
- package/dist/backend/backend/src/controllers/monitoring/terminal.controller.js +28 -8
- package/dist/backend/backend/src/controllers/monitoring/terminal.controller.js.map +1 -1
- package/dist/backend/backend/src/controllers/slack/slack.controller.d.ts.map +1 -1
- package/dist/backend/backend/src/controllers/slack/slack.controller.js +28 -1
- package/dist/backend/backend/src/controllers/slack/slack.controller.js.map +1 -1
- package/dist/backend/backend/src/controllers/team/team.controller.d.ts +1 -0
- package/dist/backend/backend/src/controllers/team/team.controller.d.ts.map +1 -1
- package/dist/backend/backend/src/controllers/team/team.controller.js +5 -1
- package/dist/backend/backend/src/controllers/team/team.controller.js.map +1 -1
- package/dist/backend/backend/src/index.d.ts.map +1 -1
- package/dist/backend/backend/src/index.js +44 -6
- package/dist/backend/backend/src/index.js.map +1 -1
- package/dist/backend/backend/src/services/agent/resource-mode.service.d.ts +1 -0
- package/dist/backend/backend/src/services/agent/resource-mode.service.d.ts.map +1 -1
- package/dist/backend/backend/src/services/agent/resource-mode.service.js +4 -3
- package/dist/backend/backend/src/services/agent/resource-mode.service.js.map +1 -1
- package/dist/backend/backend/src/services/chat-v2/chat-v2.dispatcher.service.d.ts +52 -1
- package/dist/backend/backend/src/services/chat-v2/chat-v2.dispatcher.service.d.ts.map +1 -1
- package/dist/backend/backend/src/services/chat-v2/chat-v2.dispatcher.service.js +101 -29
- package/dist/backend/backend/src/services/chat-v2/chat-v2.dispatcher.service.js.map +1 -1
- package/dist/backend/backend/src/services/messaging/deferred-start-retry.d.ts +45 -0
- package/dist/backend/backend/src/services/messaging/deferred-start-retry.d.ts.map +1 -0
- package/dist/backend/backend/src/services/messaging/deferred-start-retry.js +70 -0
- package/dist/backend/backend/src/services/messaging/deferred-start-retry.js.map +1 -0
- package/dist/backend/backend/src/services/messaging/sub-agent-message-queue.service.d.ts +18 -4
- package/dist/backend/backend/src/services/messaging/sub-agent-message-queue.service.d.ts.map +1 -1
- package/dist/backend/backend/src/services/messaging/sub-agent-message-queue.service.js +36 -8
- package/dist/backend/backend/src/services/messaging/sub-agent-message-queue.service.js.map +1 -1
- package/dist/backend/backend/src/services/orc/reply-destination-resolver.d.ts +6 -0
- package/dist/backend/backend/src/services/orc/reply-destination-resolver.d.ts.map +1 -1
- package/dist/backend/backend/src/services/orc/reply-destination-resolver.js +18 -0
- package/dist/backend/backend/src/services/orc/reply-destination-resolver.js.map +1 -1
- package/dist/backend/backend/src/services/orc/reply-destination.wiring.d.ts +2 -0
- package/dist/backend/backend/src/services/orc/reply-destination.wiring.d.ts.map +1 -1
- package/dist/backend/backend/src/services/orc/reply-destination.wiring.js +81 -8
- package/dist/backend/backend/src/services/orc/reply-destination.wiring.js.map +1 -1
- package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.d.ts +8 -0
- package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.d.ts.map +1 -1
- package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.js +22 -0
- package/dist/backend/backend/src/services/project-tickets/project-ticket-workflow.service.js.map +1 -1
- package/dist/backend/backend/src/services/session/session-command-helper.d.ts +17 -0
- package/dist/backend/backend/src/services/session/session-command-helper.d.ts.map +1 -1
- package/dist/backend/backend/src/services/session/session-command-helper.js +32 -0
- package/dist/backend/backend/src/services/session/session-command-helper.js.map +1 -1
- package/dist/backend/backend/src/services/slack/orc-owner-dm-target.d.ts +27 -0
- package/dist/backend/backend/src/services/slack/orc-owner-dm-target.d.ts.map +1 -0
- package/dist/backend/backend/src/services/slack/orc-owner-dm-target.js +48 -0
- package/dist/backend/backend/src/services/slack/orc-owner-dm-target.js.map +1 -0
- package/dist/backend/backend/src/services/slack/slack-agent-dm.service.js +1 -1
- package/dist/backend/backend/src/services/slack/slack-agent-dm.service.js.map +1 -1
- package/dist/backend/backend/src/services/slack/slack-team-channel.service.d.ts.map +1 -1
- package/dist/backend/backend/src/services/slack/slack-team-channel.service.js +13 -1
- package/dist/backend/backend/src/services/slack/slack-team-channel.service.js.map +1 -1
- package/dist/backend/backend/src/services/slack/slack-typing-placeholder.service.d.ts +3 -2
- package/dist/backend/backend/src/services/slack/slack-typing-placeholder.service.d.ts.map +1 -1
- package/dist/backend/backend/src/services/slack/slack-typing-placeholder.service.js +8 -2
- package/dist/backend/backend/src/services/slack/slack-typing-placeholder.service.js.map +1 -1
- package/dist/backend/backend/src/services/task-pool/pool-archive-migration.d.ts +18 -0
- package/dist/backend/backend/src/services/task-pool/pool-archive-migration.d.ts.map +1 -1
- package/dist/backend/backend/src/services/task-pool/pool-archive-migration.js +9 -3
- package/dist/backend/backend/src/services/task-pool/pool-archive-migration.js.map +1 -1
- package/dist/backend/backend/src/services/task-pool/pool-prune.d.ts +76 -0
- package/dist/backend/backend/src/services/task-pool/pool-prune.d.ts.map +1 -0
- package/dist/backend/backend/src/services/task-pool/pool-prune.js +129 -0
- package/dist/backend/backend/src/services/task-pool/pool-prune.js.map +1 -0
- package/dist/backend/backend/src/services/task-pool/pool-storage.d.ts +9 -1
- package/dist/backend/backend/src/services/task-pool/pool-storage.d.ts.map +1 -1
- package/dist/backend/backend/src/services/task-pool/pool-storage.js +34 -3
- package/dist/backend/backend/src/services/task-pool/pool-storage.js.map +1 -1
- package/dist/backend/backend/src/utils/screen-excerpt.d.ts +34 -0
- package/dist/backend/backend/src/utils/screen-excerpt.d.ts.map +1 -0
- package/dist/backend/backend/src/utils/screen-excerpt.js +56 -0
- package/dist/backend/backend/src/utils/screen-excerpt.js.map +1 -0
- package/dist/backend/build-info.json +2 -2
- package/dist/cli/backend/src/constants.d.ts +16 -2
- package/dist/cli/backend/src/constants.d.ts.map +1 -1
- package/dist/cli/backend/src/constants.js +16 -2
- package/dist/cli/backend/src/constants.js.map +1 -1
- package/dist/cli/backend/src/services/agent/resource-mode.service.d.ts +1 -0
- package/dist/cli/backend/src/services/agent/resource-mode.service.d.ts.map +1 -1
- package/dist/cli/backend/src/services/agent/resource-mode.service.js +4 -3
- package/dist/cli/backend/src/services/agent/resource-mode.service.js.map +1 -1
- package/dist/cli/backend/src/services/chat-v2/chat-v2.dispatcher.service.d.ts +52 -1
- package/dist/cli/backend/src/services/chat-v2/chat-v2.dispatcher.service.d.ts.map +1 -1
- package/dist/cli/backend/src/services/chat-v2/chat-v2.dispatcher.service.js +101 -29
- package/dist/cli/backend/src/services/chat-v2/chat-v2.dispatcher.service.js.map +1 -1
- package/dist/cli/backend/src/services/messaging/sub-agent-message-queue.service.d.ts +18 -4
- package/dist/cli/backend/src/services/messaging/sub-agent-message-queue.service.d.ts.map +1 -1
- package/dist/cli/backend/src/services/messaging/sub-agent-message-queue.service.js +36 -8
- package/dist/cli/backend/src/services/messaging/sub-agent-message-queue.service.js.map +1 -1
- package/dist/cli/backend/src/services/session/session-command-helper.d.ts +17 -0
- package/dist/cli/backend/src/services/session/session-command-helper.d.ts.map +1 -1
- package/dist/cli/backend/src/services/session/session-command-helper.js +32 -0
- package/dist/cli/backend/src/services/session/session-command-helper.js.map +1 -1
- package/dist/cli/backend/src/services/slack/slack-agent-dm.service.js +1 -1
- package/dist/cli/backend/src/services/slack/slack-agent-dm.service.js.map +1 -1
- package/dist/cli/backend/src/services/slack/slack-team-channel.service.d.ts.map +1 -1
- package/dist/cli/backend/src/services/slack/slack-team-channel.service.js +13 -1
- package/dist/cli/backend/src/services/slack/slack-team-channel.service.js.map +1 -1
- package/dist/cli/backend/src/services/slack/slack-typing-placeholder.service.d.ts +3 -2
- package/dist/cli/backend/src/services/slack/slack-typing-placeholder.service.d.ts.map +1 -1
- package/dist/cli/backend/src/services/slack/slack-typing-placeholder.service.js +8 -2
- package/dist/cli/backend/src/services/slack/slack-typing-placeholder.service.js.map +1 -1
- package/dist/cli/backend/src/services/task-pool/pool-storage.d.ts +9 -1
- package/dist/cli/backend/src/services/task-pool/pool-storage.d.ts.map +1 -1
- package/dist/cli/backend/src/services/task-pool/pool-storage.js +34 -3
- package/dist/cli/backend/src/services/task-pool/pool-storage.js.map +1 -1
- package/dist/cli/backend/src/utils/screen-excerpt.d.ts +34 -0
- package/dist/cli/backend/src/utils/screen-excerpt.d.ts.map +1 -0
- package/dist/cli/backend/src/utils/screen-excerpt.js +56 -0
- package/dist/cli/backend/src/utils/screen-excerpt.js.map +1 -0
- package/package.json +1 -1
|
@@ -77,7 +77,7 @@ import { parseSlackThreadKey } from './services/slack/slack-thread-key.js';
|
|
|
77
77
|
import { LIVENESS_MONITOR_CONSTANTS, INPUT_CIRCUIT_CONSTANTS, INPUT_BLOCKED_RETRY_CONSTANTS } from './constants.js';
|
|
78
78
|
import { InputBlockedRetryService } from './services/messaging/input-blocked-retry.service.js';
|
|
79
79
|
import { driveCapabilities } from './services/drive/drive-agent.service.js';
|
|
80
|
-
import { SUB_AGENT_QUEUE_CONSTANTS, CHAT_CONTEXT_CONSTANTS, SAFE_RESTART, AUTO_UPDATE_CONSTANTS, PROCESS_EXIT_CODES, CLAUDE_STARTUP_CONSTANTS, WEB_CONSTANTS, TICKET_CONSTANTS, UNASSIGNED_ROUTE_CONSTANTS, CLOUD_TALK_CONSTANTS, STANDING_ANSWERS_CONSTANTS, TICKET_AUTOPILOT_CONSTANTS, TICKET_HYGIENE_CONSTANTS, EXPERIMENT_CONSTANTS, WORK_ITEM_DESTINATION_CONSTANTS, CODEX_USAGE_SYNC_CONSTANTS, ANTIGRAVITY_USAGE_SYNC_CONSTANTS, OWNER_AUTH_CONSTANTS, CREWLY_APPS_CONSTANTS, SLACK_AGENT_DM_CONSTANTS, BRIEFING_CONSTANTS, DRIVE_CONSTANTS } from './constants.js';
|
|
80
|
+
import { SUB_AGENT_QUEUE_CONSTANTS, CHAT_CONTEXT_CONSTANTS, SAFE_RESTART, AUTO_UPDATE_CONSTANTS, PROCESS_EXIT_CODES, CLAUDE_STARTUP_CONSTANTS, WEB_CONSTANTS, TICKET_CONSTANTS, UNASSIGNED_ROUTE_CONSTANTS, CLOUD_TALK_CONSTANTS, STANDING_ANSWERS_CONSTANTS, TICKET_AUTOPILOT_CONSTANTS, TICKET_HYGIENE_CONSTANTS, EXPERIMENT_CONSTANTS, WORK_ITEM_DESTINATION_CONSTANTS, CODEX_USAGE_SYNC_CONSTANTS, ANTIGRAVITY_USAGE_SYNC_CONSTANTS, OWNER_AUTH_CONSTANTS, CREWLY_APPS_CONSTANTS, SLACK_AGENT_DM_CONSTANTS, BRIEFING_CONSTANTS, DRIVE_CONSTANTS, POOL_PRUNE_CONSTANTS } from './constants.js';
|
|
81
81
|
import { randomUUID } from 'crypto';
|
|
82
82
|
import { PtyActivityTrackerService } from './services/agent/pty-activity-tracker.service.js';
|
|
83
83
|
import { InFlightTurnTracker } from './services/restart/in-flight-turn-tracker.service.js';
|
|
@@ -88,6 +88,7 @@ import { initialDecider, nextDecider } from './services/task-pool/untargeted-rou
|
|
|
88
88
|
import { activeAcceptance, formatTicketMarker, formatTicketNumber } from './types/v2/ticket.types.js';
|
|
89
89
|
import { createWorkItem, TERMINAL_WORK_ITEM_STATUSES } from './types/v2/work-item.types.js';
|
|
90
90
|
import { runPoolArchiveMigration } from './services/task-pool/pool-archive-migration.js';
|
|
91
|
+
import { runPoolPrune } from './services/task-pool/pool-prune.js';
|
|
91
92
|
import { createPtyTurnProbe } from './services/restart/turn-probe.js';
|
|
92
93
|
import { RestartDrainService, resolveRestartDrainMs, resolveBackgroundDrainMs, } from './services/restart/restart-drain.service.js';
|
|
93
94
|
import { interruptedTurnsPath, loadInterruptedTurns, saveInterruptedTurns, writeInterruptedTurns, resumeInterruptedTurns, planCommitmentNotes, } from './services/restart/interrupted-turns.js';
|
|
@@ -185,6 +186,7 @@ import { TaskHistorySubscriber } from './services/memory/task-history.subscriber
|
|
|
185
186
|
import { TeamHealthWatchdogService, LiveTeamHealthDataProvider, loadTeamHealthConfig, setTeamHealthWatchdogSingleton, getTeamHealthWatchdogSingleton, } from './services/team-health/index.js';
|
|
186
187
|
import { traceHarness, traceTurnActivity } from './services/trace/trace-recorder.js';
|
|
187
188
|
import { inputCircuitStats, setInputCircuitOpenListener } from './services/session/input-circuit-breaker.js';
|
|
189
|
+
import { looksLikeShellPrompt } from './utils/screen-excerpt.js';
|
|
188
190
|
import { harnessPastesSinceOutsideInput, shownMarkers } from './services/session/input-ledger.js';
|
|
189
191
|
// ESM __dirname equivalent using import.meta.url
|
|
190
192
|
const __filename = fileURLToPath(import.meta.url);
|
|
@@ -764,13 +766,25 @@ export class CrewlyServer {
|
|
|
764
766
|
// Ticket loop §4: one-time archive of old WorkItems (marker file makes
|
|
765
767
|
// it run once). Through the pool's own storage cache, so no later
|
|
766
768
|
// flush can write the archived items back. Never deletes.
|
|
769
|
+
const poolPruneLogger = LoggerService.getInstance().createComponentLogger('PoolPrune');
|
|
770
|
+
const pruneOnce = () => runPoolPrune(TaskPoolService.getInstance().getStorage(), { logger: poolPruneLogger }).catch((pruneErr) => {
|
|
771
|
+
this.logger.warn('Task pool prune failed (pool left as is; retried next interval)', {
|
|
772
|
+
error: pruneErr instanceof Error ? pruneErr.message : String(pruneErr),
|
|
773
|
+
});
|
|
774
|
+
});
|
|
767
775
|
void runPoolArchiveMigration(TaskPoolService.getInstance().getStorage(), {
|
|
768
776
|
logger: LoggerService.getInstance().createComponentLogger('PoolArchive'),
|
|
769
|
-
})
|
|
777
|
+
})
|
|
778
|
+
.catch((archiveErr) => {
|
|
770
779
|
this.logger.warn('Task pool one-time archive failed (pool left as is; retried next boot)', {
|
|
771
780
|
error: archiveErr instanceof Error ? archiveErr.message : String(archiveErr),
|
|
772
781
|
});
|
|
773
|
-
})
|
|
782
|
+
})
|
|
783
|
+
// Then keep it small: finished items and ended claims move to the
|
|
784
|
+
// archive, once now and every few hours (crewly#1108).
|
|
785
|
+
.then(pruneOnce);
|
|
786
|
+
const poolPruneTimer = setInterval(() => void pruneOnce(), POOL_PRUNE_CONSTANTS.INTERVAL_MS);
|
|
787
|
+
poolPruneTimer.unref?.();
|
|
774
788
|
// Atlas 2026-05-23 fix: wire the agent-liveness gate so claimFromPool /
|
|
775
789
|
// claimSpecificItem refuse to put a WI into `running` when the requesting
|
|
776
790
|
// agent's session is dead. delegate-task's "self-heal fix #1" used to
|
|
@@ -2417,7 +2431,20 @@ export class CrewlyServer {
|
|
|
2417
2431
|
activateAgent: async (agentSession) => {
|
|
2418
2432
|
const { activateAgentBySession } = await import('./controllers/team/team.controller.js');
|
|
2419
2433
|
const res = await activateAgentBySession(this.apiController, agentSession);
|
|
2420
|
-
|
|
2434
|
+
// A start waiting for a running-agent slot is deferred, not failed.
|
|
2435
|
+
return res.success ? true : res.deferred ? 'deferred' : false;
|
|
2436
|
+
},
|
|
2437
|
+
// The message waits on the agent's persisted queue for a deferred start.
|
|
2438
|
+
holdForStart: (agentSession, prompt) => {
|
|
2439
|
+
SubAgentMessageQueue.getInstance().enqueue(agentSession, prompt);
|
|
2440
|
+
// Nothing else starts the agent when a slot frees: retry until it does.
|
|
2441
|
+
void import('./services/messaging/deferred-start-retry.js').then(async ({ scheduleDeferredStartRetry }) => {
|
|
2442
|
+
const { activateAgentBySession } = await import('./controllers/team/team.controller.js');
|
|
2443
|
+
await scheduleDeferredStartRetry(agentSession, {
|
|
2444
|
+
activate: (name) => activateAgentBySession(this.apiController, name),
|
|
2445
|
+
hasPending: (name) => SubAgentMessageQueue.getInstance().hasPending(name),
|
|
2446
|
+
});
|
|
2447
|
+
});
|
|
2421
2448
|
},
|
|
2422
2449
|
// Every owner message that reached an agent is watched until
|
|
2423
2450
|
// it is answered (specs/2026-09-30-owner-message-guarantee.md).
|
|
@@ -6370,6 +6397,17 @@ export class CrewlyServer {
|
|
|
6370
6397
|
};
|
|
6371
6398
|
// Every delivery refused for a while: automatic redelivery is slowed
|
|
6372
6399
|
// to a probe now and then, and the owner told once (crewly#1028).
|
|
6400
|
+
// What the unreadable screen shows (redacted rows), so the owner can
|
|
6401
|
+
// tell a dialog from a bare shell without opening the terminal.
|
|
6402
|
+
const screenNote = (sessionName, state) => {
|
|
6403
|
+
if (state !== 'unknown')
|
|
6404
|
+
return '';
|
|
6405
|
+
const excerpt = SessionCommandHelper.unreadableExcerpt(sessionName);
|
|
6406
|
+
if (!excerpt)
|
|
6407
|
+
return '';
|
|
6408
|
+
const hint = looksLikeShellPrompt(excerpt) ? ' It looks like the runtime exited to a shell prompt.' : '';
|
|
6409
|
+
return `${hint}\nScreen (secrets masked):\n${excerpt.split('\n').map((l) => `> ${l}`).join('\n')}`;
|
|
6410
|
+
};
|
|
6373
6411
|
setInputCircuitOpenListener((info) => {
|
|
6374
6412
|
traceHarness('guard.block', {
|
|
6375
6413
|
session: info.sessionName,
|
|
@@ -6422,7 +6460,7 @@ export class CrewlyServer {
|
|
|
6422
6460
|
? 'its input box cannot be read (a dialog or an unfamiliar screen)'
|
|
6423
6461
|
: `its input box holds ${notice.inputLength} characters that Crewly did not write`;
|
|
6424
6462
|
const maxMin = Math.round(INPUT_CIRCUIT_CONSTANTS.PROBE_MAX_MS / 60000);
|
|
6425
|
-
tell(notice.sessionName, `Needs you: ${notice.sessionName} has not received any message for ${minutes} min: ${what}, so Crewly refused to type over it (${notice.refusals} attempts). Crewly has stopped retrying every few seconds and now tries again only every few minutes (at most every ${maxMin} min). To fix it, open ${notice.sessionName}'s terminal and clear the input box (Ctrl+U), or press Enter if that text is yours. Delivery resumes on its own after that
|
|
6463
|
+
tell(notice.sessionName, `Needs you: ${notice.sessionName} has not received any message for ${minutes} min: ${what}, so Crewly refused to type over it (${notice.refusals} attempts). Crewly has stopped retrying every few seconds and now tries again only every few minutes (at most every ${maxMin} min). To fix it, open ${notice.sessionName}'s terminal and clear the input box (Ctrl+U), or press Enter if that text is yours. Delivery resumes on its own after that.${screenNote(notice.sessionName, notice.blockedState)}`, notice.message || undefined);
|
|
6426
6464
|
return;
|
|
6427
6465
|
}
|
|
6428
6466
|
if (notice.state === 'busy') {
|
|
@@ -6432,7 +6470,7 @@ export class CrewlyServer {
|
|
|
6432
6470
|
const what = notice.state === 'unknown'
|
|
6433
6471
|
? 'its input box cannot be read (a dialog or an unfamiliar screen)'
|
|
6434
6472
|
: `its input box holds ${notice.inputLength} characters of text not written by Crewly`;
|
|
6435
|
-
tell(notice.sessionName, `Needs you: messages to ${notice.sessionName} are waiting because ${what}. Crewly will not type over it. Tried ${notice.refusals} times over ${minutes} min; it keeps retrying. Clear the agent's input (or answer its screen) to let them through
|
|
6473
|
+
tell(notice.sessionName, `Needs you: messages to ${notice.sessionName} are waiting because ${what}. Crewly will not type over it. Tried ${notice.refusals} times over ${minutes} min; it keeps retrying. Clear the agent's input (or answer its screen) to let them through.${screenNote(notice.sessionName, notice.state)}`, notice.message);
|
|
6436
6474
|
},
|
|
6437
6475
|
});
|
|
6438
6476
|
// A WorkItem brief held by the restart drain gets its hand-over
|