vibe-coding-master 0.6.19 → 0.6.21
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 -5
- package/dist/backend/api/artifact-routes.js +2 -2
- package/dist/backend/api/gate-review-routes.js +1 -1
- package/dist/backend/api/task-routes.js +1 -1
- package/dist/backend/cli/install-vcm-harness.js +66 -20
- package/dist/backend/services/app-settings-service.js +11 -2
- package/dist/backend/services/artifact-service.js +9 -8
- package/dist/backend/services/gate-review-service.js +319 -24
- package/dist/backend/services/harness-feedback-service.js +8 -3
- package/dist/backend/services/harness-service.js +100 -13
- package/dist/backend/services/job-guard-service.js +2 -2
- package/dist/backend/services/message-service.js +12 -0
- package/dist/backend/services/session-service.js +18 -11
- package/dist/backend/services/status-service.js +1 -4
- package/dist/backend/templates/handoff.js +105 -17
- package/dist/backend/templates/harness/architect-agent.js +51 -27
- package/dist/backend/templates/harness/claude-root.js +43 -15
- package/dist/backend/templates/harness/coder-agent.js +66 -47
- package/dist/backend/templates/harness/coder-worker-agent.js +45 -17
- package/dist/backend/templates/harness/gate-review.js +229 -39
- package/dist/backend/templates/harness/harness-engineer-agent.js +39 -12
- package/dist/backend/templates/harness/project-coding-standards.js +73 -0
- package/dist/backend/templates/harness/project-glossary.js +30 -0
- package/dist/backend/templates/harness/project-known-issues.js +33 -0
- package/dist/backend/templates/harness/project-manager-agent.js +97 -27
- package/dist/backend/templates/harness/pull-request-template.js +6 -4
- package/dist/backend/templates/harness/tester-agent.js +82 -0
- package/dist/backend/templates/harness/vcm-final-acceptance-skill.js +19 -15
- package/dist/backend/templates/harness/vcm-harness-bootstrap-skill.js +19 -2
- package/dist/backend/templates/harness/vcm-long-running-validation-skill.js +1 -1
- package/dist/backend/templates/harness/vcm-report-harness-issue-skill.js +18 -12
- package/dist/backend/templates/harness/vcm-route-message-skill.js +48 -8
- package/dist/backend/templates/message-envelope.js +2 -5
- package/dist/shared/constants.js +3 -3
- package/dist/shared/types/gate-review.js +5 -1
- package/dist/shared/validation/artifact-check.js +64 -10
- package/dist-frontend/assets/{index-C5E5jLp-.js → index-DYBg_qYS.js} +4 -4
- package/dist-frontend/index.html +1 -1
- package/package.json +1 -1
- package/scripts/verify-package.mjs +1 -1
- package/dist/backend/templates/harness/reviewer-agent.js +0 -60
|
@@ -1,13 +1,24 @@
|
|
|
1
1
|
export function renderVcmRouteMessageSkillRules() {
|
|
2
2
|
return `## Purpose
|
|
3
3
|
|
|
4
|
-
Use this skill when a VCM role
|
|
4
|
+
Use this skill when project-manager dispatches a VCM role or when a VCM role reports a question, result, blocker, or finding back to project-manager.
|
|
5
5
|
|
|
6
6
|
This skill writes a route file. It does not deliver the message. VCM backend delivery is triggered later by Claude Code hooks.
|
|
7
7
|
|
|
8
8
|
## Route Policy
|
|
9
9
|
|
|
10
|
-
|
|
10
|
+
VCM uses project-manager as the routing hub.
|
|
11
|
+
|
|
12
|
+
Allowed routes:
|
|
13
|
+
|
|
14
|
+
- \`project-manager -> architect\`
|
|
15
|
+
- \`project-manager -> coder\`
|
|
16
|
+
- \`project-manager -> tester\`
|
|
17
|
+
- \`architect -> project-manager\`
|
|
18
|
+
- \`coder -> project-manager\`
|
|
19
|
+
- \`tester -> project-manager\`
|
|
20
|
+
|
|
21
|
+
Non-PM roles must not route directly to each other. Report questions, blockers, results, findings, or validation evidence back to project-manager. PM decides the next role route.
|
|
11
22
|
|
|
12
23
|
Allowed message types:
|
|
13
24
|
|
|
@@ -27,7 +38,7 @@ Write or update exactly one file:
|
|
|
27
38
|
.ai/vcm/handoffs/messages/<from-role>-<to-role>.md
|
|
28
39
|
\`\`\`
|
|
29
40
|
|
|
30
|
-
The file name is authoritative. Do not put from/to in frontmatter and do not create alternate message paths.
|
|
41
|
+
Use one allowed route above. The file name is authoritative. Do not put from/to in frontmatter and do not create alternate message paths.
|
|
31
42
|
|
|
32
43
|
If the same route file already contains a not-yet-delivered message, update that file instead of creating a fragmented follow-up.
|
|
33
44
|
|
|
@@ -37,7 +48,7 @@ Use the smallest body that is complete. Include artifact refs instead of copying
|
|
|
37
48
|
|
|
38
49
|
For simple user relay, use a lightweight body instead of the formal dispatch format.
|
|
39
50
|
|
|
40
|
-
For
|
|
51
|
+
For PM dispatch, use:
|
|
41
52
|
|
|
42
53
|
\`\`\`md
|
|
43
54
|
---
|
|
@@ -56,19 +67,46 @@ Request or result:
|
|
|
56
67
|
Evidence:
|
|
57
68
|
...
|
|
58
69
|
|
|
59
|
-
|
|
70
|
+
Next gate:
|
|
71
|
+
...
|
|
72
|
+
|
|
73
|
+
Stop conditions:
|
|
60
74
|
...
|
|
61
75
|
\`\`\`
|
|
62
76
|
|
|
77
|
+
For non-PM reports, use:
|
|
78
|
+
|
|
79
|
+
\`\`\`md
|
|
80
|
+
---
|
|
81
|
+
type: result
|
|
82
|
+
artifact_refs:
|
|
83
|
+
- .ai/vcm/handoffs/example.md
|
|
84
|
+
---
|
|
85
|
+
|
|
86
|
+
Summary:
|
|
87
|
+
...
|
|
88
|
+
|
|
89
|
+
Result, blocker, or finding:
|
|
90
|
+
...
|
|
91
|
+
|
|
92
|
+
Evidence:
|
|
93
|
+
...
|
|
94
|
+
|
|
95
|
+
Requested PM decision:
|
|
96
|
+
...
|
|
97
|
+
\`\`\`
|
|
98
|
+
|
|
99
|
+
For non-PM role reports, \`Requested PM decision\` is a request for PM classification, not an instruction to route, skip gates, continue, pause, or close the task.
|
|
100
|
+
|
|
63
101
|
## Formal Body Content
|
|
64
102
|
|
|
65
103
|
Formal messages should include:
|
|
66
104
|
|
|
67
105
|
- why this message exists
|
|
68
|
-
- what the target role should do or what result is being reported
|
|
106
|
+
- what the target role should do for PM dispatch, or what result/status is being reported for non-PM reports
|
|
69
107
|
- source of truth or artifact references
|
|
70
108
|
- validation or documentation state when relevant
|
|
71
|
-
- blocker,
|
|
109
|
+
- blocker, finding, status, or PM decision needed when relevant
|
|
72
110
|
|
|
73
111
|
## Turn Rule
|
|
74
112
|
|
|
@@ -81,7 +119,9 @@ Do not:
|
|
|
81
119
|
- start a shell loop
|
|
82
120
|
- wait for another role's answer
|
|
83
121
|
- paste directly into another role terminal
|
|
84
|
-
- use Claude Code Task/Subagent
|
|
122
|
+
- use Claude Code Task/Subagent to replace VCM role routing. Coder worker
|
|
123
|
+
subagents are governed by Coder's \`vcm-coder-worker\` rules and are not
|
|
124
|
+
route-message delivery.
|
|
85
125
|
|
|
86
126
|
VCM scans pending route files after the Stop hook and delivers later replies in a new turn.
|
|
87
127
|
|
|
@@ -2,9 +2,6 @@ export function renderMessageEnvelope(message) {
|
|
|
2
2
|
const artifactRefs = message.artifactRefs.length > 0
|
|
3
3
|
? message.artifactRefs.map((artifact) => `- ${artifact}`).join("\n")
|
|
4
4
|
: "- none";
|
|
5
|
-
const routeFileExample = message.toRole === "project-manager"
|
|
6
|
-
? ".ai/vcm/handoffs/messages/project-manager-<target-role>.md"
|
|
7
|
-
: `.ai/vcm/handoffs/messages/${message.toRole}-project-manager.md`;
|
|
8
5
|
return `
|
|
9
6
|
[VCM MESSAGE]
|
|
10
7
|
id: ${message.id}
|
|
@@ -21,8 +18,8 @@ ${artifactRefs}
|
|
|
21
18
|
Instructions:
|
|
22
19
|
- Read the message and execute only within this VCM task.
|
|
23
20
|
- If you write or update a VCM route file, use the vcm-route-message skill.
|
|
24
|
-
- If
|
|
25
|
-
-
|
|
21
|
+
- If PM sends a VCM message after handling this, write or update .ai/vcm/handoffs/messages/project-manager-<target-role>.md.
|
|
22
|
+
- If a non-PM role sends a VCM message after handling this, reply only to project-manager with .ai/vcm/handoffs/messages/<your-role>-project-manager.md.
|
|
26
23
|
- After writing a route file, end this Claude Code turn immediately.
|
|
27
24
|
- Do not poll, loop, or wait for another role in this turn. VCM scans route files after your Stop hook and delivers later replies in a new turn.
|
|
28
25
|
[/VCM MESSAGE]
|
package/dist/shared/constants.js
CHANGED
|
@@ -1,21 +1,30 @@
|
|
|
1
1
|
const REQUIRED_HEADINGS = {
|
|
2
2
|
"architecture-plan": [
|
|
3
|
-
"
|
|
3
|
+
"Accepted Scope",
|
|
4
|
+
"Current Code Reality",
|
|
4
5
|
"Architecture Decision",
|
|
6
|
+
"Module/File Plan",
|
|
7
|
+
"Public Surface Impact",
|
|
5
8
|
"Scaffold Manifest",
|
|
6
|
-
"
|
|
7
|
-
"
|
|
8
|
-
"
|
|
9
|
+
"Tester Coverage Hints",
|
|
10
|
+
"Docs Impact",
|
|
11
|
+
"Known Risks",
|
|
12
|
+
"Coder Handoff Notes"
|
|
9
13
|
],
|
|
10
14
|
"known-issues": [
|
|
11
15
|
"Task Issues",
|
|
12
16
|
"Escalation To Docs"
|
|
13
17
|
],
|
|
14
|
-
"
|
|
15
|
-
"
|
|
16
|
-
"
|
|
17
|
-
"
|
|
18
|
-
"
|
|
18
|
+
"test-report": [
|
|
19
|
+
"Evidence Reviewed",
|
|
20
|
+
"Tests Added Or Updated",
|
|
21
|
+
"Commands Run Or Checked",
|
|
22
|
+
"Validation Results",
|
|
23
|
+
"Failed Expectations",
|
|
24
|
+
"Reproduction Steps",
|
|
25
|
+
"Skipped Checks With Reasons",
|
|
26
|
+
"Coverage Gaps",
|
|
27
|
+
"Blocking Validation Issues"
|
|
19
28
|
],
|
|
20
29
|
"docs-sync-report": [
|
|
21
30
|
"Summary",
|
|
@@ -34,6 +43,7 @@ const REQUIRED_HEADINGS = {
|
|
|
34
43
|
"Validation Summary",
|
|
35
44
|
"Review And Docs Sync",
|
|
36
45
|
"Known Issues Disposition",
|
|
46
|
+
"Gate Review Gates",
|
|
37
47
|
"Cleanup Readiness",
|
|
38
48
|
"Final User Summary"
|
|
39
49
|
]
|
|
@@ -48,6 +58,7 @@ export function checkMarkdownArtifact(kind, artifactPath, content) {
|
|
|
48
58
|
isEmpty: true,
|
|
49
59
|
hasPlaceholder: false,
|
|
50
60
|
missingHeadings: [...REQUIRED_HEADINGS[kind]],
|
|
61
|
+
invalidFields: [],
|
|
51
62
|
status: "missing"
|
|
52
63
|
};
|
|
53
64
|
}
|
|
@@ -60,11 +71,13 @@ export function checkMarkdownArtifact(kind, artifactPath, content) {
|
|
|
60
71
|
isEmpty: true,
|
|
61
72
|
hasPlaceholder: false,
|
|
62
73
|
missingHeadings: [...REQUIRED_HEADINGS[kind]],
|
|
74
|
+
invalidFields: [],
|
|
63
75
|
status: "empty"
|
|
64
76
|
};
|
|
65
77
|
}
|
|
66
78
|
const missingHeadings = REQUIRED_HEADINGS[kind].filter((heading) => !hasHeading(trimmed, heading));
|
|
67
79
|
const hasPlaceholder = PLACEHOLDER_PATTERN.test(trimmed);
|
|
80
|
+
const invalidFields = validateArtifactFields(kind, trimmed);
|
|
68
81
|
return {
|
|
69
82
|
kind,
|
|
70
83
|
path: artifactPath,
|
|
@@ -72,9 +85,50 @@ export function checkMarkdownArtifact(kind, artifactPath, content) {
|
|
|
72
85
|
isEmpty: false,
|
|
73
86
|
hasPlaceholder,
|
|
74
87
|
missingHeadings,
|
|
75
|
-
|
|
88
|
+
invalidFields,
|
|
89
|
+
status: missingHeadings.length === 0 && !hasPlaceholder && invalidFields.length === 0 ? "ok" : "incomplete"
|
|
76
90
|
};
|
|
77
91
|
}
|
|
92
|
+
function validateArtifactFields(kind, content) {
|
|
93
|
+
if (kind === "test-report") {
|
|
94
|
+
const result = /^\s*Test Result\s*:\s*(\S+)\s*$/im.exec(content)?.[1]?.toLowerCase();
|
|
95
|
+
return result === "pass" || result === "fail"
|
|
96
|
+
? []
|
|
97
|
+
: ["Test Result must be pass or fail."];
|
|
98
|
+
}
|
|
99
|
+
if (kind === "docs-sync-report") {
|
|
100
|
+
return validateDecision(content, ["synced", "unchanged", "blocked"]);
|
|
101
|
+
}
|
|
102
|
+
if (kind === "final-acceptance") {
|
|
103
|
+
return validateDecision(content, [
|
|
104
|
+
"accepted",
|
|
105
|
+
"accepted-with-known-risks",
|
|
106
|
+
"needs-coder-follow-up",
|
|
107
|
+
"needs-architect-follow-up",
|
|
108
|
+
"needs-docs-sync",
|
|
109
|
+
"blocked-by-user-decision"
|
|
110
|
+
]);
|
|
111
|
+
}
|
|
112
|
+
return [];
|
|
113
|
+
}
|
|
114
|
+
function validateDecision(content, allowed) {
|
|
115
|
+
const decision = readArtifactSectionValue(content, "Decision")?.toLowerCase();
|
|
116
|
+
return decision && allowed.includes(decision)
|
|
117
|
+
? []
|
|
118
|
+
: [`Decision must be one of: ${allowed.join(", ")}.`];
|
|
119
|
+
}
|
|
120
|
+
export function readArtifactSectionValue(content, heading) {
|
|
121
|
+
const match = new RegExp(`^#{1,6}\\s+${escapeRegExp(heading)}\\s*$`, "im").exec(content);
|
|
122
|
+
if (!match || match.index === undefined) {
|
|
123
|
+
return undefined;
|
|
124
|
+
}
|
|
125
|
+
const afterHeading = content.slice(match.index + match[0].length);
|
|
126
|
+
const nextHeading = /\n#{1,6}\s+\S/.exec(afterHeading);
|
|
127
|
+
const section = nextHeading?.index === undefined
|
|
128
|
+
? afterHeading
|
|
129
|
+
: afterHeading.slice(0, nextHeading.index);
|
|
130
|
+
return section.split(/\r?\n/).map((line) => line.trim()).find(Boolean);
|
|
131
|
+
}
|
|
78
132
|
function hasHeading(content, heading) {
|
|
79
133
|
const pattern = new RegExp(`^#{1,6}\\s+${escapeRegExp(heading)}\\s*$`, "im");
|
|
80
134
|
return pattern.test(content);
|