@xn-intenton-z2a/agentic-lib 7.1.31 → 7.1.33
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/actions/agentic-step/copilot.js +17 -2
- package/src/actions/agentic-step/index.js +3 -0
- package/src/actions/agentic-step/logging.js +9 -2
- package/src/actions/agentic-step/tasks/discussions.js +4 -1
- package/src/actions/agentic-step/tasks/enhance-issue.js +4 -1
- package/src/actions/agentic-step/tasks/fix-code.js +4 -1
- package/src/actions/agentic-step/tasks/maintain-features.js +4 -1
- package/src/actions/agentic-step/tasks/maintain-library.js +4 -1
- package/src/actions/agentic-step/tasks/resolve-issue.js +4 -1
- package/src/actions/agentic-step/tasks/review-issue.js +7 -1
- package/src/actions/agentic-step/tasks/supervise.js +11 -1
- package/src/actions/agentic-step/tasks/transform.js +7 -1
- package/src/agents/agent-supervisor.md +17 -9
- package/src/seeds/zero-agentic-lib.toml +1 -1
- package/src/seeds/zero-package.json +1 -1
- package/src/workflows/agent-supervisor-schedule.yml +1 -1
- package/src/workflows/agent-supervisor.yml +17 -0
package/package.json
CHANGED
|
@@ -76,12 +76,27 @@ export async function runCopilotTask({ model, systemMessage, prompt, writablePat
|
|
|
76
76
|
core.warning(`[copilot] Auth check failed: ${authErr.message}`);
|
|
77
77
|
}
|
|
78
78
|
|
|
79
|
+
// Accumulate usage from assistant.usage events (tokens are NOT on the sendAndWait response)
|
|
80
|
+
let totalInputTokens = 0;
|
|
81
|
+
let totalOutputTokens = 0;
|
|
82
|
+
let totalCost = 0;
|
|
83
|
+
|
|
79
84
|
// Register wildcard event handler for ALL events
|
|
80
85
|
session.on((event) => {
|
|
81
86
|
const eventType = event?.type || "unknown";
|
|
82
87
|
if (eventType === "assistant.message") {
|
|
83
88
|
const preview = event?.data?.content?.substring(0, 100) || "(no content)";
|
|
84
89
|
core.info(`[copilot] event=${eventType}: ${preview}...`);
|
|
90
|
+
} else if (eventType === "assistant.usage") {
|
|
91
|
+
const d = event?.data || {};
|
|
92
|
+
const input = d.inputTokens || 0;
|
|
93
|
+
const output = d.outputTokens || 0;
|
|
94
|
+
const cacheRead = d.cacheReadTokens || 0;
|
|
95
|
+
const cost = d.cost || 0;
|
|
96
|
+
totalInputTokens += input;
|
|
97
|
+
totalOutputTokens += output;
|
|
98
|
+
totalCost += cost;
|
|
99
|
+
core.info(`[copilot] event=${eventType}: model=${d.model} input=${input} output=${output} cacheRead=${cacheRead} cost=${cost}`);
|
|
85
100
|
} else if (eventType === "session.idle") {
|
|
86
101
|
core.info(`[copilot] event=${eventType}`);
|
|
87
102
|
} else if (eventType === "session.error") {
|
|
@@ -94,10 +109,10 @@ export async function runCopilotTask({ model, systemMessage, prompt, writablePat
|
|
|
94
109
|
core.info("[copilot] Sending prompt and waiting for idle...");
|
|
95
110
|
const response = await session.sendAndWait({ prompt }, 600000);
|
|
96
111
|
core.info(`[copilot] sendAndWait resolved`);
|
|
97
|
-
const tokensUsed =
|
|
112
|
+
const tokensUsed = totalInputTokens + totalOutputTokens;
|
|
98
113
|
const content = response?.data?.content || "";
|
|
99
114
|
|
|
100
|
-
return { content, tokensUsed };
|
|
115
|
+
return { content, tokensUsed, inputTokens: totalInputTokens, outputTokens: totalOutputTokens, cost: totalCost };
|
|
101
116
|
} finally {
|
|
102
117
|
await client.stop();
|
|
103
118
|
}
|
|
@@ -105,6 +105,9 @@ async function run() {
|
|
|
105
105
|
prNumber: result.prNumber,
|
|
106
106
|
commitUrl: result.commitUrl,
|
|
107
107
|
tokensUsed: result.tokensUsed,
|
|
108
|
+
inputTokens: result.inputTokens,
|
|
109
|
+
outputTokens: result.outputTokens,
|
|
110
|
+
cost: result.cost,
|
|
108
111
|
model: result.model || model,
|
|
109
112
|
details: result.details,
|
|
110
113
|
workflowUrl: `${process.env.GITHUB_SERVER_URL}/${github.context.repo.owner}/${github.context.repo.repo}/actions/runs/${github.context.runId}`,
|
|
@@ -19,7 +19,10 @@ import * as core from "@actions/core";
|
|
|
19
19
|
* @param {string} [options.issueNumber] - Related issue number
|
|
20
20
|
* @param {string} [options.prNumber] - Related PR number
|
|
21
21
|
* @param {string} [options.commitUrl] - URL to the commit
|
|
22
|
-
* @param {number} [options.tokensUsed] -
|
|
22
|
+
* @param {number} [options.tokensUsed] - Total tokens consumed (input + output)
|
|
23
|
+
* @param {number} [options.inputTokens] - Input tokens consumed
|
|
24
|
+
* @param {number} [options.outputTokens] - Output tokens consumed
|
|
25
|
+
* @param {number} [options.cost] - Cost reported by Copilot SDK
|
|
23
26
|
* @param {string} [options.model] - Model used
|
|
24
27
|
* @param {string} [options.details] - Additional details
|
|
25
28
|
* @param {string} [options.workflowUrl] - URL to the workflow run
|
|
@@ -32,6 +35,9 @@ export function logActivity({
|
|
|
32
35
|
prNumber,
|
|
33
36
|
commitUrl,
|
|
34
37
|
tokensUsed,
|
|
38
|
+
inputTokens,
|
|
39
|
+
outputTokens,
|
|
40
|
+
cost,
|
|
35
41
|
model,
|
|
36
42
|
details,
|
|
37
43
|
workflowUrl,
|
|
@@ -48,7 +54,8 @@ export function logActivity({
|
|
|
48
54
|
if (prNumber) parts.push(`**PR:** #${prNumber}`);
|
|
49
55
|
if (commitUrl) parts.push(`**Commit:** [${commitUrl}](${commitUrl})`);
|
|
50
56
|
if (model) parts.push(`**Model:** ${model}`);
|
|
51
|
-
if (tokensUsed
|
|
57
|
+
if (tokensUsed) parts.push(`**Tokens:** ${tokensUsed} (in: ${inputTokens || 0}, out: ${outputTokens || 0})`);
|
|
58
|
+
if (cost) parts.push(`**Cost:** ${cost}`);
|
|
52
59
|
if (workflowUrl) parts.push(`**Workflow:** [${workflowUrl}](${workflowUrl})`);
|
|
53
60
|
if (details) {
|
|
54
61
|
parts.push("");
|
|
@@ -158,7 +158,7 @@ export async function discussions(context) {
|
|
|
158
158
|
const discussion = await fetchDiscussion(octokit, discussionUrl);
|
|
159
159
|
const prompt = buildPrompt(discussionUrl, discussion, context);
|
|
160
160
|
|
|
161
|
-
const { content, tokensUsed } = await runCopilotTask({
|
|
161
|
+
const { content, tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
162
162
|
model,
|
|
163
163
|
systemMessage:
|
|
164
164
|
"You are this repository. Respond in first person. Be concise and engaging — never repeat what you said in your last reply. Adapt to the user's language level. Encourage experimentation and suggest interesting projects. When a user requests an action, pass it to the supervisor via [ACTION:request-supervisor]. Protect the mission: push back on requests that contradict it.",
|
|
@@ -178,6 +178,9 @@ export async function discussions(context) {
|
|
|
178
178
|
return {
|
|
179
179
|
outcome: `discussion-${action}`,
|
|
180
180
|
tokensUsed,
|
|
181
|
+
inputTokens,
|
|
182
|
+
outputTokens,
|
|
183
|
+
cost,
|
|
181
184
|
model,
|
|
182
185
|
details: `Action: ${action}${argSuffix}\nReply: ${replyBody.substring(0, 200)}`,
|
|
183
186
|
action,
|
|
@@ -59,7 +59,7 @@ export async function enhanceIssue(context) {
|
|
|
59
59
|
"Output ONLY the new issue body text, no markdown code fences.",
|
|
60
60
|
].join("\n");
|
|
61
61
|
|
|
62
|
-
const { content: enhancedBody, tokensUsed } = await runCopilotTask({
|
|
62
|
+
const { content: enhancedBody, tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
63
63
|
model,
|
|
64
64
|
systemMessage: "You are a requirements analyst. Enhance GitHub issues with clear, testable acceptance criteria.",
|
|
65
65
|
prompt,
|
|
@@ -96,6 +96,9 @@ export async function enhanceIssue(context) {
|
|
|
96
96
|
return {
|
|
97
97
|
outcome: "issue-enhanced",
|
|
98
98
|
tokensUsed,
|
|
99
|
+
inputTokens,
|
|
100
|
+
outputTokens,
|
|
101
|
+
cost,
|
|
99
102
|
model,
|
|
100
103
|
details: `Enhanced issue #${issueNumber} with acceptance criteria`,
|
|
101
104
|
};
|
|
@@ -53,7 +53,7 @@ export async function fixCode(context) {
|
|
|
53
53
|
"- Make minimal changes to fix the failing tests",
|
|
54
54
|
].join("\n");
|
|
55
55
|
|
|
56
|
-
const { tokensUsed } = await runCopilotTask({
|
|
56
|
+
const { tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
57
57
|
model,
|
|
58
58
|
systemMessage: `You are an autonomous coding agent fixing failing tests on PR #${prNumber}. Make minimal, targeted changes to fix the test failures.`,
|
|
59
59
|
prompt,
|
|
@@ -65,6 +65,9 @@ export async function fixCode(context) {
|
|
|
65
65
|
return {
|
|
66
66
|
outcome: "fix-applied",
|
|
67
67
|
tokensUsed,
|
|
68
|
+
inputTokens,
|
|
69
|
+
outputTokens,
|
|
70
|
+
cost,
|
|
68
71
|
model,
|
|
69
72
|
details: `Applied fix for ${failedChecks.length} failing check(s) on PR #${prNumber}`,
|
|
70
73
|
};
|
|
@@ -62,7 +62,7 @@ export async function maintainFeatures(context) {
|
|
|
62
62
|
"- Feature files must be markdown with a descriptive filename (e.g. HTTP_SERVER.md)",
|
|
63
63
|
].join("\n");
|
|
64
64
|
|
|
65
|
-
const { tokensUsed } = await runCopilotTask({
|
|
65
|
+
const { tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
66
66
|
model,
|
|
67
67
|
systemMessage:
|
|
68
68
|
"You are a feature lifecycle manager. Create, update, and prune feature specification files to keep the project focused on its mission.",
|
|
@@ -73,6 +73,9 @@ export async function maintainFeatures(context) {
|
|
|
73
73
|
return {
|
|
74
74
|
outcome: "features-maintained",
|
|
75
75
|
tokensUsed,
|
|
76
|
+
inputTokens,
|
|
77
|
+
outputTokens,
|
|
78
|
+
cost,
|
|
76
79
|
model,
|
|
77
80
|
details: `Maintained features (${features.length} existing, limit ${featureLimit})`,
|
|
78
81
|
};
|
|
@@ -50,7 +50,7 @@ export async function maintainLibrary(context) {
|
|
|
50
50
|
`- Maximum ${libraryLimit} library documents`,
|
|
51
51
|
].join("\n");
|
|
52
52
|
|
|
53
|
-
const { tokensUsed } = await runCopilotTask({
|
|
53
|
+
const { tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
54
54
|
model,
|
|
55
55
|
systemMessage:
|
|
56
56
|
"You are a knowledge librarian. Maintain a library of technical documents extracted from web sources.",
|
|
@@ -61,6 +61,9 @@ export async function maintainLibrary(context) {
|
|
|
61
61
|
return {
|
|
62
62
|
outcome: "library-maintained",
|
|
63
63
|
tokensUsed,
|
|
64
|
+
inputTokens,
|
|
65
|
+
outputTokens,
|
|
66
|
+
cost,
|
|
64
67
|
model,
|
|
65
68
|
details: `Maintained library (${libraryDocs.length} docs, limit ${libraryLimit})`,
|
|
66
69
|
};
|
|
@@ -78,7 +78,7 @@ export async function resolveIssue(context) {
|
|
|
78
78
|
contributing ? `\n## Contributing Guidelines\n${contributing}` : "",
|
|
79
79
|
].join("\n");
|
|
80
80
|
|
|
81
|
-
const { content: resultContent, tokensUsed } = await runCopilotTask({
|
|
81
|
+
const { content: resultContent, tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
82
82
|
model,
|
|
83
83
|
systemMessage: `You are an autonomous coding agent resolving GitHub issue #${issueNumber}. Write clean, tested code. Only modify files listed under "Writable" paths. Read-only paths are for context only.`,
|
|
84
84
|
prompt,
|
|
@@ -91,6 +91,9 @@ export async function resolveIssue(context) {
|
|
|
91
91
|
outcome: "code-generated",
|
|
92
92
|
prNumber: null,
|
|
93
93
|
tokensUsed,
|
|
94
|
+
inputTokens,
|
|
95
|
+
outputTokens,
|
|
96
|
+
cost,
|
|
94
97
|
model,
|
|
95
98
|
commitUrl: null,
|
|
96
99
|
details: `Generated code for issue #${issueNumber}: ${resultContent.substring(0, 200)}`,
|
|
@@ -74,7 +74,7 @@ export async function reviewIssue(context) {
|
|
|
74
74
|
'- "OPEN: <reason>" if the issue is not yet resolved',
|
|
75
75
|
].join("\n");
|
|
76
76
|
|
|
77
|
-
const { content: verdict, tokensUsed } = await runCopilotTask({
|
|
77
|
+
const { content: verdict, tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
78
78
|
model,
|
|
79
79
|
systemMessage: "You are a code reviewer determining if GitHub issues have been resolved.",
|
|
80
80
|
prompt,
|
|
@@ -108,6 +108,9 @@ export async function reviewIssue(context) {
|
|
|
108
108
|
return {
|
|
109
109
|
outcome: "issue-closed",
|
|
110
110
|
tokensUsed,
|
|
111
|
+
inputTokens,
|
|
112
|
+
outputTokens,
|
|
113
|
+
cost,
|
|
111
114
|
model,
|
|
112
115
|
details: `Closed issue #${targetIssueNumber}: ${verdict.substring(0, 200)}`,
|
|
113
116
|
};
|
|
@@ -117,6 +120,9 @@ export async function reviewIssue(context) {
|
|
|
117
120
|
return {
|
|
118
121
|
outcome: "issue-still-open",
|
|
119
122
|
tokensUsed,
|
|
123
|
+
inputTokens,
|
|
124
|
+
outputTokens,
|
|
125
|
+
cost,
|
|
120
126
|
model,
|
|
121
127
|
details: `Issue #${targetIssueNumber} remains open: ${verdict.substring(0, 200)}`,
|
|
122
128
|
};
|
|
@@ -76,6 +76,8 @@ async function gatherContext(octokit, repo, config) {
|
|
|
76
76
|
workflowsSummary,
|
|
77
77
|
schedule: config.schedule,
|
|
78
78
|
supervisor: config.supervisor,
|
|
79
|
+
featureIssuesWipLimit: config.featureDevelopmentIssuesWipLimit,
|
|
80
|
+
maintenanceIssuesWipLimit: config.maintenanceIssuesWipLimit,
|
|
79
81
|
};
|
|
80
82
|
}
|
|
81
83
|
|
|
@@ -108,6 +110,11 @@ function buildPrompt(ctx, agentInstructions) {
|
|
|
108
110
|
"",
|
|
109
111
|
`### Schedule: ${ctx.schedule}, Supervisor: ${ctx.supervisor}`,
|
|
110
112
|
"",
|
|
113
|
+
`### Issue Limits`,
|
|
114
|
+
`Feature development WIP limit: ${ctx.featureIssuesWipLimit}`,
|
|
115
|
+
`Maintenance WIP limit: ${ctx.maintenanceIssuesWipLimit}`,
|
|
116
|
+
`Open issues: ${ctx.issuesSummary.length} (capacity for ${Math.max(0, ctx.featureIssuesWipLimit - ctx.issuesSummary.length)} more)`,
|
|
117
|
+
"",
|
|
111
118
|
"## Available Actions",
|
|
112
119
|
"Pick one or more actions. Output them in the format below.",
|
|
113
120
|
"",
|
|
@@ -250,7 +257,7 @@ export async function supervise(context) {
|
|
|
250
257
|
const agentInstructions = instructions || "You are the supervisor. Decide what actions to take.";
|
|
251
258
|
const prompt = buildPrompt(ctx, agentInstructions);
|
|
252
259
|
|
|
253
|
-
const { content, tokensUsed } = await runCopilotTask({
|
|
260
|
+
const { content, tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
254
261
|
model,
|
|
255
262
|
systemMessage:
|
|
256
263
|
"You are the supervisor of an autonomous coding repository. Your job is to advance the mission by choosing which workflows to dispatch and which GitHub actions to take. Pick multiple actions when appropriate. Be strategic — consider what's already in progress, what's blocked, and what will make the most impact.",
|
|
@@ -279,6 +286,9 @@ export async function supervise(context) {
|
|
|
279
286
|
return {
|
|
280
287
|
outcome: actions.length === 0 ? "nop" : `supervised:${actions.length}-actions`,
|
|
281
288
|
tokensUsed,
|
|
289
|
+
inputTokens,
|
|
290
|
+
outputTokens,
|
|
291
|
+
cost,
|
|
282
292
|
model,
|
|
283
293
|
details: `Actions: ${results.join(", ")}\nReasoning: ${reasoning.substring(0, 300)}`,
|
|
284
294
|
};
|
|
@@ -85,7 +85,7 @@ export async function transform(context) {
|
|
|
85
85
|
|
|
86
86
|
core.info(`Transform prompt length: ${prompt.length} chars`);
|
|
87
87
|
|
|
88
|
-
const { content: resultContent, tokensUsed } = await runCopilotTask({
|
|
88
|
+
const { content: resultContent, tokensUsed, inputTokens, outputTokens, cost } = await runCopilotTask({
|
|
89
89
|
model,
|
|
90
90
|
systemMessage:
|
|
91
91
|
"You are an autonomous code transformation agent. Your goal is to advance the repository toward its mission by making the most impactful change possible in a single step.",
|
|
@@ -98,6 +98,9 @@ export async function transform(context) {
|
|
|
98
98
|
return {
|
|
99
99
|
outcome: "transformed",
|
|
100
100
|
tokensUsed,
|
|
101
|
+
inputTokens,
|
|
102
|
+
outputTokens,
|
|
103
|
+
cost,
|
|
101
104
|
model,
|
|
102
105
|
details: resultContent.substring(0, 500),
|
|
103
106
|
};
|
|
@@ -207,6 +210,9 @@ async function transformTdd({
|
|
|
207
210
|
return {
|
|
208
211
|
outcome: "transformed-tdd",
|
|
209
212
|
tokensUsed: totalTokens,
|
|
213
|
+
inputTokens: (phase1.inputTokens || 0) + (phase2.inputTokens || 0),
|
|
214
|
+
outputTokens: (phase1.outputTokens || 0) + (phase2.outputTokens || 0),
|
|
215
|
+
cost: (phase1.cost || 0) + (phase2.cost || 0),
|
|
210
216
|
model,
|
|
211
217
|
details: `TDD transformation: Phase 1 (failing test) + Phase 2 (implementation). ${testResult.substring(0, 200)}`,
|
|
212
218
|
};
|
|
@@ -1,25 +1,32 @@
|
|
|
1
1
|
You are the supervisor of an autonomous coding repository. Your job is to advance the mission by strategically choosing which workflows to dispatch and which GitHub actions to take.
|
|
2
2
|
|
|
3
|
+
## Priority Order
|
|
4
|
+
|
|
5
|
+
1. **Create issues when the backlog is low** — if fewer than 3 open issues exist, create at least 1 new issue from the features list or mission before dispatching workflows. The pipeline stalls without issues to work on. Always include descriptive titles and the `automated` label.
|
|
6
|
+
2. **Dispatch transform when ready issues exist** — transform is where code gets written. Always prefer it over maintain when there are open issues with the `ready` label.
|
|
7
|
+
3. **Dispatch review after transform** — when recent workflow runs show a transform completion, dispatch review to close resolved issues and add `ready` labels to new issues. This keeps the pipeline flowing.
|
|
8
|
+
4. **Fix failing PRs** — dispatch fix-code for any PR with failing checks (include pr-number).
|
|
9
|
+
5. **Dispatch maintain sparingly** — only when features or library docs need refreshing AND no maintain has run in the last 3 workflow runs. Maintain is low-value if features are already populated.
|
|
10
|
+
|
|
3
11
|
## Decision Framework
|
|
4
12
|
|
|
5
13
|
1. **Check what's already in progress** — don't duplicate work. If a transform is running, don't dispatch another.
|
|
6
|
-
2. **Prioritise
|
|
7
|
-
3. **
|
|
8
|
-
4. **Respect limits** — don't create issues beyond the WIP limit. Don't dispatch workflows that will fail due to missing prerequisites.
|
|
9
|
-
5. **Be strategic about timing** — if the schedule is hourly, you can afford to spread work across cycles. If daily, batch more aggressively.
|
|
14
|
+
2. **Prioritise code generation** — the goal is working code. Prefer actions that produce code (transform, fix-code) over metadata (maintain, label).
|
|
15
|
+
3. **Keep the issue pipeline full** — the biggest bottleneck is running out of open issues. Proactively create issues when capacity allows.
|
|
16
|
+
4. **Respect limits** — don't create issues beyond the WIP limit shown in the context. Don't dispatch workflows that will fail due to missing prerequisites.
|
|
10
17
|
|
|
11
18
|
## When to use each action
|
|
12
19
|
|
|
13
|
-
- **
|
|
14
|
-
- **dispatch:agent-flow-
|
|
15
|
-
- **dispatch:agent-flow-review** —
|
|
20
|
+
- **github:create-issue** — When open issues < WIP limit. Derive the issue title from unimplemented features or mission goals. Always include relevant labels (`automated`, `enhancement`).
|
|
21
|
+
- **dispatch:agent-flow-transform** — When there are open issues with the `ready` label and no transform is currently running.
|
|
22
|
+
- **dispatch:agent-flow-review** — After observing a recent transform completion, or when there are unenhanced issues needing the `ready` label.
|
|
16
23
|
- **dispatch:agent-flow-fix-code** — When a specific PR has failing checks. Always include the pr-number.
|
|
24
|
+
- **dispatch:agent-flow-maintain** — When features are below their limit AND no maintain appears in the last 3 workflow runs.
|
|
17
25
|
- **dispatch:agent-discussions-bot** — When you want to proactively engage in discussions or respond to a user request.
|
|
18
|
-
- **github:create-issue** — When you identify a gap between the mission and current features. Always include a descriptive title and relevant labels.
|
|
19
26
|
- **github:label-issue** — When an issue needs better categorisation for prioritisation.
|
|
20
27
|
- **github:close-issue** — When an issue is clearly resolved or no longer relevant.
|
|
21
28
|
- **respond:discussions** — When replying to a user request that came through the discussions bot. Include the discussion URL and a clear message.
|
|
22
|
-
- **nop** — When everything is running
|
|
29
|
+
- **nop** — When everything is running optimally: transform is active, issues are flowing, no failures.
|
|
23
30
|
|
|
24
31
|
## Guidelines
|
|
25
32
|
|
|
@@ -28,3 +35,4 @@ You are the supervisor of an autonomous coding repository. Your job is to advanc
|
|
|
28
35
|
- When a user has made a request via discussions, prioritise responding to it.
|
|
29
36
|
- Don't dispatch the same workflow twice in one cycle.
|
|
30
37
|
- If recent workflow runs show failures, investigate before dispatching more work.
|
|
38
|
+
- Creating an issue + dispatching review in the same cycle is a good pattern: review will enhance the new issue with acceptance criteria and the `ready` label.
|
|
@@ -23,6 +23,8 @@ on:
|
|
|
23
23
|
- test
|
|
24
24
|
- agent-flow-transform
|
|
25
25
|
- agent-flow-fix-code
|
|
26
|
+
- agent-flow-maintain
|
|
27
|
+
- agent-flow-review
|
|
26
28
|
- ci-automerge
|
|
27
29
|
types:
|
|
28
30
|
- completed
|
|
@@ -172,6 +174,21 @@ jobs:
|
|
|
172
174
|
core.warning(`Stale PR check failed: ${err.message}`);
|
|
173
175
|
}
|
|
174
176
|
|
|
177
|
+
// ─── 3. Successful transform → dispatch review ────────────────
|
|
178
|
+
try {
|
|
179
|
+
if (workflowRun && workflowName === 'agent-flow-transform' && conclusion === 'success') {
|
|
180
|
+
core.info('Transform completed successfully — dispatching review to close resolved issues and enhance new ones.');
|
|
181
|
+
await github.rest.actions.createWorkflowDispatch({
|
|
182
|
+
owner, repo,
|
|
183
|
+
workflow_id: 'agent-flow-review.yml',
|
|
184
|
+
ref: 'main',
|
|
185
|
+
inputs: {},
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
} catch (err) {
|
|
189
|
+
core.warning(`Post-transform review dispatch failed: ${err.message}`);
|
|
190
|
+
}
|
|
191
|
+
|
|
175
192
|
# ─── Proactive: LLM-driven strategic decisions ───────────────────────
|
|
176
193
|
supervise:
|
|
177
194
|
needs: params
|