@diff-review-system/drs 1.0.0 → 1.1.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 (135) hide show
  1. package/.opencode/agent/github-reviewer.md +22 -7
  2. package/.opencode/agent/gitlab-reviewer.md +22 -7
  3. package/.opencode/agent/local-reviewer.md +21 -29
  4. package/.opencode/agent/review/performance.md +22 -13
  5. package/.opencode/agent/review/quality.md +22 -13
  6. package/.opencode/agent/review/security.md +22 -19
  7. package/.opencode/agent/review/style.md +22 -10
  8. package/.opencode/opencode.jsonc +7 -19
  9. package/README.md +175 -69
  10. package/dist/ci/runner.d.ts.map +1 -1
  11. package/dist/ci/runner.js +2 -4
  12. package/dist/ci/runner.js.map +1 -1
  13. package/dist/cli/index.js +14 -4
  14. package/dist/cli/index.js.map +1 -1
  15. package/dist/cli/init.d.ts.map +1 -1
  16. package/dist/cli/init.js +112 -23
  17. package/dist/cli/init.js.map +1 -1
  18. package/dist/cli/review-local.d.ts.map +1 -1
  19. package/dist/cli/review-local.js +27 -70
  20. package/dist/cli/review-local.js.map +1 -1
  21. package/dist/cli/review-mr.d.ts +1 -0
  22. package/dist/cli/review-mr.d.ts.map +1 -1
  23. package/dist/cli/review-mr.js +34 -119
  24. package/dist/cli/review-mr.js.map +1 -1
  25. package/dist/cli/review-pr.d.ts.map +1 -1
  26. package/dist/cli/review-pr.js +74 -114
  27. package/dist/cli/review-pr.js.map +1 -1
  28. package/dist/github/client.d.ts +199 -4
  29. package/dist/github/client.d.ts.map +1 -1
  30. package/dist/github/client.js +37 -2
  31. package/dist/github/client.js.map +1 -1
  32. package/dist/github/client.test.d.ts +2 -0
  33. package/dist/github/client.test.d.ts.map +1 -0
  34. package/dist/github/client.test.js +206 -0
  35. package/dist/github/client.test.js.map +1 -0
  36. package/dist/github/platform-adapter.d.ts +31 -0
  37. package/dist/github/platform-adapter.d.ts.map +1 -0
  38. package/dist/github/platform-adapter.js +127 -0
  39. package/dist/github/platform-adapter.js.map +1 -0
  40. package/dist/github/platform-adapter.test.d.ts +2 -0
  41. package/dist/github/platform-adapter.test.d.ts.map +1 -0
  42. package/dist/github/platform-adapter.test.js +40 -0
  43. package/dist/github/platform-adapter.test.js.map +1 -0
  44. package/dist/gitlab/client.d.ts +12 -0
  45. package/dist/gitlab/client.d.ts.map +1 -1
  46. package/dist/gitlab/client.js +18 -0
  47. package/dist/gitlab/client.js.map +1 -1
  48. package/dist/gitlab/diff-parser.test.d.ts +2 -0
  49. package/dist/gitlab/diff-parser.test.d.ts.map +1 -0
  50. package/dist/gitlab/diff-parser.test.js +315 -0
  51. package/dist/gitlab/diff-parser.test.js.map +1 -0
  52. package/dist/gitlab/platform-adapter.d.ts +27 -0
  53. package/dist/gitlab/platform-adapter.d.ts.map +1 -0
  54. package/dist/gitlab/platform-adapter.js +120 -0
  55. package/dist/gitlab/platform-adapter.js.map +1 -0
  56. package/dist/gitlab/platform-adapter.test.d.ts +2 -0
  57. package/dist/gitlab/platform-adapter.test.d.ts.map +1 -0
  58. package/dist/gitlab/platform-adapter.test.js +21 -0
  59. package/dist/gitlab/platform-adapter.test.js.map +1 -0
  60. package/dist/index.test.d.ts +2 -0
  61. package/dist/index.test.d.ts.map +1 -0
  62. package/dist/index.test.js +7 -0
  63. package/dist/index.test.js.map +1 -0
  64. package/dist/lib/code-quality-report.d.ts +44 -0
  65. package/dist/lib/code-quality-report.d.ts.map +1 -0
  66. package/dist/lib/code-quality-report.js +62 -0
  67. package/dist/lib/code-quality-report.js.map +1 -0
  68. package/dist/lib/code-quality-report.test.d.ts +2 -0
  69. package/dist/lib/code-quality-report.test.d.ts.map +1 -0
  70. package/dist/lib/code-quality-report.test.js +327 -0
  71. package/dist/lib/code-quality-report.test.js.map +1 -0
  72. package/dist/{gitlab → lib}/comment-formatter.d.ts +4 -2
  73. package/dist/lib/comment-formatter.d.ts.map +1 -0
  74. package/dist/{gitlab → lib}/comment-formatter.js +48 -15
  75. package/dist/lib/comment-formatter.js.map +1 -0
  76. package/dist/lib/comment-manager.d.ts +61 -0
  77. package/dist/lib/comment-manager.d.ts.map +1 -0
  78. package/dist/lib/comment-manager.js +91 -0
  79. package/dist/lib/comment-manager.js.map +1 -0
  80. package/dist/lib/config-model-overrides.test.d.ts +12 -0
  81. package/dist/lib/config-model-overrides.test.d.ts.map +1 -0
  82. package/dist/lib/config-model-overrides.test.js +224 -0
  83. package/dist/lib/config-model-overrides.test.js.map +1 -0
  84. package/dist/lib/config.d.ts +30 -1
  85. package/dist/lib/config.d.ts.map +1 -1
  86. package/dist/lib/config.js +70 -11
  87. package/dist/lib/config.js.map +1 -1
  88. package/dist/lib/config.test.d.ts +2 -0
  89. package/dist/lib/config.test.d.ts.map +1 -0
  90. package/dist/lib/config.test.js +28 -0
  91. package/dist/lib/config.test.js.map +1 -0
  92. package/dist/lib/context-loader.d.ts +29 -0
  93. package/dist/lib/context-loader.d.ts.map +1 -0
  94. package/dist/lib/context-loader.js +68 -0
  95. package/dist/lib/context-loader.js.map +1 -0
  96. package/dist/lib/diff-parser.d.ts.map +1 -0
  97. package/dist/{gitlab → lib}/diff-parser.js +3 -3
  98. package/dist/lib/diff-parser.js.map +1 -0
  99. package/dist/lib/issue-parser.d.ts +29 -0
  100. package/dist/lib/issue-parser.d.ts.map +1 -0
  101. package/dist/lib/issue-parser.js +151 -0
  102. package/dist/lib/issue-parser.js.map +1 -0
  103. package/dist/lib/issue-parser.test.d.ts +2 -0
  104. package/dist/lib/issue-parser.test.d.ts.map +1 -0
  105. package/dist/lib/issue-parser.test.js +281 -0
  106. package/dist/lib/issue-parser.test.js.map +1 -0
  107. package/dist/lib/platform-client.d.ts +130 -0
  108. package/dist/lib/platform-client.d.ts.map +1 -0
  109. package/dist/lib/platform-client.js +8 -0
  110. package/dist/lib/platform-client.js.map +1 -0
  111. package/dist/lib/position-validator.d.ts +36 -0
  112. package/dist/lib/position-validator.d.ts.map +1 -0
  113. package/dist/lib/position-validator.js +43 -0
  114. package/dist/lib/position-validator.js.map +1 -0
  115. package/dist/lib/review-orchestrator.d.ts +60 -0
  116. package/dist/lib/review-orchestrator.d.ts.map +1 -0
  117. package/dist/lib/review-orchestrator.js +183 -0
  118. package/dist/lib/review-orchestrator.js.map +1 -0
  119. package/dist/lib/unified-review-executor.d.ts +32 -0
  120. package/dist/lib/unified-review-executor.d.ts.map +1 -0
  121. package/dist/lib/unified-review-executor.js +228 -0
  122. package/dist/lib/unified-review-executor.js.map +1 -0
  123. package/dist/opencode/agent-loader.d.ts.map +1 -1
  124. package/dist/opencode/agent-loader.js +5 -10
  125. package/dist/opencode/agent-loader.js.map +1 -1
  126. package/dist/opencode/client.d.ts +3 -2
  127. package/dist/opencode/client.d.ts.map +1 -1
  128. package/dist/opencode/client.js +141 -28
  129. package/dist/opencode/client.js.map +1 -1
  130. package/package.json +28 -19
  131. package/dist/gitlab/comment-formatter.d.ts.map +0 -1
  132. package/dist/gitlab/comment-formatter.js.map +0 -1
  133. package/dist/gitlab/diff-parser.d.ts.map +0 -1
  134. package/dist/gitlab/diff-parser.js.map +0 -1
  135. /package/dist/{gitlab → lib}/diff-parser.d.ts +0 -0
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=code-quality-report.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"code-quality-report.test.d.ts","sourceRoot":"","sources":["../../src/lib/code-quality-report.test.ts"],"names":[],"mappings":""}
@@ -0,0 +1,327 @@
1
+ import { describe, it, expect } from 'vitest';
2
+ import { convertToCodeQualityIssue, generateCodeQualityReport, formatCodeQualityReport, } from './code-quality-report.js';
3
+ describe('code-quality-report', () => {
4
+ describe('convertToCodeQualityIssue', () => {
5
+ it('should convert a DRS issue to GitLab code quality format', () => {
6
+ const drsIssue = {
7
+ category: 'SECURITY',
8
+ severity: 'CRITICAL',
9
+ title: 'SQL Injection',
10
+ file: 'src/api/users.ts',
11
+ line: 42,
12
+ problem: 'Query uses string concatenation.',
13
+ solution: 'Use parameterized queries instead.',
14
+ agent: 'security',
15
+ };
16
+ const result = convertToCodeQualityIssue(drsIssue);
17
+ expect(result).toMatchObject({
18
+ description: 'Query uses string concatenation. Use parameterized queries instead.',
19
+ check_name: 'drs-security',
20
+ severity: 'blocker',
21
+ location: {
22
+ path: 'src/api/users.ts',
23
+ lines: {
24
+ begin: 42,
25
+ },
26
+ },
27
+ });
28
+ expect(result.fingerprint).toBeDefined();
29
+ expect(result.fingerprint.length).toBeGreaterThan(0);
30
+ });
31
+ it('should map CRITICAL severity to blocker', () => {
32
+ const issue = {
33
+ category: 'SECURITY',
34
+ severity: 'CRITICAL',
35
+ title: 'Test',
36
+ file: 'test.ts',
37
+ line: 1,
38
+ problem: 'Problem',
39
+ solution: 'Solution',
40
+ agent: 'test',
41
+ };
42
+ const result = convertToCodeQualityIssue(issue);
43
+ expect(result.severity).toBe('blocker');
44
+ });
45
+ it('should map HIGH severity to critical', () => {
46
+ const issue = {
47
+ category: 'QUALITY',
48
+ severity: 'HIGH',
49
+ title: 'Test',
50
+ file: 'test.ts',
51
+ line: 1,
52
+ problem: 'Problem',
53
+ solution: 'Solution',
54
+ agent: 'test',
55
+ };
56
+ const result = convertToCodeQualityIssue(issue);
57
+ expect(result.severity).toBe('critical');
58
+ });
59
+ it('should map MEDIUM severity to major', () => {
60
+ const issue = {
61
+ category: 'QUALITY',
62
+ severity: 'MEDIUM',
63
+ title: 'Test',
64
+ file: 'test.ts',
65
+ line: 1,
66
+ problem: 'Problem',
67
+ solution: 'Solution',
68
+ agent: 'test',
69
+ };
70
+ const result = convertToCodeQualityIssue(issue);
71
+ expect(result.severity).toBe('major');
72
+ });
73
+ it('should map LOW severity to minor', () => {
74
+ const issue = {
75
+ category: 'STYLE',
76
+ severity: 'LOW',
77
+ title: 'Test',
78
+ file: 'test.ts',
79
+ line: 1,
80
+ problem: 'Problem',
81
+ solution: 'Solution',
82
+ agent: 'test',
83
+ };
84
+ const result = convertToCodeQualityIssue(issue);
85
+ expect(result.severity).toBe('minor');
86
+ });
87
+ it('should generate check_name from category', () => {
88
+ const issue = {
89
+ category: 'QUALITY',
90
+ severity: 'MEDIUM',
91
+ title: 'Test',
92
+ file: 'test.ts',
93
+ line: 1,
94
+ problem: 'Problem',
95
+ solution: 'Solution',
96
+ agent: 'test',
97
+ };
98
+ const result = convertToCodeQualityIssue(issue);
99
+ expect(result.check_name).toBe('drs-quality');
100
+ });
101
+ it('should handle issues with empty solution', () => {
102
+ const issue = {
103
+ category: 'SECURITY',
104
+ severity: 'HIGH',
105
+ title: 'Test',
106
+ file: 'test.ts',
107
+ line: 1,
108
+ problem: 'This is a problem',
109
+ solution: '',
110
+ agent: 'test',
111
+ };
112
+ const result = convertToCodeQualityIssue(issue);
113
+ expect(result.description).toBe('This is a problem');
114
+ });
115
+ it('should default to line 1 if no line number provided', () => {
116
+ const issue = {
117
+ category: 'STYLE',
118
+ severity: 'LOW',
119
+ title: 'Missing header',
120
+ file: 'src/main.ts',
121
+ problem: 'No copyright header',
122
+ solution: 'Add standard file header',
123
+ agent: 'test',
124
+ };
125
+ const result = convertToCodeQualityIssue(issue);
126
+ expect(result.location.lines.begin).toBe(1);
127
+ });
128
+ it('should create consistent fingerprints for identical issues', () => {
129
+ const issue1 = {
130
+ category: 'SECURITY',
131
+ severity: 'CRITICAL',
132
+ title: 'Test',
133
+ file: 'test.ts',
134
+ line: 42,
135
+ problem: 'Problem',
136
+ solution: 'Solution',
137
+ agent: 'test',
138
+ };
139
+ const issue2 = {
140
+ category: 'SECURITY',
141
+ severity: 'CRITICAL',
142
+ title: 'Test',
143
+ file: 'test.ts',
144
+ line: 42,
145
+ problem: 'Problem',
146
+ solution: 'Solution',
147
+ agent: 'test',
148
+ };
149
+ const result1 = convertToCodeQualityIssue(issue1);
150
+ const result2 = convertToCodeQualityIssue(issue2);
151
+ expect(result1.fingerprint).toBe(result2.fingerprint);
152
+ });
153
+ it('should create different fingerprints for different issues', () => {
154
+ const issue1 = {
155
+ category: 'SECURITY',
156
+ severity: 'CRITICAL',
157
+ title: 'Test',
158
+ file: 'test.ts',
159
+ line: 42,
160
+ problem: 'Problem',
161
+ solution: 'Solution',
162
+ agent: 'test',
163
+ };
164
+ const issue2 = {
165
+ category: 'SECURITY',
166
+ severity: 'CRITICAL',
167
+ title: 'Test',
168
+ file: 'test.ts',
169
+ line: 43, // Different line
170
+ problem: 'Problem',
171
+ solution: 'Solution',
172
+ agent: 'test',
173
+ };
174
+ const result1 = convertToCodeQualityIssue(issue1);
175
+ const result2 = convertToCodeQualityIssue(issue2);
176
+ expect(result1.fingerprint).not.toBe(result2.fingerprint);
177
+ });
178
+ });
179
+ describe('generateCodeQualityReport', () => {
180
+ it('should convert multiple DRS issues to code quality format', () => {
181
+ const issues = [
182
+ {
183
+ category: 'SECURITY',
184
+ severity: 'CRITICAL',
185
+ title: 'SQL Injection',
186
+ file: 'src/api/users.ts',
187
+ line: 42,
188
+ problem: 'Query uses string concatenation',
189
+ solution: 'Use parameterized queries',
190
+ agent: 'security',
191
+ },
192
+ {
193
+ category: 'QUALITY',
194
+ severity: 'HIGH',
195
+ title: 'High complexity',
196
+ file: 'src/utils/helper.ts',
197
+ line: 10,
198
+ problem: 'Function has cyclomatic complexity of 15',
199
+ solution: 'Break into smaller functions',
200
+ agent: 'quality',
201
+ },
202
+ ];
203
+ const report = generateCodeQualityReport(issues);
204
+ expect(report).toHaveLength(2);
205
+ expect(report[0].severity).toBe('blocker');
206
+ expect(report[0].check_name).toBe('drs-security');
207
+ expect(report[1].severity).toBe('critical');
208
+ expect(report[1].check_name).toBe('drs-quality');
209
+ });
210
+ it('should handle empty issues array', () => {
211
+ const report = generateCodeQualityReport([]);
212
+ expect(report).toEqual([]);
213
+ });
214
+ it('should preserve all issues in order', () => {
215
+ const issues = [
216
+ {
217
+ category: 'SECURITY',
218
+ severity: 'CRITICAL',
219
+ title: 'First',
220
+ file: 'a.ts',
221
+ line: 1,
222
+ problem: 'Problem 1',
223
+ solution: 'Solution 1',
224
+ agent: 'test',
225
+ },
226
+ {
227
+ category: 'QUALITY',
228
+ severity: 'MEDIUM',
229
+ title: 'Second',
230
+ file: 'b.ts',
231
+ line: 2,
232
+ problem: 'Problem 2',
233
+ solution: 'Solution 2',
234
+ agent: 'test',
235
+ },
236
+ {
237
+ category: 'STYLE',
238
+ severity: 'LOW',
239
+ title: 'Third',
240
+ file: 'c.ts',
241
+ line: 3,
242
+ problem: 'Problem 3',
243
+ solution: 'Solution 3',
244
+ agent: 'test',
245
+ },
246
+ ];
247
+ const report = generateCodeQualityReport(issues);
248
+ expect(report).toHaveLength(3);
249
+ expect(report[0].location.path).toBe('a.ts');
250
+ expect(report[1].location.path).toBe('b.ts');
251
+ expect(report[2].location.path).toBe('c.ts');
252
+ });
253
+ });
254
+ describe('formatCodeQualityReport', () => {
255
+ it('should format report as valid JSON', () => {
256
+ const report = [
257
+ {
258
+ description: 'Query uses string concatenation',
259
+ check_name: 'drs-security',
260
+ fingerprint: 'abc123',
261
+ severity: 'blocker',
262
+ location: {
263
+ path: 'src/api/users.ts',
264
+ lines: {
265
+ begin: 42,
266
+ },
267
+ },
268
+ },
269
+ ];
270
+ const json = formatCodeQualityReport(report);
271
+ expect(() => JSON.parse(json)).not.toThrow();
272
+ const parsed = JSON.parse(json);
273
+ expect(parsed).toHaveLength(1);
274
+ expect(parsed[0].description).toBe('Query uses string concatenation');
275
+ });
276
+ it('should format with pretty printing', () => {
277
+ const report = [
278
+ {
279
+ description: 'Test issue',
280
+ check_name: 'drs-test',
281
+ fingerprint: 'test123',
282
+ severity: 'minor',
283
+ location: {
284
+ path: 'test.ts',
285
+ lines: {
286
+ begin: 1,
287
+ },
288
+ },
289
+ },
290
+ ];
291
+ const json = formatCodeQualityReport(report);
292
+ // Should have indentation (pretty printed)
293
+ expect(json).toContain('\n');
294
+ expect(json).toContain(' ');
295
+ });
296
+ it('should handle empty report', () => {
297
+ const json = formatCodeQualityReport([]);
298
+ expect(json).toBe('[]');
299
+ });
300
+ it('should produce valid GitLab code quality format', () => {
301
+ const report = [
302
+ {
303
+ description: "'unused' is assigned a value but never used.",
304
+ check_name: 'no-unused-vars',
305
+ fingerprint: '7815696ecbf1c96e6894b779456d330e',
306
+ severity: 'minor',
307
+ location: {
308
+ path: 'lib/index.js',
309
+ lines: {
310
+ begin: 42,
311
+ },
312
+ },
313
+ },
314
+ ];
315
+ const json = formatCodeQualityReport(report);
316
+ const parsed = JSON.parse(json);
317
+ // Verify all required fields are present
318
+ expect(parsed[0]).toHaveProperty('description');
319
+ expect(parsed[0]).toHaveProperty('fingerprint');
320
+ expect(parsed[0]).toHaveProperty('location');
321
+ expect(parsed[0].location).toHaveProperty('path');
322
+ expect(parsed[0].location).toHaveProperty('lines');
323
+ expect(parsed[0].location.lines).toHaveProperty('begin');
324
+ });
325
+ });
326
+ });
327
+ //# sourceMappingURL=code-quality-report.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"code-quality-report.test.js","sourceRoot":"","sources":["../../src/lib/code-quality-report.test.ts"],"names":[],"mappings":"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"}
@@ -19,12 +19,14 @@ export interface ReviewSummary {
19
19
  }
20
20
  /**
21
21
  * Format a single review issue as a GitLab comment
22
+ * @param fingerprint Optional fingerprint to embed in comment for deduplication
22
23
  */
23
- export declare function formatIssueComment(issue: ReviewIssue): string;
24
+ export declare function formatIssueComment(issue: ReviewIssue, fingerprint?: string): string;
24
25
  /**
25
26
  * Format a review summary as a GitLab comment
27
+ * @param commentId Optional comment ID to embed for update identification
26
28
  */
27
- export declare function formatSummaryComment(summary: ReviewSummary, issues: ReviewIssue[]): string;
29
+ export declare function formatSummaryComment(summary: ReviewSummary, issues: ReviewIssue[], commentId?: string): string;
28
30
  /**
29
31
  * Format issue for terminal output with colors
30
32
  */
@@ -0,0 +1 @@
1
+ {"version":3,"file":"comment-formatter.d.ts","sourceRoot":"","sources":["../../src/lib/comment-formatter.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,aAAa,GAAG,UAAU,GAAG,MAAM,GAAG,QAAQ,GAAG,KAAK,CAAC;AACnE,MAAM,MAAM,aAAa,GAAG,UAAU,GAAG,SAAS,GAAG,OAAO,GAAG,aAAa,CAAC;AAE7E,MAAM,WAAW,WAAW;IAC1B,QAAQ,EAAE,aAAa,CAAC;IACxB,QAAQ,EAAE,aAAa,CAAC;IACxB,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;IACtB,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,aAAa;IAC5B,aAAa,EAAE,MAAM,CAAC;IACtB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC,aAAa,EAAE,MAAM,CAAC,CAAC;IAC1C,UAAU,EAAE,MAAM,CAAC,aAAa,EAAE,MAAM,CAAC,CAAC;CAC3C;AAgBD;;;GAGG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,WAAW,EAAE,WAAW,CAAC,EAAE,MAAM,GAAG,MAAM,CA0BnF;AAED;;;GAGG;AACH,wBAAgB,oBAAoB,CAClC,OAAO,EAAE,aAAa,EACtB,MAAM,EAAE,WAAW,EAAE,EACrB,SAAS,CAAC,EAAE,MAAM,GACjB,MAAM,CA8ER;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,WAAW,GAAG,MAAM,CAY9D;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,aAAa,EAAE,MAAM,EAAE,MAAM,EAAE,WAAW,EAAE,GAAG,aAAa,CAwB5F"}
@@ -12,14 +12,20 @@ const CATEGORY_EMOJI = {
12
12
  };
13
13
  /**
14
14
  * Format a single review issue as a GitLab comment
15
+ * @param fingerprint Optional fingerprint to embed in comment for deduplication
15
16
  */
16
- export function formatIssueComment(issue) {
17
+ export function formatIssueComment(issue, fingerprint) {
17
18
  const emoji = CATEGORY_EMOJI[issue.category];
18
19
  const severityEmoji = SEVERITY_EMOJI[issue.severity];
19
- let comment = `## ${emoji} ${issue.category} - ${issue.title}\n\n`;
20
+ // Add hidden fingerprint for deduplication
21
+ let comment = '';
22
+ if (fingerprint) {
23
+ comment += `<!-- issue-fp: ${fingerprint} -->\n`;
24
+ }
25
+ comment += `## ${emoji} ${issue.category} - ${issue.title}\n\n`;
20
26
  comment += `**File**: \`${issue.file}${issue.line ? `:${issue.line}` : ''}\`\n`;
21
27
  comment += `**Severity**: ${severityEmoji} ${issue.severity}\n`;
22
- comment += `**Reviewer**: ${issue.agent}\n\n`;
28
+ comment += `**Analysis by**: ${issue.agent}\n\n`;
23
29
  comment += `### Problem\n${issue.problem}\n\n`;
24
30
  comment += `### Solution\n${issue.solution}\n`;
25
31
  if (issue.references && issue.references.length > 0) {
@@ -32,9 +38,15 @@ export function formatIssueComment(issue) {
32
38
  }
33
39
  /**
34
40
  * Format a review summary as a GitLab comment
41
+ * @param commentId Optional comment ID to embed for update identification
35
42
  */
36
- export function formatSummaryComment(summary, issues) {
37
- let comment = `# 🤖 AI Code Review Summary\n\n`;
43
+ export function formatSummaryComment(summary, issues, commentId) {
44
+ // Add hidden identifier for update-or-create logic
45
+ let comment = '';
46
+ if (commentId) {
47
+ comment += `<!-- drs-comment-id: ${commentId} -->\n`;
48
+ }
49
+ comment += `# 📋 Code Review Analysis\n\n`;
38
50
  comment += `## 📊 Statistics\n\n`;
39
51
  comment += `- **Files Reviewed**: ${summary.filesReviewed}\n`;
40
52
  comment += `- **Total Issues**: ${summary.issuesFound}\n\n`;
@@ -49,30 +61,51 @@ export function formatSummaryComment(summary, issues) {
49
61
  comment += `- ${CATEGORY_EMOJI.QUALITY} **Quality**: ${summary.byCategory.QUALITY}\n`;
50
62
  comment += `- ${CATEGORY_EMOJI.STYLE} **Style**: ${summary.byCategory.STYLE}\n`;
51
63
  comment += `- ${CATEGORY_EMOJI.PERFORMANCE} **Performance**: ${summary.byCategory.PERFORMANCE}\n\n`;
52
- // List critical and high issues
53
- const criticalIssues = issues.filter(i => i.severity === 'CRITICAL');
54
- const highIssues = issues.filter(i => i.severity === 'HIGH');
64
+ // Group issues by severity
65
+ const criticalIssues = issues.filter((i) => i.severity === 'CRITICAL');
66
+ const highIssues = issues.filter((i) => i.severity === 'HIGH');
67
+ const mediumIssues = issues.filter((i) => i.severity === 'MEDIUM');
68
+ const lowIssues = issues.filter((i) => i.severity === 'LOW');
69
+ // Helper function to format issue details
70
+ const formatIssueDetails = (issue) => {
71
+ let details = `### ${CATEGORY_EMOJI[issue.category]} ${issue.title}\n\n`;
72
+ details += `**File**: \`${issue.file}${issue.line ? `:${issue.line}` : ''}\` | **Category**: ${issue.category}\n\n`;
73
+ details += `**Problem**: ${issue.problem}\n\n`;
74
+ details += `**Solution**: ${issue.solution}\n`;
75
+ if (issue.references && issue.references.length > 0) {
76
+ details += `\n**References**: ${issue.references.join(', ')}\n`;
77
+ }
78
+ return details + '\n';
79
+ };
55
80
  if (criticalIssues.length > 0) {
56
81
  comment += `## 🔴 Critical Issues\n\n`;
57
82
  for (const issue of criticalIssues) {
58
- comment += `- **${issue.title}** in \`${issue.file}${issue.line ? `:${issue.line}` : ''}\`\n`;
83
+ comment += formatIssueDetails(issue);
59
84
  }
60
- comment += `\n`;
61
85
  }
62
86
  if (highIssues.length > 0) {
63
87
  comment += `## 🟡 High Priority Issues\n\n`;
64
88
  for (const issue of highIssues) {
65
- comment += `- **${issue.title}** in \`${issue.file}${issue.line ? `:${issue.line}` : ''}\`\n`;
89
+ comment += formatIssueDetails(issue);
90
+ }
91
+ }
92
+ if (mediumIssues.length > 0) {
93
+ comment += `## 🟠 Medium Priority Issues\n\n`;
94
+ for (const issue of mediumIssues) {
95
+ comment += formatIssueDetails(issue);
96
+ }
97
+ }
98
+ if (lowIssues.length > 0) {
99
+ comment += `## ⚪ Low Priority Issues\n\n`;
100
+ for (const issue of lowIssues) {
101
+ comment += formatIssueDetails(issue);
66
102
  }
67
- comment += `\n`;
68
103
  }
69
- comment += `\n---\n`;
70
- comment += `*Detailed findings have been posted as individual discussion threads on the affected lines.*\n`;
71
104
  }
72
105
  else {
73
106
  comment += `✅ **No issues found!** The code looks good.\n`;
74
107
  }
75
- comment += `\n*Powered by DRS - GitLab Review Bot*\n`;
108
+ comment += `\n---\n\n*Analyzed by **DRS** | Diff Review System*\n`;
76
109
  return comment;
77
110
  }
78
111
  /**
@@ -0,0 +1 @@
1
+ {"version":3,"file":"comment-formatter.js","sourceRoot":"","sources":["../../src/lib/comment-formatter.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,61 @@
1
+ import type { ReviewIssue } from './comment-formatter.js';
2
+ /**
3
+ * Platform-agnostic comment management for deduplication and updates
4
+ */
5
+ export declare const BOT_COMMENT_ID = "drs-review-summary";
6
+ /**
7
+ * Create a unique fingerprint for an issue to detect duplicates
8
+ */
9
+ export declare function createIssueFingerprint(issue: ReviewIssue): string;
10
+ /**
11
+ * Extract bot comment ID from comment body
12
+ */
13
+ export declare function extractCommentId(body: string): string | null;
14
+ /**
15
+ * Extract issue fingerprints from comment body
16
+ */
17
+ export declare function extractIssueFingerprints(body: string): Set<string>;
18
+ /**
19
+ * Filter issues to only include CRITICAL and HIGH severity
20
+ * (for inline comments - reduces noise and API calls)
21
+ */
22
+ export declare function filterCriticalAndHigh(issues: ReviewIssue[]): ReviewIssue[];
23
+ /**
24
+ * Filter out duplicate issues based on existing fingerprints
25
+ */
26
+ export declare function filterDuplicateIssues(issues: ReviewIssue[], existingFingerprints: Set<string>): ReviewIssue[];
27
+ /**
28
+ * Represents a comment from any platform
29
+ */
30
+ export interface PlatformComment {
31
+ id: number | string;
32
+ body: string;
33
+ }
34
+ /**
35
+ * Find existing summary comment using bot marker
36
+ */
37
+ export declare function findExistingSummaryComment(comments: PlatformComment[]): PlatformComment | null;
38
+ /**
39
+ * Collect all existing issue fingerprints from comments
40
+ */
41
+ export declare function collectExistingFingerprints(comments: PlatformComment[]): Set<string>;
42
+ /**
43
+ * Result of preparing issues for posting
44
+ */
45
+ export interface PreparedIssues {
46
+ /** Issues to post as inline comments (CRITICAL/HIGH, new, with valid lines) */
47
+ inlineIssues: ReviewIssue[];
48
+ /** Number of issues that were deduplicated */
49
+ deduplicatedCount: number;
50
+ /** Number of medium/low severity issues (not posted inline) */
51
+ nonInlineCount: number;
52
+ }
53
+ /**
54
+ * Prepare issues for posting, applying all filters:
55
+ * 1. Filter to CRITICAL/HIGH severity only
56
+ * 2. Filter out duplicates based on existing comments
57
+ * 3. Filter to only issues with line numbers
58
+ * 4. Optionally filter to valid line numbers (platform-specific)
59
+ */
60
+ export declare function prepareIssuesForPosting(allIssues: ReviewIssue[], existingComments: PlatformComment[], validLinesChecker?: (issue: ReviewIssue) => boolean): PreparedIssues;
61
+ //# sourceMappingURL=comment-manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"comment-manager.d.ts","sourceRoot":"","sources":["../../src/lib/comment-manager.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAC;AAE1D;;GAEG;AAGH,eAAO,MAAM,cAAc,uBAAuB,CAAC;AAEnD;;GAEG;AACH,wBAAgB,sBAAsB,CAAC,KAAK,EAAE,WAAW,GAAG,MAAM,CAEjE;AAED;;GAEG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAG5D;AAED;;GAEG;AACH,wBAAgB,wBAAwB,CAAC,IAAI,EAAE,MAAM,GAAG,GAAG,CAAC,MAAM,CAAC,CAQlE;AAED;;;GAGG;AACH,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,WAAW,EAAE,GAAG,WAAW,EAAE,CAE1E;AAED;;GAEG;AACH,wBAAgB,qBAAqB,CACnC,MAAM,EAAE,WAAW,EAAE,EACrB,oBAAoB,EAAE,GAAG,CAAC,MAAM,CAAC,GAChC,WAAW,EAAE,CAKf;AAED;;GAEG;AACH,MAAM,WAAW,eAAe;IAC9B,EAAE,EAAE,MAAM,GAAG,MAAM,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;CACd;AAED;;GAEG;AACH,wBAAgB,0BAA0B,CAAC,QAAQ,EAAE,eAAe,EAAE,GAAG,eAAe,GAAG,IAAI,CAE9F;AAED;;GAEG;AACH,wBAAgB,2BAA2B,CAAC,QAAQ,EAAE,eAAe,EAAE,GAAG,GAAG,CAAC,MAAM,CAAC,CAOpF;AAED;;GAEG;AACH,MAAM,WAAW,cAAc;IAC7B,+EAA+E;IAC/E,YAAY,EAAE,WAAW,EAAE,CAAC;IAC5B,8CAA8C;IAC9C,iBAAiB,EAAE,MAAM,CAAC;IAC1B,+DAA+D;IAC/D,cAAc,EAAE,MAAM,CAAC;CACxB;AAED;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CACrC,SAAS,EAAE,WAAW,EAAE,EACxB,gBAAgB,EAAE,eAAe,EAAE,EACnC,iBAAiB,CAAC,EAAE,CAAC,KAAK,EAAE,WAAW,KAAK,OAAO,GAClD,cAAc,CAuBhB"}
@@ -0,0 +1,91 @@
1
+ /**
2
+ * Platform-agnostic comment management for deduplication and updates
3
+ */
4
+ // Bot identifier for tracking our comments
5
+ export const BOT_COMMENT_ID = 'drs-review-summary';
6
+ /**
7
+ * Create a unique fingerprint for an issue to detect duplicates
8
+ */
9
+ export function createIssueFingerprint(issue) {
10
+ return `${issue.file}:${issue.line || 'general'}:${issue.category}:${issue.title}`;
11
+ }
12
+ /**
13
+ * Extract bot comment ID from comment body
14
+ */
15
+ export function extractCommentId(body) {
16
+ const match = body.match(/<!-- drs-comment-id: (.*?) -->/);
17
+ return match ? match[1] : null;
18
+ }
19
+ /**
20
+ * Extract issue fingerprints from comment body
21
+ */
22
+ export function extractIssueFingerprints(body) {
23
+ const fingerprints = new Set();
24
+ const regex = /<!-- issue-fp: (.*?) -->/g;
25
+ let match;
26
+ while ((match = regex.exec(body)) !== null) {
27
+ fingerprints.add(match[1]);
28
+ }
29
+ return fingerprints;
30
+ }
31
+ /**
32
+ * Filter issues to only include CRITICAL and HIGH severity
33
+ * (for inline comments - reduces noise and API calls)
34
+ */
35
+ export function filterCriticalAndHigh(issues) {
36
+ return issues.filter((i) => i.severity === 'CRITICAL' || i.severity === 'HIGH');
37
+ }
38
+ /**
39
+ * Filter out duplicate issues based on existing fingerprints
40
+ */
41
+ export function filterDuplicateIssues(issues, existingFingerprints) {
42
+ return issues.filter((issue) => {
43
+ const fingerprint = createIssueFingerprint(issue);
44
+ return !existingFingerprints.has(fingerprint);
45
+ });
46
+ }
47
+ /**
48
+ * Find existing summary comment using bot marker
49
+ */
50
+ export function findExistingSummaryComment(comments) {
51
+ return comments.find((c) => extractCommentId(c.body) === BOT_COMMENT_ID) || null;
52
+ }
53
+ /**
54
+ * Collect all existing issue fingerprints from comments
55
+ */
56
+ export function collectExistingFingerprints(comments) {
57
+ const allFingerprints = new Set();
58
+ for (const comment of comments) {
59
+ const fingerprints = extractIssueFingerprints(comment.body);
60
+ fingerprints.forEach((fp) => allFingerprints.add(fp));
61
+ }
62
+ return allFingerprints;
63
+ }
64
+ /**
65
+ * Prepare issues for posting, applying all filters:
66
+ * 1. Filter to CRITICAL/HIGH severity only
67
+ * 2. Filter out duplicates based on existing comments
68
+ * 3. Filter to only issues with line numbers
69
+ * 4. Optionally filter to valid line numbers (platform-specific)
70
+ */
71
+ export function prepareIssuesForPosting(allIssues, existingComments, validLinesChecker) {
72
+ // Step 1: Filter to CRITICAL/HIGH only
73
+ const criticalAndHigh = filterCriticalAndHigh(allIssues);
74
+ const nonInlineCount = allIssues.length - criticalAndHigh.length;
75
+ // Step 2: Filter out duplicates
76
+ const existingFingerprints = collectExistingFingerprints(existingComments);
77
+ const newIssues = filterDuplicateIssues(criticalAndHigh, existingFingerprints);
78
+ const deduplicatedCount = criticalAndHigh.length - newIssues.length;
79
+ // Step 3: Filter to only issues with line numbers
80
+ let inlineIssues = newIssues.filter((issue) => issue.line !== undefined && issue.line !== null);
81
+ // Step 4: Optionally filter based on valid lines (platform-specific)
82
+ if (validLinesChecker) {
83
+ inlineIssues = inlineIssues.filter(validLinesChecker);
84
+ }
85
+ return {
86
+ inlineIssues,
87
+ deduplicatedCount,
88
+ nonInlineCount,
89
+ };
90
+ }
91
+ //# sourceMappingURL=comment-manager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"comment-manager.js","sourceRoot":"","sources":["../../src/lib/comment-manager.ts"],"names":[],"mappings":"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"}