Skip to content

Commit fe02b64

Browse files
pelikhanCopilot
andauthored
Standardize work-queue naming across runtime, specs, and ADRs (#65208)
* Standardize work-queue naming across runtime and specs Use aw_context.work_queue for inbound assignments and rename MCP tools, artifacts, compiler and report types, workflow wiring, TLA+ sources, and ADR references. Define the existing versioned workflow transaction and assignment contracts in TypeSpec and regenerate their schemas. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> * Preserve queue state and context across the work-queue rename Validate and retain nested work_queue assignments, normalize legacy worker contexts, keep checked writes on existing queue storage, and preserve historical logs/audit evidence. Add regression coverage for in-flight workers, storage conflicts, malformed assignments, and legacy artifacts; finish the backfill flag rename. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --------- Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
1 parent de6e5b9 commit fe02b64

95 files changed

Lines changed: 1746 additions & 1053 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/workflows/smoke-dispatch-work-coordinator.lock.yml renamed to .github/workflows/smoke-work-queue.lock.yml

Lines changed: 73 additions & 73 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

.github/workflows/smoke-dispatch-work-coordinator.md renamed to .github/workflows/smoke-work-queue.md

Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
---
22
private: true
33
emoji: "🧪"
4-
name: Smoke Dispatch Work Coordinator
5-
description: End-to-end smoke test for dispatch coordinator snapshot and finish tools
4+
name: Smoke Work Queue
5+
description: End-to-end smoke test for work queue snapshot and finish tools
66
on:
77
schedule: every 2 days
88
workflow_dispatch:
@@ -20,37 +20,37 @@ tools:
2020
work-queue: true
2121
safe-outputs:
2222
steps:
23-
- name: Verify coordinator finish intent artifact
23+
- name: Verify queue finish intent artifact
2424
run: |
2525
if grep -Eq '"type"[[:space:]]*:[[:space:]]*"create_issue"' /tmp/gh-aw/safeoutputs.jsonl; then
26-
echo 'Dispatch coordinator smoke failure reported; processing the failure issue'
26+
echo 'Work queue smoke failure reported; processing the failure issue'
2727
else
28-
test -s /tmp/gh-aw/dispatch-work-coordinator.finish.jsonl
29-
grep -Fx '{"outcome":"completed"}' /tmp/gh-aw/dispatch-work-coordinator.finish.jsonl
28+
test -s /tmp/gh-aw/work-queue.finish.jsonl
29+
grep -Fx '{"outcome":"completed"}' /tmp/gh-aw/work-queue.finish.jsonl
3030
fi
3131
create-issue:
3232
max: 1
33-
title-prefix: "[smoke-dispatch-work-coordinator] "
33+
title-prefix: "[smoke-work-queue] "
3434
labels: [automation, testing]
3535
close-older-issues: true
36-
close-older-key: "smoke-dispatch-work-coordinator"
36+
close-older-key: "smoke-work-queue"
3737
noop:
3838
timeout-minutes: 10
3939
strict: true
4040
features:
4141
gh-aw-detection: false
4242
---
4343

44-
# Dispatch Work Coordinator Smoke Test
44+
# Work Queue Smoke Test
4545

46-
Exercise the coordinator MCP server mounted from the activation snapshot and the
46+
Exercise the queue MCP server mounted from the activation snapshot and the
4747
trusted safe-output finish-intent path. This workflow has no inbound worker claim,
48-
so it must not mutate the durable coordinator log.
48+
so it must not mutate the durable queue log.
4949

50-
1. Call `dispatch_work_coordinator_read` with
50+
1. Call `work_queue_read` with
5151
`work: "__gh_aw_smoke__-${{ github.run_id }}"`. Verify the returned work is
5252
`absent` and that the response includes a snapshot version.
53-
2. Call `dispatch_claim_finish` with `outcome: "completed"`. Verify it reports
53+
2. Call `work_queue_claim_finish` with `outcome: "completed"`. Verify it reports
5454
that the finish intent was recorded. Do not supply work or claim identifiers.
5555
The safe-output check must find this finish intent in the downloaded agent
5656
artifact before the `noop` handler runs.
Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,31 +1,31 @@
1-
name: Dispatch Coordinator Compilation Integration
1+
name: Work Queue Compilation Integration
22

33
on:
44
pull_request:
55
paths:
6-
- '.github/workflows/dispatch-coordinator-integration.yml'
7-
- 'actions/setup/js/dispatch_work_coordinator*'
8-
- 'actions/setup/js/finish_dispatch_work_claim*'
6+
- '.github/workflows/work-queue-integration.yml'
7+
- 'actions/setup/js/work_queue*'
8+
- 'actions/setup/js/finish_work_queue_claim*'
99
- 'actions/setup/js/setup_sh_file_lists.test.cjs'
10-
- 'actions/setup/js/write_dispatch_work_coordinator_snapshot*'
10+
- 'actions/setup/js/write_work_queue_snapshot*'
1111
- 'actions/setup/setup.sh'
1212
- 'pkg/constants/**'
1313
- 'pkg/workflow/**'
14-
- 'specs/dispatch-work-coordinator/**'
14+
- 'specs/work-queue/**'
1515
- 'go.mod'
1616
- 'go.sum'
1717
push:
1818
branches: [main]
1919
paths:
20-
- '.github/workflows/dispatch-coordinator-integration.yml'
21-
- 'actions/setup/js/dispatch_work_coordinator*'
22-
- 'actions/setup/js/finish_dispatch_work_claim*'
20+
- '.github/workflows/work-queue-integration.yml'
21+
- 'actions/setup/js/work_queue*'
22+
- 'actions/setup/js/finish_work_queue_claim*'
2323
- 'actions/setup/js/setup_sh_file_lists.test.cjs'
24-
- 'actions/setup/js/write_dispatch_work_coordinator_snapshot*'
24+
- 'actions/setup/js/write_work_queue_snapshot*'
2525
- 'actions/setup/setup.sh'
2626
- 'pkg/constants/**'
2727
- 'pkg/workflow/**'
28-
- 'specs/dispatch-work-coordinator/**'
28+
- 'specs/work-queue/**'
2929
- 'go.mod'
3030
- 'go.sum'
3131
workflow_dispatch:
@@ -35,7 +35,7 @@ permissions:
3535

3636
jobs:
3737
compilation-phases:
38-
name: Compile coordinator phases
38+
name: Compile queue phases
3939
runs-on: ubuntu-latest
4040
timeout-minutes: 15
4141
steps:
@@ -49,4 +49,4 @@ jobs:
4949
cache: true
5050

5151
- name: Compile activation, agent, and safe-outputs phases
52-
run: go test -tags=integration ./pkg/workflow -run '^TestDispatchCoordinatorCompilationPhases$' -count=1
52+
run: go test -tags=integration ./pkg/workflow -run '^TestWorkQueueCompilationPhases$' -count=1

‎actions/setup/js/aw_context.cjs‎

Lines changed: 32 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -167,6 +167,37 @@ function readInboundAwContext(payload) {
167167
return parseInboundAwContext(payload?.inputs?.aw_context) || parseInboundAwContext(payload?.client_payload?.aw_context);
168168
}
169169

170+
/**
171+
* @param {Record<string, unknown> | null} awContext
172+
* @returns {{work_id: string, claim_id: string, work: Record<string, unknown>} | null}
173+
*/
174+
function readWorkQueueAssignment(awContext) {
175+
if (!awContext) return null;
176+
const hasCurrent = Object.hasOwn(awContext, "work_queue");
177+
const hasLegacy = Object.hasOwn(awContext, "work_claim");
178+
if (hasCurrent && hasLegacy) {
179+
throw new TypeError("aw_context cannot contain both work_queue and the legacy work_claim assignment");
180+
}
181+
if (!hasCurrent && !hasLegacy) return null;
182+
const assignment = hasCurrent ? awContext.work_queue : awContext.work_claim;
183+
if (!isRecord(assignment) || Object.keys(assignment).length !== 3 || typeof assignment.work_id !== "string" || !assignment.work_id || typeof assignment.claim_id !== "string" || !assignment.claim_id || !isRecord(assignment.work)) {
184+
throw new TypeError("work queue assignment has an invalid shape");
185+
}
186+
return { work_id: assignment.work_id, claim_id: assignment.claim_id, work: assignment.work };
187+
}
188+
189+
/**
190+
* @param {Record<string, unknown>} awContext
191+
* @returns {Record<string, unknown>}
192+
*/
193+
function normalizeWorkQueueContext(awContext) {
194+
const assignment = readWorkQueueAssignment(awContext);
195+
const normalized = { ...awContext };
196+
delete normalized.work_claim;
197+
if (assignment) normalized.work_queue = assignment;
198+
return normalized;
199+
}
200+
170201
/**
171202
* Builds the aw_context object that identifies the calling workflow run.
172203
* This metadata is injected into dispatched workflows that declare an
@@ -357,4 +388,4 @@ function buildAwContext() {
357388
};
358389
}
359390

360-
module.exports = { buildAwContext, buildWorkflowCallId, resolveItemContext, parseInboundAwContext, readInboundAwContext };
391+
module.exports = { buildAwContext, buildWorkflowCallId, resolveItemContext, parseInboundAwContext, readInboundAwContext, readWorkQueueAssignment, normalizeWorkQueueContext };

‎actions/setup/js/create_prompt.cjs‎

Lines changed: 4 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ const fs = require("fs");
55
const path = require("path");
66
const { getErrorMessage } = require("./error_helpers.cjs");
77
const { ERR_CONFIG, ERR_PARSE, ERR_SYSTEM } = require("./error_codes.cjs");
8-
const { readInboundAwContext } = require("./aw_context.cjs");
8+
const { readInboundAwContext, readWorkQueueAssignment } = require("./aw_context.cjs");
99
const LEDGER_REPLAY_PROMPT = "/tmp/gh-aw/ledgers/replay-prompt.txt";
1010

1111
/**
@@ -156,23 +156,15 @@ function renderPrompt(config, env, promptsDir, replayPromptPath = LEDGER_REPLAY_
156156
return result;
157157
}
158158

159-
/**
160-
* @param {unknown} value
161-
* @returns {value is Record<string, unknown>}
162-
*/
163-
function isRecord(value) {
164-
return typeof value === "object" && value !== null && !Array.isArray(value);
165-
}
166-
167159
function renderWorkClaim(payload) {
168-
const assignment = readInboundAwContext(payload)?.work_claim;
169-
if (!isRecord(assignment) || typeof assignment.work_id !== "string" || !assignment.work_id || typeof assignment.claim_id !== "string" || !assignment.claim_id || !isRecord(assignment.work)) {
160+
const assignment = readWorkQueueAssignment(readInboundAwContext(payload));
161+
if (!assignment) {
170162
return "";
171163
}
172164

173165
const work = JSON.stringify({ id: assignment.work_id, payload: assignment.work }).replace(/</g, "\\u003c");
174166
const claim = JSON.stringify({ id: assignment.claim_id, work_id: assignment.work_id }).replace(/</g, "\\u003c");
175-
return `<work-claim>\n${work}\n${claim}\nWhen the work is complete, call dispatch_claim_finish with outcome "completed" to record the finish intent. If you cannot complete the work, call it with outcome "cancelled". The claim is only complete after trusted reconciliation verifies it; recording intent alone does not authorize safe outputs.\n</work-claim>\n`;
167+
return `<work-claim>\n${work}\n${claim}\nWhen the work is complete, call work_queue_claim_finish with outcome "completed" to record the finish intent. If you cannot complete the work, call it with outcome "cancelled". The claim is only complete after trusted reconciliation verifies it; recording intent alone does not authorize safe outputs.\n</work-claim>\n`;
176168
}
177169

178170
/**

‎actions/setup/js/create_prompt.test.cjs‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,7 @@ describe("create_prompt", () => {
134134
payload: {
135135
inputs: {
136136
aw_context: JSON.stringify({
137-
work_claim: { work_id: "work-1", claim_id: "claim-1", work: { task: "</work-claim> review the issue" } },
137+
work_queue: { work_id: "work-1", claim_id: "claim-1", work: { task: "</work-claim> review the issue" } },
138138
}),
139139
},
140140
},
@@ -152,7 +152,7 @@ describe("create_prompt", () => {
152152
const user = fs.readFileSync(path.join(path.dirname(promptPath), "user.txt"), "utf8");
153153
expect(core.setFailed).not.toHaveBeenCalled();
154154
expect(user).toContain('<work-claim>\n{"id":"work-1","payload":{"task":"\\u003c/work-claim> review the issue"}}\n{"id":"claim-1","work_id":"work-1"}');
155-
expect(user).toContain('call dispatch_claim_finish with outcome "completed"');
155+
expect(user).toContain('call work_queue_claim_finish with outcome "completed"');
156156
expect(user).toContain('call it with outcome "cancelled"');
157157
expect(user).toContain("recording intent alone does not authorize safe outputs.\n</work-claim>\nOriginal prompt\n");
158158
expect(user).not.toContain("<WorkClaim>");

actions/setup/js/finish_dispatch_work_claim.cjs renamed to actions/setup/js/finish_work_queue_claim.cjs

Lines changed: 28 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -2,16 +2,16 @@
22
"use strict";
33

44
const fs = require("fs");
5-
const { applyAndPublishCoordinatorTransactions, readCoordinatorLog } = require("./dispatch_work_coordinator_store.cjs");
6-
const { CURRENT_VERSION } = require("./dispatch_work_coordinator_codemods.cjs");
7-
const { replayTransactions } = require("./dispatch_work_coordinator_replay.cjs");
5+
const { applyAndPublishWorkQueueTransactions, readWorkQueueLog } = require("./work_queue_store.cjs");
6+
const { CURRENT_VERSION } = require("./work_queue_codemods.cjs");
7+
const { replayTransactions } = require("./work_queue_replay.cjs");
88
const { buildWorkflowCallId } = require("./aw_context.cjs");
99

10-
const SNAPSHOT_PATH = "/tmp/gh-aw/dispatch-work-coordinator.snapshot.json";
11-
const FINISH_INTENT_PATH = "/tmp/gh-aw/dispatch-work-coordinator.finish.jsonl";
10+
const SNAPSHOT_PATH = "/tmp/gh-aw/work-queue.snapshot.json";
11+
const FINISH_INTENT_PATH = "/tmp/gh-aw/work-queue.finish.jsonl";
1212
const SAFE_OUTPUTS_PATH = "/tmp/gh-aw/safeoutputs.jsonl";
1313

14-
function readWorkerSnapshot(snapshotPath = process.env.GH_AW_DISPATCH_COORDINATOR_SNAPSHOT || SNAPSHOT_PATH) {
14+
function readWorkerSnapshot(snapshotPath = process.env.GH_AW_WORK_QUEUE_SNAPSHOT || SNAPSHOT_PATH) {
1515
const snapshot = JSON.parse(fs.readFileSync(snapshotPath, "utf8"));
1616
if (
1717
!snapshot ||
@@ -20,12 +20,12 @@ function readWorkerSnapshot(snapshotPath = process.env.GH_AW_DISPATCH_COORDINATO
2020
(snapshot.worker !== null &&
2121
(!snapshot.worker || typeof snapshot.worker !== "object" || typeof snapshot.worker.work_id !== "string" || snapshot.worker.work_id.length === 0 || typeof snapshot.worker.claim_id !== "string" || snapshot.worker.claim_id.length === 0))
2222
) {
23-
throw new TypeError("dispatch coordinator snapshot has an invalid worker assignment");
23+
throw new TypeError("work queue snapshot has an invalid worker assignment");
2424
}
2525
return snapshot.worker;
2626
}
2727

28-
function readFinishIntent(finishIntentPath = process.env.GH_AW_DISPATCH_COORDINATOR_FINISH_INTENT || FINISH_INTENT_PATH) {
28+
function readFinishIntent(finishIntentPath = process.env.GH_AW_WORK_QUEUE_FINISH_INTENT || FINISH_INTENT_PATH) {
2929
if (!fs.existsSync(finishIntentPath)) return null;
3030
const outcomes = new Set();
3131
const contents = fs.readFileSync(finishIntentPath, "utf8");
@@ -35,14 +35,14 @@ function readFinishIntent(finishIntentPath = process.env.GH_AW_DISPATCH_COORDINA
3535
try {
3636
intent = JSON.parse(line);
3737
} catch {
38-
throw new TypeError(`dispatch claim finish intent line ${index + 1} is malformed`);
38+
throw new TypeError(`work queue claim finish intent line ${index + 1} is malformed`);
3939
}
4040
if (!intent || typeof intent !== "object" || Array.isArray(intent) || Object.keys(intent).length !== 1 || !Object.hasOwn(intent, "outcome") || !["completed", "cancelled"].includes(intent.outcome)) {
41-
throw new TypeError(`dispatch claim finish intent line ${index + 1} is invalid`);
41+
throw new TypeError(`work queue claim finish intent line ${index + 1} is invalid`);
4242
}
4343
outcomes.add(intent.outcome);
4444
}
45-
if (outcomes.size > 1) throw new TypeError("dispatch claim finish intents conflict");
45+
if (outcomes.size > 1) throw new TypeError("work queue claim finish intents conflict");
4646
return outcomes.size === 0 ? null : [...outcomes][0];
4747
}
4848

@@ -56,7 +56,7 @@ function renderSummary(status) {
5656
failed: "Claim reconciliation failed; ordinary safe outputs were blocked.",
5757
};
5858
const description = labels[status] || labels.failed;
59-
return `## Dispatch work reconciliation\n\n<details>\n<summary>Show claim reconciliation</summary>\n\n${description}\n\n</details>\n`;
59+
return `## Work queue reconciliation\n\n<details>\n<summary>Show claim reconciliation</summary>\n\n${description}\n\n</details>\n`;
6060
}
6161

6262
async function reconcileWorkerClaim(options = {}) {
@@ -67,21 +67,21 @@ async function reconcileWorkerClaim(options = {}) {
6767
if (!repositoryContext?.repo) throw new Error("GitHub repository context is unavailable");
6868
const owner = repositoryContext.repo.owner;
6969
const repo = repositoryContext.repo.repo;
70-
const readLog = options.readCoordinatorLog || readCoordinatorLog;
70+
const readLog = options.readWorkQueueLog || readWorkQueueLog;
7171

7272
if (!worker) {
73-
coreApi?.info("Dispatch coordinator: no inbound worker claim; skipping queue reconciliation");
73+
coreApi?.info("Work queue: no inbound worker claim; skipping queue reconciliation");
7474
return { authorized: true, status: "unassigned" };
7575
}
7676

7777
const finishIntent = readFinishIntent(options.finishIntentPath);
78-
coreApi?.info(`Dispatch coordinator: worker finish intent ${finishIntent || "absent"}`);
78+
coreApi?.info(`Work queue: worker finish intent ${finishIntent || "absent"}`);
7979
const initial = await readLog({ githubClient, owner, repo, core: coreApi });
8080
const projection = replayTransactions(initial.transactions);
81-
coreApi?.info(`Dispatch coordinator: rechecking worker against ${initial.transactions.length} queue transactions`);
81+
coreApi?.info(`Work queue: rechecking worker against ${initial.transactions.length} queue transactions`);
8282
const claim = initial.transactions.find(transaction => transaction.kind === "Claim" && transaction.claim === worker.claim_id);
8383
if (!claim || claim.work !== worker.work_id || !Object.hasOwn(projection.work, worker.work_id) || !Object.hasOwn(projection.claim, worker.claim_id)) {
84-
coreApi?.info("Dispatch coordinator: worker claim is no longer present in the queue");
84+
coreApi?.info("Work queue: worker claim is no longer present in the queue");
8585
return { authorized: false, status: "superseded" };
8686
}
8787

@@ -91,12 +91,12 @@ async function reconcileWorkerClaim(options = {}) {
9191

9292
const existingCompletion = initial.transactions.find(transaction => transaction.kind === "Completion" && transaction.work === worker.work_id && transaction.claim === worker.claim_id && transaction.attempt === attempt);
9393
if (existingCompletion && projection.work[worker.work_id] === "completed" && projection.winner[worker.work_id] === worker.claim_id) {
94-
coreApi?.info("Dispatch coordinator: worker completion already verified");
94+
coreApi?.info("Work queue: worker completion already verified");
9595
return { authorized: true, status: "completed" };
9696
}
9797

9898
if (projection.claim[worker.claim_id] !== "effective") {
99-
coreApi?.info(`Dispatch coordinator: worker claim is ${projection.claim[worker.claim_id]}`);
99+
coreApi?.info(`Work queue: worker claim is ${projection.claim[worker.claim_id]}`);
100100
if (projection.claim[worker.claim_id] === "cancelled") return { authorized: false, status: "cancelled" };
101101
return { authorized: false, status: ["completed", "cancelled"].includes(projection.work[worker.work_id]) ? "terminal" : "superseded" };
102102
}
@@ -105,27 +105,27 @@ async function reconcileWorkerClaim(options = {}) {
105105
const intent = cancel
106106
? { version: CURRENT_VERSION, kind: "ClaimCancellation", work: worker.work_id, claim: worker.claim_id, attempt: null }
107107
: { version: CURRENT_VERSION, kind: "Completion", work: worker.work_id, claim: worker.claim_id, attempt };
108-
const publish = options.applyAndPublish || applyAndPublishCoordinatorTransactions;
109-
coreApi?.info(`Dispatch coordinator: publishing worker ${cancel ? "cancellation" : "completion"}`);
108+
const publish = options.applyAndPublish || applyAndPublishWorkQueueTransactions;
109+
coreApi?.info(`Work queue: publishing worker ${cancel ? "cancellation" : "completion"}`);
110110
await publish({ githubClient, owner, repo, intents: [intent], core: coreApi });
111111

112112
const latest = await readLog({ githubClient, owner, repo, core: coreApi });
113113
const verified = replayTransactions(latest.transactions);
114-
coreApi?.info(`Dispatch coordinator: verifying worker against ${latest.transactions.length} queue transactions`);
114+
coreApi?.info(`Work queue: verifying worker against ${latest.transactions.length} queue transactions`);
115115
if (
116116
!cancel &&
117117
latest.transactions.some(transaction => transaction.kind === "Completion" && transaction.work === worker.work_id && transaction.claim === worker.claim_id && transaction.attempt === attempt) &&
118118
verified.work[worker.work_id] === "completed" &&
119119
verified.winner[worker.work_id] === worker.claim_id
120120
) {
121-
coreApi?.info("Dispatch coordinator: worker completion verified");
121+
coreApi?.info("Work queue: worker completion verified");
122122
return { authorized: true, status: "completed" };
123123
}
124124
if (cancel && latest.transactions.some(transaction => transaction.kind === "ClaimCancellation" && transaction.work === worker.work_id && transaction.claim === worker.claim_id) && verified.claim[worker.claim_id] === "cancelled") {
125-
coreApi?.info("Dispatch coordinator: worker cancellation verified");
125+
coreApi?.info("Work queue: worker cancellation verified");
126126
return { authorized: false, status: "cancelled" };
127127
}
128-
coreApi?.info("Dispatch coordinator: worker reconciliation did not verify the intended queue state");
128+
coreApi?.info("Work queue: worker reconciliation did not verify the intended queue state");
129129
return { authorized: false, status: ["completed", "cancelled"].includes(verified.work[worker.work_id]) ? "terminal" : "superseded" };
130130
}
131131

@@ -134,14 +134,14 @@ async function main(options = {}) {
134134
try {
135135
const result = await reconcileWorkerClaim(options);
136136
coreApi.setOutput("authorized", String(result.authorized));
137-
coreApi.info(`Dispatch work claim reconciliation: ${result.status}`);
137+
coreApi.info(`Work queue claim reconciliation: ${result.status}`);
138138
await coreApi.summary.addRaw(renderSummary(result.status)).write();
139139
return result;
140140
} catch {
141141
coreApi.setOutput("authorized", "false");
142-
coreApi.info("Dispatch work claim reconciliation failed; ordinary safe outputs are blocked.");
142+
coreApi.info("Work queue claim reconciliation failed; ordinary safe outputs are blocked.");
143143
await coreApi.summary.addRaw(renderSummary("failed")).write();
144-
throw new Error("Dispatch work claim reconciliation failed; ordinary safe outputs are blocked");
144+
throw new Error("Work queue claim reconciliation failed; ordinary safe outputs are blocked");
145145
}
146146
}
147147

0 commit comments

Comments
 (0)