clud-bug 0.6.34 → 0.7.0-rc.2

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.
Files changed (110) hide show
  1. package/bin/clud-bug.js +10 -1353
  2. package/dist/cli/agents-md.d.ts +16 -0
  3. package/dist/cli/agents-md.d.ts.map +1 -0
  4. package/dist/cli/agents-md.js +226 -0
  5. package/dist/cli/agents-md.js.map +1 -0
  6. package/dist/cli/audit.d.ts +13 -0
  7. package/dist/cli/audit.d.ts.map +1 -0
  8. package/dist/cli/audit.js +90 -0
  9. package/dist/cli/audit.js.map +1 -0
  10. package/dist/cli/branch-protection.d.ts +57 -0
  11. package/dist/cli/branch-protection.d.ts.map +1 -0
  12. package/dist/cli/branch-protection.js +118 -0
  13. package/dist/cli/branch-protection.js.map +1 -0
  14. package/dist/cli/edit-workflow.d.ts +18 -0
  15. package/dist/cli/edit-workflow.d.ts.map +1 -0
  16. package/dist/cli/edit-workflow.js +43 -0
  17. package/dist/cli/edit-workflow.js.map +1 -0
  18. package/dist/cli/index.d.ts +8 -0
  19. package/dist/cli/index.d.ts.map +1 -0
  20. package/dist/cli/index.js +18 -0
  21. package/dist/cli/index.js.map +1 -0
  22. package/dist/cli/main.d.ts +3 -0
  23. package/dist/cli/main.d.ts.map +1 -0
  24. package/dist/cli/main.js +1336 -0
  25. package/dist/cli/main.js.map +1 -0
  26. package/dist/cli/skill-usage.d.ts +109 -0
  27. package/dist/cli/skill-usage.d.ts.map +1 -0
  28. package/dist/cli/skill-usage.js +380 -0
  29. package/dist/cli/skill-usage.js.map +1 -0
  30. package/dist/cli/skills.d.ts +56 -0
  31. package/dist/cli/skills.d.ts.map +1 -0
  32. package/dist/cli/skills.js +292 -0
  33. package/dist/cli/skills.js.map +1 -0
  34. package/dist/cli/update.d.ts +29 -0
  35. package/dist/cli/update.d.ts.map +1 -0
  36. package/dist/cli/update.js +186 -0
  37. package/dist/cli/update.js.map +1 -0
  38. package/dist/cli/usage.d.ts +142 -0
  39. package/dist/cli/usage.d.ts.map +1 -0
  40. package/dist/cli/usage.js +348 -0
  41. package/dist/cli/usage.js.map +1 -0
  42. package/dist/core/audit.d.ts +8 -0
  43. package/dist/core/audit.d.ts.map +1 -0
  44. package/dist/core/audit.js +47 -0
  45. package/dist/core/audit.js.map +1 -0
  46. package/dist/core/detect.d.ts +77 -0
  47. package/dist/core/detect.d.ts.map +1 -0
  48. package/dist/core/detect.js +262 -0
  49. package/dist/core/detect.js.map +1 -0
  50. package/dist/core/index.d.ts +11 -0
  51. package/dist/core/index.d.ts.map +1 -0
  52. package/dist/core/index.js +31 -0
  53. package/dist/core/index.js.map +1 -0
  54. package/dist/core/prompt-builder.d.ts +164 -0
  55. package/dist/core/prompt-builder.d.ts.map +1 -0
  56. package/dist/core/prompt-builder.js +419 -0
  57. package/dist/core/prompt-builder.js.map +1 -0
  58. package/dist/core/prompts.d.ts +9 -0
  59. package/dist/core/prompts.d.ts.map +1 -0
  60. package/dist/core/prompts.js +401 -0
  61. package/dist/core/prompts.js.map +1 -0
  62. package/dist/core/render-review.d.ts +6 -0
  63. package/dist/core/render-review.d.ts.map +1 -0
  64. package/dist/core/render-review.js +219 -0
  65. package/dist/core/render-review.js.map +1 -0
  66. package/dist/core/render.d.ts +13 -0
  67. package/dist/core/render.d.ts.map +1 -0
  68. package/dist/core/render.js +80 -0
  69. package/dist/core/render.js.map +1 -0
  70. package/dist/core/review-schema-zod.d.ts +240 -0
  71. package/dist/core/review-schema-zod.d.ts.map +1 -0
  72. package/dist/core/review-schema-zod.js +218 -0
  73. package/dist/core/review-schema-zod.js.map +1 -0
  74. package/dist/core/review-schema.d.ts +42 -0
  75. package/dist/core/review-schema.d.ts.map +1 -0
  76. package/dist/core/review-schema.js +156 -0
  77. package/dist/core/review-schema.js.map +1 -0
  78. package/dist/core/review-writeback.d.ts +139 -0
  79. package/dist/core/review-writeback.d.ts.map +1 -0
  80. package/dist/core/review-writeback.js +313 -0
  81. package/dist/core/review-writeback.js.map +1 -0
  82. package/dist/core/skills.d.ts +122 -0
  83. package/dist/core/skills.d.ts.map +1 -0
  84. package/dist/core/skills.js +636 -0
  85. package/dist/core/skills.js.map +1 -0
  86. package/package.json +30 -4
  87. package/{lib/agents-md.js → src/cli/agents-md.ts} +25 -14
  88. package/{lib/audit.js → src/cli/audit.ts} +37 -44
  89. package/{lib/branch-protection.js → src/cli/branch-protection.ts} +75 -11
  90. package/{lib/edit-workflow.js → src/cli/edit-workflow.ts} +32 -11
  91. package/src/cli/index.ts +101 -0
  92. package/src/cli/main.ts +1376 -0
  93. package/{lib/skill-usage.js → src/cli/skill-usage.ts} +168 -94
  94. package/src/cli/skills.ts +386 -0
  95. package/{lib/update.js → src/cli/update.ts} +68 -27
  96. package/{lib/usage.js → src/cli/usage.ts} +167 -76
  97. package/src/core/audit.ts +53 -0
  98. package/{lib/detect.js → src/core/detect.ts} +100 -47
  99. package/src/core/index.ts +155 -0
  100. package/src/core/prompt-builder.ts +561 -0
  101. package/{lib/prompts.js → src/core/prompts.ts} +16 -2
  102. package/{lib/render-review.js → src/core/render-review.ts} +57 -25
  103. package/{lib/render.js → src/core/render.ts} +36 -10
  104. package/src/core/review-schema-zod.ts +262 -0
  105. package/{lib/review-schema.js → src/core/review-schema.ts} +68 -5
  106. package/src/core/review-writeback.ts +446 -0
  107. package/{lib/skills.js → src/core/skills.ts} +339 -342
  108. package/templates/workflow-py.yml.tmpl +2 -2
  109. package/templates/workflow-ts.yml.tmpl +2 -2
  110. package/templates/workflow.yml.tmpl +17 -8
@@ -0,0 +1,156 @@
1
+ // JSON Schema for clud-bug review structured output (0.0.O / v0.6.22).
2
+ //
3
+ // Passed to claude-code-action via `claude_args: --json-schema '<JSON>'`.
4
+ // The Agent SDK validates the LLM's emitted JSON against this schema and
5
+ // re-prompts on mismatch (internal retry; not a clud-bug-level loop).
6
+ //
7
+ // Schema design choices:
8
+ // - Flat top-level — composite-action outputs are a single string, so we
9
+ // fromJSON() once and pluck fields. No deep nesting that would force
10
+ // extra path traversal in the post-step shell.
11
+ // - Word/char caps in `description:` — the SDK doc names these as the
12
+ // primary lever for keeping output cheap. They're advisory (the SDK
13
+ // does not enforce numeric caps; the LLM treats them as instruction).
14
+ // 0.0.X already lives in the prompt, so the schema description here is
15
+ // a complementary belt-and-suspenders signal.
16
+ // - Required minimum — only the fields a renderer absolutely needs to
17
+ // produce a valid summary comment. Counts are always required (the
18
+ // stats header + status block depend on them); finding arrays are
19
+ // required but may be empty (a clean review has 0 findings, not
20
+ // missing arrays).
21
+ // - `additionalProperties: false` on every object — schema-strict mode.
22
+ // Anthropic's structured-outputs doc explicitly recommends this to
23
+ // keep the model from inventing fields.
24
+ //
25
+ // Bumped via deliberate edit; not derived from a TypeScript type. The
26
+ // rendering side (./render-review.ts) treats unknown fields permissively
27
+ // — schema and renderer can drift up to one minor version safely.
28
+ const FINDING_ITEM = {
29
+ type: 'object',
30
+ additionalProperties: false,
31
+ properties: {
32
+ skill: {
33
+ type: 'string',
34
+ description: 'The skill name in brackets, e.g. "critical-issues-only". Must match a loaded skill or "(none)".',
35
+ },
36
+ file: {
37
+ type: 'string',
38
+ description: 'Path of the affected file relative to repo root. Optional when the finding is cross-cutting.',
39
+ },
40
+ line: {
41
+ type: 'integer',
42
+ minimum: 1,
43
+ description: 'Line number in the affected file. Required when `file` is set.',
44
+ },
45
+ summary: {
46
+ type: 'string',
47
+ description: 'One sentence stating the claim. Max ~20 words; no trailing period (the renderer adds one).',
48
+ },
49
+ reasoning: {
50
+ type: 'string',
51
+ description: 'Evidence anchor + suggested fix. Max ~80 words. Rendered inside <details> block; can be omitted for self-evident findings.',
52
+ },
53
+ },
54
+ required: ['skill', 'summary'],
55
+ };
56
+ const PER_SKILL_SCAN_ITEM = {
57
+ type: 'object',
58
+ additionalProperties: false,
59
+ properties: {
60
+ skill: { type: 'string' },
61
+ outcome: {
62
+ type: 'string',
63
+ description: 'One sentence describing what the skill found. Max ~15 words. Examples: "scanned all paths. 2 critical findings below.", "0 findings.", "not applicable to this diff."',
64
+ },
65
+ },
66
+ required: ['skill', 'outcome'],
67
+ };
68
+ export const REVIEW_SCHEMA = {
69
+ type: 'object',
70
+ additionalProperties: false,
71
+ properties: {
72
+ status_header: {
73
+ type: 'string',
74
+ enum: ['critical findings', 'clean', 'bare'],
75
+ description: 'Strict-mode opt-in repos: `critical findings` when ANY 🔴 finding exists, otherwise `clean`. Non-strict-mode repos (the default): emit `bare` — the renderer produces a `## 🐛 Clud Bug review` H2 with no suffix, matching the v0.6.21- behaviour. Check .claude/skills/.clud-bug.json for `strictMode: true` to pick critical/clean vs bare.',
76
+ },
77
+ summary_counts: {
78
+ type: 'object',
79
+ additionalProperties: false,
80
+ properties: {
81
+ critical: { type: 'integer', minimum: 0 },
82
+ minor: { type: 'integer', minimum: 0 },
83
+ preexisting: { type: 'integer', minimum: 0 },
84
+ resolved_from_prior: { type: 'integer', minimum: 0 },
85
+ still_open: { type: 'integer', minimum: 0 },
86
+ },
87
+ required: ['critical', 'minor', 'preexisting', 'resolved_from_prior', 'still_open'],
88
+ },
89
+ per_skill_scan: {
90
+ type: 'array',
91
+ description: 'One entry per LOADED skill — even silent ones. Empty when no skills are installed.',
92
+ items: PER_SKILL_SCAN_ITEM,
93
+ },
94
+ critical_findings: {
95
+ type: 'array',
96
+ description: 'NEW 🔴 findings (bugs, security, perf, missing test coverage). May be empty.',
97
+ items: FINDING_ITEM,
98
+ },
99
+ minor_findings: {
100
+ type: 'array',
101
+ description: 'NEW 🟡 findings (nits, style, observations). May be empty.',
102
+ items: FINDING_ITEM,
103
+ },
104
+ preexisting_findings: {
105
+ type: 'array',
106
+ description: 'NEW 🟣 findings (issues that pre-date this PR). May be empty.',
107
+ items: FINDING_ITEM,
108
+ },
109
+ dedicated_sections: {
110
+ type: 'array',
111
+ description: 'Per-dedicated-mode-skill section blocks. Each item carries the section header text and its findings.',
112
+ items: {
113
+ type: 'object',
114
+ additionalProperties: false,
115
+ properties: {
116
+ section_name: { type: 'string', description: 'Human-readable section title, e.g. "Brand voice".' },
117
+ skill: { type: 'string', description: 'The dedicated skill name.' },
118
+ findings: { type: 'array', items: FINDING_ITEM },
119
+ },
120
+ required: ['section_name', 'skill', 'findings'],
121
+ },
122
+ },
123
+ diagnostics: {
124
+ type: 'array',
125
+ description: '0.0.T tee-hint diagnostics. One line per `head -c` cap that fired during fetch. Empty when no truncation occurred.',
126
+ items: { type: 'string' },
127
+ },
128
+ skills_referenced: {
129
+ type: 'array',
130
+ description: 'Names of every skill cited in any finding. Empty list (or ["(none)"]) when no skill applied.',
131
+ items: { type: 'string' },
132
+ },
133
+ last_reviewed_sha: {
134
+ type: 'string',
135
+ description: 'The HEAD SHA at review time, used by the incremental-diff handshake. Set to the literal value of the workflow env var $HEAD_SHA.',
136
+ },
137
+ },
138
+ required: [
139
+ 'status_header',
140
+ 'summary_counts',
141
+ 'per_skill_scan',
142
+ 'critical_findings',
143
+ 'minor_findings',
144
+ 'preexisting_findings',
145
+ 'skills_referenced',
146
+ 'last_reviewed_sha',
147
+ ],
148
+ };
149
+ // Serialize the schema for inclusion in workflow templates as the
150
+ // `--json-schema '<JSON>'` argument. Single-line (the workflow YAML uses
151
+ // the pipe block; single-quoted JSON inside that needs to stay flat to
152
+ // avoid YAML parser surprises with embedded newlines).
153
+ export function serializedReviewSchema() {
154
+ return JSON.stringify(REVIEW_SCHEMA);
155
+ }
156
+ //# sourceMappingURL=review-schema.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"review-schema.js","sourceRoot":"","sources":["../../src/core/review-schema.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,139 @@
1
+ import { type Finding, type Review } from './review-schema-zod.js';
2
+ /** Protocol version this implementation emits. */
3
+ export declare const PROTOCOL_VERSION = "0.1.0";
4
+ /** "Written by" tag for the App writeback (SPEC §6.1). */
5
+ export declare const WRITTEN_BY = "clud-bug[bot]";
6
+ export declare const SEVERITY_EMOJI: {
7
+ readonly critical: "🔴";
8
+ readonly minor: "🟡";
9
+ readonly preexisting: "🟣";
10
+ };
11
+ export interface RenderReviewFileInput {
12
+ review: Review;
13
+ prNumber: number;
14
+ /** 40-char head SHA. Pinned to `<!-- review-sha: ... -->`. */
15
+ headSha: string;
16
+ /** GitHub PR URL — appended verbatim to the trailing rule. */
17
+ prUrl: string;
18
+ }
19
+ /**
20
+ * Renders the review object to the SPEC §1.8.1 markdown template.
21
+ *
22
+ * Pure: no I/O, no time-of-day, no provider info — fixture-stable.
23
+ *
24
+ * NB: This produces the doc-file shape (`# clud-bug review — PR #N` H1).
25
+ * The CLI's `renderReview` produces the PR-comment shape (`## 🐛 Clud Bug
26
+ * review` H2). Both are valid review outputs; SPEC §6.2 says they share
27
+ * the underlying finding data but differ in container.
28
+ */
29
+ export declare function renderReviewFile(input: RenderReviewFileInput): string;
30
+ /**
31
+ * Provenance label for a single finding's attribution from one pass.
32
+ * Mirrors the App's `PassSource` discriminator.
33
+ *
34
+ * `mode === 'cross-check'`:
35
+ * - 'first' → finding raised by Pass 1
36
+ * - 'agreed' → later pass agreed
37
+ * - 'disagreed' → later pass disagreed
38
+ * - 'independent' → later pass surfaced this finding independently
39
+ *
40
+ * `mode === 'consensus'`:
41
+ * - 'first' → finding tuple unique to Pass 1
42
+ * - 'independent' → finding tuple unique to Pass N (N > 1)
43
+ * - 'agreed' → finding tuple appeared in 2+ passes (consensus)
44
+ */
45
+ export type PassSource = 'first' | 'agreed' | 'disagreed' | 'independent';
46
+ export interface PassAttribution {
47
+ /** 1-indexed pass number — matches the spec's "[Pass N]" label. */
48
+ passNumber: number;
49
+ /** Role display name, e.g. "Beetle". */
50
+ roleName: string;
51
+ /** Model slug for this pass — used by the renderer for the "· Sonnet 4.6" tail. */
52
+ model: string;
53
+ /** Provenance — see PassSource doc. */
54
+ source: PassSource;
55
+ /** Optional one-line note from the pass, e.g. cross-check rationale. */
56
+ note?: string;
57
+ }
58
+ export interface UnifiedFinding extends Finding {
59
+ /** One PassAttribution per pass involved with this finding. Order: by passNumber. */
60
+ attributions: PassAttribution[];
61
+ }
62
+ /** Effective resolution verdict the multi-pass orchestrator emits. */
63
+ export type MultiPassVerdict = 'request_changes' | 'review_only' | 'clean';
64
+ /** Effective multi-pass mode. */
65
+ export type ReviewPassMode = 'cross-check' | 'consensus' | 'independent';
66
+ export interface MultiPassReview {
67
+ /** Status header — derived from aggregated findings + mode resolution rules. */
68
+ status_header: Review['status_header'];
69
+ /** Summary counts, derived from the unified findings list. */
70
+ summary_counts: Review['summary_counts'];
71
+ /** Skills cited at least once across any pass. */
72
+ skills_referenced: string[];
73
+ /** Unified findings, with per-pass attribution. */
74
+ findings: UnifiedFinding[];
75
+ /** Effective mode (for the renderer's "(N passes · mode)" header line). */
76
+ mode: ReviewPassMode;
77
+ /** Number of passes that actually ran. */
78
+ passCount: number;
79
+ /** Role labels per pass, parallel to passCount. Used by the renderer. */
80
+ roles: Array<{
81
+ passNumber: number;
82
+ roleName: string;
83
+ model: string;
84
+ }>;
85
+ /** Resolution verdict — see App's multi-pass-aggregator for derivation. */
86
+ verdict: MultiPassVerdict;
87
+ }
88
+ export interface RenderMultiPassMarkdownInput {
89
+ review: MultiPassReview;
90
+ prNumber: number;
91
+ /** 40-char head SHA. Pinned to `<!-- review-sha: ... -->`. */
92
+ headSha: string;
93
+ /** GitHub PR URL — appended verbatim to the trailing rule. */
94
+ prUrl: string;
95
+ }
96
+ /**
97
+ * Renders a multi-pass review with per-pass attribution lines.
98
+ *
99
+ * Output layout (SPEC §1.8.5):
100
+ *
101
+ * # clud-bug review — PR #N (M passes · mode)
102
+ * <!-- protocol-version: ... -->
103
+ * <!-- written-by: clud-bug[bot] -->
104
+ * <!-- review-sha: ... -->
105
+ * <!-- passes: M -->
106
+ * <!-- mode: cross-check|consensus|independent -->
107
+ *
108
+ * **Summary:** ... · **Verdict:** request_changes / review_only / clean
109
+ *
110
+ * **Reviewers:**
111
+ * - Pass 1 — Beetle · anthropic/claude-sonnet-4.6
112
+ * - Pass 2 — Wasp · anthropic/claude-opus-4.7
113
+ *
114
+ * **Skills cited:** ...
115
+ *
116
+ * **Findings:**
117
+ *
118
+ * ### (red) Critical
119
+ * - [Pass 1 — Beetle · Sonnet 4.6] auth.ts:42 — race-conditions: Race condition
120
+ * Reasoning: ...
121
+ * [Pass 2 — Wasp · Opus 4.7]: (check) AGREED — same finding identified independently.
122
+ *
123
+ * ...
124
+ *
125
+ * ---
126
+ * [Link to PR](...)
127
+ *
128
+ * Pure: no I/O, no time-of-day, fixture-stable.
129
+ */
130
+ export declare function renderMultiPassMarkdown(input: RenderMultiPassMarkdownInput): string;
131
+ /** SPEC §6.1 / §1.8 path. The App's Octokit writeback uses this. */
132
+ export declare function reviewFilePath(prNumber: number): string;
133
+ /**
134
+ * SPEC §6.1 commit message: exactly `[skip-logmind] clud-bug review: PR #<n>`.
135
+ * The `[skip-logmind]` prefix tells `check-decisions.yml` to ignore this
136
+ * commit (SPEC §6.4). The App's Octokit writeback uses this.
137
+ */
138
+ export declare function reviewCommitMessage(prNumber: number): string;
139
+ //# sourceMappingURL=review-writeback.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"review-writeback.d.ts","sourceRoot":"","sources":["../../src/core/review-writeback.ts"],"names":[],"mappings":"AAwBA,OAAO,EAIL,KAAK,OAAO,EACZ,KAAK,MAAM,EACZ,MAAM,wBAAwB,CAAC;AAEhC,kDAAkD;AAClD,eAAO,MAAM,gBAAgB,UAAU,CAAC;AAExC,0DAA0D;AAC1D,eAAO,MAAM,UAAU,kBAAkB,CAAC;AAM1C,eAAO,MAAM,cAAc;;;;CAIjB,CAAC;AAEX,MAAM,WAAW,qBAAqB;IACpC,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,8DAA8D;IAC9D,OAAO,EAAE,MAAM,CAAC;IAChB,8DAA8D;IAC9D,KAAK,EAAE,MAAM,CAAC;CACf;AAED;;;;;;;;;GASG;AACH,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,qBAAqB,GAAG,MAAM,CAsErE;AAkCD;;;;;;;;;;;;;;GAcG;AACH,MAAM,MAAM,UAAU,GAAG,OAAO,GAAG,QAAQ,GAAG,WAAW,GAAG,aAAa,CAAC;AAE1E,MAAM,WAAW,eAAe;IAC9B,mEAAmE;IACnE,UAAU,EAAE,MAAM,CAAC;IACnB,wCAAwC;IACxC,QAAQ,EAAE,MAAM,CAAC;IACjB,mFAAmF;IACnF,KAAK,EAAE,MAAM,CAAC;IACd,uCAAuC;IACvC,MAAM,EAAE,UAAU,CAAC;IACnB,wEAAwE;IACxE,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,cAAe,SAAQ,OAAO;IAC7C,qFAAqF;IACrF,YAAY,EAAE,eAAe,EAAE,CAAC;CACjC;AAED,sEAAsE;AACtE,MAAM,MAAM,gBAAgB,GAAG,iBAAiB,GAAG,aAAa,GAAG,OAAO,CAAC;AAE3E,iCAAiC;AACjC,MAAM,MAAM,cAAc,GAAG,aAAa,GAAG,WAAW,GAAG,aAAa,CAAC;AAEzE,MAAM,WAAW,eAAe;IAC9B,gFAAgF;IAChF,aAAa,EAAE,MAAM,CAAC,eAAe,CAAC,CAAC;IACvC,8DAA8D;IAC9D,cAAc,EAAE,MAAM,CAAC,gBAAgB,CAAC,CAAC;IACzC,kDAAkD;IAClD,iBAAiB,EAAE,MAAM,EAAE,CAAC;IAC5B,mDAAmD;IACnD,QAAQ,EAAE,cAAc,EAAE,CAAC;IAC3B,2EAA2E;IAC3E,IAAI,EAAE,cAAc,CAAC;IACrB,0CAA0C;IAC1C,SAAS,EAAE,MAAM,CAAC;IAClB,yEAAyE;IACzE,KAAK,EAAE,KAAK,CAAC;QAAE,UAAU,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IACtE,2EAA2E;IAC3E,OAAO,EAAE,gBAAgB,CAAC;CAC3B;AAED,MAAM,WAAW,4BAA4B;IAC3C,MAAM,EAAE,eAAe,CAAC;IACxB,QAAQ,EAAE,MAAM,CAAC;IACjB,8DAA8D;IAC9D,OAAO,EAAE,MAAM,CAAC;IAChB,8DAA8D;IAC9D,KAAK,EAAE,MAAM,CAAC;CACf;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiCG;AACH,wBAAgB,uBAAuB,CACrC,KAAK,EAAE,4BAA4B,GAClC,MAAM,CAmER;AA0FD,oEAAoE;AACpE,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAEvD;AAED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAE5D"}
@@ -0,0 +1,313 @@
1
+ // SPEC §1.8.1 doc-file renderer for `docs/reviews/PR-<n>.md`.
2
+ //
3
+ // This is the PURE rendering half of the App's `lib/review-writeback.ts`.
4
+ // The Octokit-side WRITEBACK (branch detection, idempotent rewrite,
5
+ // Contents-API commit) stays App-side — that surface depends on Octokit
6
+ // which we don't want to pull into core.
7
+ //
8
+ // Renamed from the App's `renderReview` to `renderReviewFile` to avoid
9
+ // colliding with the CLI's existing `renderReview` (which renders the
10
+ // summary-PR-comment shape, not the doc-file). Both renderers coexist:
11
+ // - `renderReview` (./render-review.ts) → `## 🐛 Clud Bug review` PR comment
12
+ // - `renderReviewFile` (this module) → `# clud-bug review — PR #N` doc file
13
+ //
14
+ // SPEC pins honored here:
15
+ // - `<!-- protocol-version: 0.1.0 -->` — SPEC version.
16
+ // - `<!-- written-by: clud-bug[bot] -->` — App identity, not Action.
17
+ // - `<!-- review-sha: <40-char-head-sha> -->` — pinned to review-time HEAD.
18
+ // - Severity bucket order: red → yellow → purple.
19
+ // - Empty buckets omitted entirely (no empty headers).
20
+ // - "Resolved this round:" and "Still open:" blocks omitted when empty
21
+ // (D.2.0 always omits — multi-pass is D.2.5).
22
+ // - Trailing `---\n[Link to PR](<url>)` line preserved verbatim.
23
+ // - Emoji codepoints: U+1F534, U+1F7E1, U+1F7E3, NFC-normalized.
24
+ import { deriveSkillsReferenced, deriveSummaryCounts, flattenFindings, } from './review-schema-zod.js';
25
+ /** Protocol version this implementation emits. */
26
+ export const PROTOCOL_VERSION = '0.1.0';
27
+ /** "Written by" tag for the App writeback (SPEC §6.1). */
28
+ export const WRITTEN_BY = 'clud-bug[bot]';
29
+ // Severity emoji per SPEC §1.8.1. We define them by codepoint so a stray
30
+ // editor that switches encoding can't silently break byte-equality with
31
+ // the Action-runner output. Same constants as render-review.ts but kept
32
+ // local so this module is independent of the CLI renderer.
33
+ export const SEVERITY_EMOJI = {
34
+ critical: '\u{1F534}', // U+1F534 RED CIRCLE
35
+ minor: '\u{1F7E1}', // U+1F7E1 YELLOW CIRCLE
36
+ preexisting: '\u{1F7E3}', // U+1F7E3 PURPLE CIRCLE
37
+ };
38
+ /**
39
+ * Renders the review object to the SPEC §1.8.1 markdown template.
40
+ *
41
+ * Pure: no I/O, no time-of-day, no provider info — fixture-stable.
42
+ *
43
+ * NB: This produces the doc-file shape (`# clud-bug review — PR #N` H1).
44
+ * The CLI's `renderReview` produces the PR-comment shape (`## 🐛 Clud Bug
45
+ * review` H2). Both are valid review outputs; SPEC §6.2 says they share
46
+ * the underlying finding data but differ in container.
47
+ */
48
+ export function renderReviewFile(input) {
49
+ const { review, prNumber, headSha, prUrl } = input;
50
+ // Wire-shape Review carries findings in 3 severity arrays. Flatten to
51
+ // internal `Finding[]` so the renderer's bucketing, count-derivation,
52
+ // and per-skill aggregation can work uniformly.
53
+ const findings = flattenFindings(review);
54
+ // Always derive these from findings to guarantee they match what we
55
+ // actually render. The model can drift on counts; we don't trust it.
56
+ const counts = deriveSummaryCounts(findings);
57
+ const skillsReferenced = deriveSkillsReferenced(findings);
58
+ const lines = [];
59
+ lines.push(`# clud-bug review — PR #${prNumber}`);
60
+ lines.push(`<!-- protocol-version: ${PROTOCOL_VERSION} -->`);
61
+ lines.push(`<!-- written-by: ${WRITTEN_BY} -->`);
62
+ lines.push(`<!-- review-sha: ${headSha} -->`);
63
+ lines.push('');
64
+ // Summary line — SPEC §1.8.1 wording.
65
+ lines.push(`**Summary:** ${counts.critical} critical · ${counts.minor} minor · ${counts.preexisting} preexisting · ${counts.resolved_from_prior} resolved-from-prior · ${counts.still_open} still-open`);
66
+ lines.push('');
67
+ // Skills cited block — group findings per skill for citation counts.
68
+ lines.push('**Skills cited:**');
69
+ if (skillsReferenced.length === 0) {
70
+ lines.push('- _(none — see summary above)_');
71
+ }
72
+ else {
73
+ for (const slug of skillsReferenced) {
74
+ const count = findings.filter((f) => f.skill === slug).length;
75
+ lines.push(`- ${slug} (${count} finding${count === 1 ? '' : 's'})`);
76
+ }
77
+ }
78
+ lines.push('');
79
+ lines.push('**Findings:**');
80
+ lines.push('');
81
+ // Severity buckets in SPEC order; empty buckets are omitted entirely.
82
+ const bucketed = bucketBySeverity(findings);
83
+ if (bucketed.critical.length > 0) {
84
+ lines.push(`### ${SEVERITY_EMOJI.critical} Critical`);
85
+ for (const f of bucketed.critical)
86
+ lines.push(renderFinding(f, true));
87
+ lines.push('');
88
+ }
89
+ if (bucketed.minor.length > 0) {
90
+ lines.push(`### ${SEVERITY_EMOJI.minor} Minor`);
91
+ for (const f of bucketed.minor)
92
+ lines.push(renderFinding(f, false));
93
+ lines.push('');
94
+ }
95
+ if (bucketed.preexisting.length > 0) {
96
+ lines.push(`### ${SEVERITY_EMOJI.preexisting} Preexisting (informational)`);
97
+ for (const f of bucketed.preexisting)
98
+ lines.push(renderFinding(f, false));
99
+ lines.push('');
100
+ }
101
+ // D.2.0 never emits "Resolved this round" / "Still open" — both lists
102
+ // are empty until D.2.5 (multi-pass tracking). SPEC §1.8.1 says these
103
+ // blocks MUST be omitted when empty.
104
+ lines.push('---');
105
+ lines.push('');
106
+ lines.push(`[Link to PR](${prUrl})`);
107
+ // Final NFC normalization — guarantees the emoji codepoints stay
108
+ // composed even if a future renderer step decomposes them.
109
+ return lines.join('\n').normalize('NFC') + '\n';
110
+ }
111
+ function bucketBySeverity(findings) {
112
+ return {
113
+ critical: findings.filter((f) => f.severity === 'critical'),
114
+ minor: findings.filter((f) => f.severity === 'minor'),
115
+ preexisting: findings.filter((f) => f.severity === 'preexisting'),
116
+ };
117
+ }
118
+ function renderFinding(f, includeReasoning) {
119
+ // findingItemSchema.file is z.string().optional() — the model is
120
+ // instructed to always provide it, but Zod doesn't enforce. Without
121
+ // the fallback an absent file would emit literal "undefined" in the
122
+ // committed SPEC §1.8.1 doc file. clud-bug-review #158 flagged this.
123
+ const fileLabel = f.file ?? '(unknown file)';
124
+ const location = f.line ? `${fileLabel}:${f.line}` : fileLabel;
125
+ // Per SPEC §1.8.1: "**<file>:<line>** — <skill-name>: <one-line summary>".
126
+ const head = `- **${location}** — ${f.skill}: ${f.summary}`;
127
+ // Reasoning line is documented for the Critical bucket; we follow the
128
+ // SPEC template strictly. For Minor/Preexisting, no reasoning line.
129
+ if (includeReasoning && f.reasoning) {
130
+ return `${head}\n Reasoning: ${f.reasoning}`;
131
+ }
132
+ return head;
133
+ }
134
+ /**
135
+ * Renders a multi-pass review with per-pass attribution lines.
136
+ *
137
+ * Output layout (SPEC §1.8.5):
138
+ *
139
+ * # clud-bug review — PR #N (M passes · mode)
140
+ * <!-- protocol-version: ... -->
141
+ * <!-- written-by: clud-bug[bot] -->
142
+ * <!-- review-sha: ... -->
143
+ * <!-- passes: M -->
144
+ * <!-- mode: cross-check|consensus|independent -->
145
+ *
146
+ * **Summary:** ... · **Verdict:** request_changes / review_only / clean
147
+ *
148
+ * **Reviewers:**
149
+ * - Pass 1 — Beetle · anthropic/claude-sonnet-4.6
150
+ * - Pass 2 — Wasp · anthropic/claude-opus-4.7
151
+ *
152
+ * **Skills cited:** ...
153
+ *
154
+ * **Findings:**
155
+ *
156
+ * ### (red) Critical
157
+ * - [Pass 1 — Beetle · Sonnet 4.6] auth.ts:42 — race-conditions: Race condition
158
+ * Reasoning: ...
159
+ * [Pass 2 — Wasp · Opus 4.7]: (check) AGREED — same finding identified independently.
160
+ *
161
+ * ...
162
+ *
163
+ * ---
164
+ * [Link to PR](...)
165
+ *
166
+ * Pure: no I/O, no time-of-day, fixture-stable.
167
+ */
168
+ export function renderMultiPassMarkdown(input) {
169
+ const { review, prNumber, headSha, prUrl } = input;
170
+ const lines = [];
171
+ lines.push(`# clud-bug review — PR #${prNumber} (${review.passCount} ${review.passCount === 1 ? 'pass' : 'passes'} · ${review.mode})`);
172
+ lines.push(`<!-- protocol-version: ${PROTOCOL_VERSION} -->`);
173
+ lines.push(`<!-- written-by: ${WRITTEN_BY} -->`);
174
+ lines.push(`<!-- review-sha: ${headSha} -->`);
175
+ lines.push(`<!-- passes: ${review.passCount} -->`);
176
+ lines.push(`<!-- mode: ${review.mode} -->`);
177
+ lines.push('');
178
+ const counts = review.summary_counts;
179
+ lines.push(`**Summary:** ${counts.critical} critical · ${counts.minor} minor · ${counts.preexisting} preexisting · ${counts.resolved_from_prior} resolved-from-prior · ${counts.still_open} still-open · **Verdict:** ${review.verdict}`);
180
+ lines.push('');
181
+ lines.push('**Reviewers:**');
182
+ for (const r of review.roles) {
183
+ lines.push(`- Pass ${r.passNumber} — ${r.roleName} · ${r.model}`);
184
+ }
185
+ lines.push('');
186
+ lines.push('**Skills cited:**');
187
+ if (review.skills_referenced.length === 0) {
188
+ lines.push('- _(none — see summary above)_');
189
+ }
190
+ else {
191
+ for (const slug of review.skills_referenced) {
192
+ const count = review.findings.filter((f) => f.skill === slug).length;
193
+ lines.push(`- ${slug} (${count} finding${count === 1 ? '' : 's'})`);
194
+ }
195
+ }
196
+ lines.push('');
197
+ lines.push('**Findings:**');
198
+ lines.push('');
199
+ // Severity buckets in SPEC order; empty buckets are omitted entirely.
200
+ const bucketed = bucketUnifiedBySeverity(review.findings);
201
+ if (bucketed.critical.length > 0) {
202
+ lines.push(`### ${SEVERITY_EMOJI.critical} Critical`);
203
+ for (const f of bucketed.critical)
204
+ lines.push(renderUnifiedFinding(f, /* includeReasoning */ true));
205
+ lines.push('');
206
+ }
207
+ if (bucketed.minor.length > 0) {
208
+ lines.push(`### ${SEVERITY_EMOJI.minor} Minor`);
209
+ for (const f of bucketed.minor)
210
+ lines.push(renderUnifiedFinding(f, false));
211
+ lines.push('');
212
+ }
213
+ if (bucketed.preexisting.length > 0) {
214
+ lines.push(`### ${SEVERITY_EMOJI.preexisting} Preexisting (informational)`);
215
+ for (const f of bucketed.preexisting)
216
+ lines.push(renderUnifiedFinding(f, false));
217
+ lines.push('');
218
+ }
219
+ lines.push('---');
220
+ lines.push('');
221
+ lines.push(`[Link to PR](${prUrl})`);
222
+ return lines.join('\n').normalize('NFC') + '\n';
223
+ }
224
+ function bucketUnifiedBySeverity(findings) {
225
+ return {
226
+ critical: findings.filter((f) => f.severity === 'critical'),
227
+ minor: findings.filter((f) => f.severity === 'minor'),
228
+ preexisting: findings.filter((f) => f.severity === 'preexisting'),
229
+ };
230
+ }
231
+ /**
232
+ * Renders one finding with inline per-pass attribution. The headline carries
233
+ * the FIRST attribution (whichever pass raised the issue); subsequent
234
+ * attributions appear on indented sub-lines:
235
+ *
236
+ * - [Pass 1 — Beetle · sonnet] auth.ts:42 — race: Race condition
237
+ * Reasoning: ...
238
+ * [Pass 2 — Wasp · opus]: (check) AGREED — confirmed by independent review.
239
+ * [Pass 3 — Mantis · opus]: (x) DISAGREED — guarded by the surrounding lock.
240
+ *
241
+ * The headline always tracks the FIRST attribution to preserve the SPEC
242
+ * §1.8.1 grep pattern (`**<file>:<line>** — <skill>: <summary>`).
243
+ */
244
+ function renderUnifiedFinding(f, includeReasoning) {
245
+ // Same guard as renderFinding — findingItemSchema.file is optional.
246
+ const fileLabel = f.file ?? '(unknown file)';
247
+ const location = f.line ? `${fileLabel}:${f.line}` : fileLabel;
248
+ const head = f.attributions[0];
249
+ if (!head) {
250
+ // Defensive — shouldn't happen; the aggregator guarantees ≥1 attribution.
251
+ return `- **${location}** — ${f.skill}: ${f.summary}`;
252
+ }
253
+ const headLabel = formatAttributionLabel(head);
254
+ const lines = [];
255
+ lines.push(`- ${headLabel} **${location}** — ${f.skill}: ${f.summary}`);
256
+ if (includeReasoning && f.reasoning) {
257
+ lines.push(` Reasoning: ${f.reasoning}`);
258
+ }
259
+ for (let i = 1; i < f.attributions.length; i++) {
260
+ const a = f.attributions[i];
261
+ if (!a)
262
+ continue;
263
+ lines.push(` ${formatFollowupAttribution(a)}`);
264
+ }
265
+ return lines.join('\n');
266
+ }
267
+ /**
268
+ * The leading bracket on the head line. Example:
269
+ *
270
+ * [Pass 1 — Beetle · anthropic/claude-sonnet-4.6]
271
+ * [Pass 2 — Wasp · anthropic/claude-opus-4.7 — found independently]
272
+ *
273
+ * "found independently" only fires when the head attribution is NOT
274
+ * `source: 'first'` — i.e. when a later pass surfaced this finding without
275
+ * Pass 1 raising it.
276
+ */
277
+ function formatAttributionLabel(a) {
278
+ const independent = a.source === 'independent' && a.passNumber > 1
279
+ ? ' — found independently'
280
+ : '';
281
+ return `[Pass ${a.passNumber} — ${a.roleName} · ${a.model}${independent}]`;
282
+ }
283
+ /**
284
+ * Subsequent-line attribution. Example:
285
+ *
286
+ * [Pass 2 — Wasp · opus]: ✅ AGREED — confirmed.
287
+ * [Pass 3 — Mantis · opus]: ❌ DISAGREED — guarded by surrounding lock.
288
+ */
289
+ function formatFollowupAttribution(a) {
290
+ const verdictSymbol = a.source === 'agreed'
291
+ ? '✅ AGREED' // U+2705 WHITE HEAVY CHECK MARK
292
+ : a.source === 'disagreed'
293
+ ? '❌ DISAGREED' // U+274C CROSS MARK
294
+ : a.source === 'independent'
295
+ ? 'INDEPENDENTLY FLAGGED'
296
+ : 'NOTED';
297
+ const note = a.note ? ` — ${a.note}` : '';
298
+ const disputed = a.source === 'disagreed' ? ' (Disputed — human decides.)' : '';
299
+ return `[Pass ${a.passNumber} — ${a.roleName} · ${a.model}]: ${verdictSymbol}${note}${disputed}`;
300
+ }
301
+ /** SPEC §6.1 / §1.8 path. The App's Octokit writeback uses this. */
302
+ export function reviewFilePath(prNumber) {
303
+ return `docs/reviews/PR-${prNumber}.md`;
304
+ }
305
+ /**
306
+ * SPEC §6.1 commit message: exactly `[skip-logmind] clud-bug review: PR #<n>`.
307
+ * The `[skip-logmind]` prefix tells `check-decisions.yml` to ignore this
308
+ * commit (SPEC §6.4). The App's Octokit writeback uses this.
309
+ */
310
+ export function reviewCommitMessage(prNumber) {
311
+ return `[skip-logmind] clud-bug review: PR #${prNumber}`;
312
+ }
313
+ //# sourceMappingURL=review-writeback.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"review-writeback.js","sourceRoot":"","sources":["../../src/core/review-writeback.ts"],"names":[],"mappings":"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"}