@descent-vtt/spec-brief 0.2.7 → 0.3.0
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/CHANGELOG.md +67 -1
- package/README.md +162 -29
- package/dist/cli.d.ts +1 -1
- package/dist/cli.js +61 -43
- package/dist/cli.js.map +1 -1
- package/dist/collisions.js +13 -8
- package/dist/collisions.js.map +1 -1
- package/dist/config.js +2 -1
- package/dist/config.js.map +1 -1
- package/dist/corpus.d.ts +5 -0
- package/dist/corpus.js +7 -0
- package/dist/corpus.js.map +1 -1
- package/dist/glob.d.ts +6 -5
- package/dist/glob.js +22 -103
- package/dist/glob.js.map +1 -1
- package/dist/lint.js +1 -0
- package/dist/lint.js.map +1 -1
- package/dist/report.d.ts +18 -4
- package/dist/report.js +98 -28
- package/dist/report.js.map +1 -1
- package/dist/rules.d.ts +2 -0
- package/dist/rules.js +21 -8
- package/dist/rules.js.map +1 -1
- package/dist/schedule.js +12 -10
- package/dist/schedule.js.map +1 -1
- package/dist/schema.d.ts +5 -1
- package/dist/schema.js +6 -2
- package/dist/schema.js.map +1 -1
- package/dist/scope.d.ts +26 -4
- package/dist/scope.js +64 -8
- package/dist/scope.js.map +1 -1
- package/dist/trigger.js +59 -3
- package/dist/trigger.js.map +1 -1
- package/dist/types.d.ts +9 -0
- package/dist/types.js.map +1 -1
- package/dist/vendor/spec-core/markdown/frontmatter.d.ts +11 -1
- package/dist/vendor/spec-core/markdown/frontmatter.js +20 -3
- package/dist/vendor/spec-core/markdown/frontmatter.js.map +1 -1
- package/dist/vendor/spec-core/pattern/glob.d.ts +85 -0
- package/dist/vendor/spec-core/pattern/glob.js +207 -17
- package/dist/vendor/spec-core/pattern/glob.js.map +1 -1
- package/dist/vendor/spec-core/pattern/index.d.ts +2 -2
- package/dist/vendor/spec-core/pattern/index.js +1 -1
- package/dist/vendor/spec-core/pattern/index.js.map +1 -1
- package/dist/vendor/spec-core/text/index.d.ts +1 -0
- package/dist/vendor/spec-core/text/index.js +1 -0
- package/dist/vendor/spec-core/text/index.js.map +1 -1
- package/dist/vendor/spec-core/text/width.d.ts +30 -0
- package/dist/vendor/spec-core/text/width.js +113 -0
- package/dist/vendor/spec-core/text/width.js.map +1 -0
- package/package.json +1 -1
package/dist/report.js
CHANGED
|
@@ -9,10 +9,13 @@
|
|
|
9
9
|
* so the family is not GitHub's alone.
|
|
10
10
|
*/
|
|
11
11
|
import { createHash } from 'node:crypto';
|
|
12
|
+
import { idKey } from './corpus.js';
|
|
12
13
|
import { summarise } from './lint.js';
|
|
13
14
|
import { ARCHIVE_RULES, COLLISION_RULES, RULES } from './rules.js';
|
|
14
15
|
import { breachReasons, holds, moves, reasons } from './schedule.js';
|
|
16
|
+
import { witnessText } from './scope.js';
|
|
15
17
|
import { inWords } from './text.js';
|
|
18
|
+
import { displayWidth } from './vendor/spec-core/text/index.js';
|
|
16
19
|
export const FORMATS = ['pretty', 'json', 'sarif', 'github', 'gitlab'];
|
|
17
20
|
/**
|
|
18
21
|
* The version of the JSON documents this tool prints, every command's alike.
|
|
@@ -121,29 +124,44 @@ export function sarif(findings, version) {
|
|
|
121
124
|
return `${JSON.stringify(document, null, 2)}\n`;
|
|
122
125
|
}
|
|
123
126
|
/**
|
|
124
|
-
* GitLab's Code Quality severities
|
|
125
|
-
*
|
|
127
|
+
* GitLab's Code Quality severities, as the family maps them: an error is
|
|
128
|
+
* `major`, a warning `minor`, a note `info`. An error fails the run but is not
|
|
129
|
+
* a security hole or a crash, which is what `critical` and `blocker` say in
|
|
126
130
|
* GitLab's own reports, so the scale tops out at `major`.
|
|
127
131
|
*/
|
|
128
132
|
const GITLAB_SEVERITY = { error: 'major', warning: 'minor', note: 'info' };
|
|
133
|
+
/**
|
|
134
|
+
* What a finding is, whatever it says: its rule, its file, its brief, and what
|
|
135
|
+
* it is about there - a section, a pattern, the other brief of a pair, the one
|
|
136
|
+
* path a refusal names. Never the message, the hint or the line.
|
|
137
|
+
*/
|
|
138
|
+
function identity(f) {
|
|
139
|
+
return [f.rule, f.file, f.brief ?? '', f.subject ?? f.path ?? ''];
|
|
140
|
+
}
|
|
129
141
|
/**
|
|
130
142
|
* GitLab Code Quality: a JSON array of issues, which a merge request shows
|
|
131
143
|
* beside the lines they are on. The fingerprint is how GitLab tells a new
|
|
132
|
-
* issue from one it has seen, so it hashes the
|
|
133
|
-
*
|
|
134
|
-
*
|
|
135
|
-
*
|
|
144
|
+
* issue from one it has seen, so it hashes the finding's identity and nothing
|
|
145
|
+
* that changes while the problem stays: not the line, so a finding that moves
|
|
146
|
+
* down a page is the same finding, and not the message, so rewording one, or
|
|
147
|
+
* naming another file two colliding briefs both write, does not show as one
|
|
148
|
+
* problem fixed and another found. Findings that share an identity - a front
|
|
149
|
+
* matter with two problems - are told apart by their order, the second hashed
|
|
150
|
+
* with a `2`, as spec-graph hashes them. The description carries the next
|
|
151
|
+
* action as well as the message.
|
|
136
152
|
*/
|
|
137
153
|
export function gitlabCodeQuality(findings) {
|
|
138
154
|
const seen = new Map();
|
|
139
155
|
const issues = findings.map((f) => {
|
|
140
|
-
const key =
|
|
141
|
-
const
|
|
142
|
-
seen.set(key,
|
|
156
|
+
const key = JSON.stringify(identity(f));
|
|
157
|
+
const occurrence = (seen.get(key) ?? 0) + 1;
|
|
158
|
+
seen.set(key, occurrence);
|
|
143
159
|
return {
|
|
144
160
|
description: f.hint === undefined ? f.message : `${f.message}. ${f.hint}`,
|
|
145
161
|
check_name: f.rule,
|
|
146
|
-
fingerprint: createHash('sha256')
|
|
162
|
+
fingerprint: createHash('sha256')
|
|
163
|
+
.update(occurrence === 1 ? key : JSON.stringify([...identity(f), occurrence]))
|
|
164
|
+
.digest('hex'),
|
|
147
165
|
severity: GITLAB_SEVERITY[f.severity],
|
|
148
166
|
location: { path: f.file, lines: { begin: f.line } },
|
|
149
167
|
};
|
|
@@ -204,12 +222,56 @@ export function sectionsJson(config) {
|
|
|
204
222
|
...Object.entries(config.types).flatMap(([type, rules]) => rules.map((rule) => describe(rule, type))),
|
|
205
223
|
];
|
|
206
224
|
}
|
|
207
|
-
/**
|
|
225
|
+
/**
|
|
226
|
+
* What may stand between an id and the rest of a title: an em or an en dash,
|
|
227
|
+
* a colon, ASCII or full-width, with or without spaces, or a hyphen with a
|
|
228
|
+
* space on each side, so that `001-2 migration` keeps its id.
|
|
229
|
+
*/
|
|
230
|
+
const ID_SEPARATOR = /^(?:\s*[\u2014\u2013:\uff1a]|\s+-(?=\s))\s*(?=\S)/u;
|
|
231
|
+
/**
|
|
232
|
+
* A title as a table shows it, without the id it repeats: `new` writes
|
|
233
|
+
* `# 012 — Rotate tokens`, and the table has an id column already. Only the
|
|
234
|
+
* brief's own id comes off, compared as ids are, so that `12 - x` in brief
|
|
235
|
+
* `012` loses it and `0010 — x` in brief `001` keeps it, and only before a
|
|
236
|
+
* separator: `Fix - the login bug` and `2026:roadmap` are titles. For
|
|
237
|
+
* display alone: `Brief.title`, and every JSON document, keep the title as
|
|
238
|
+
* written.
|
|
239
|
+
*/
|
|
240
|
+
export function titleWithoutId(title, id) {
|
|
241
|
+
if (id === null)
|
|
242
|
+
return title;
|
|
243
|
+
const text = title.trimStart();
|
|
244
|
+
// An id of digits is compared by value, so the title's own leading digits
|
|
245
|
+
// are the candidate. A title with none has `''`, which no id's key equals;
|
|
246
|
+
// any other text in its place fails `startsWith` and answers the same.
|
|
247
|
+
const lead = /^\d+$/.test(id) ? (/^\d+/.exec(text)?.[0] ?? '') : id;
|
|
248
|
+
if (!text.startsWith(lead) || idKey(lead) !== idKey(id))
|
|
249
|
+
return title;
|
|
250
|
+
const separator = ID_SEPARATOR.exec(text.slice(lead.length));
|
|
251
|
+
return separator === null ? title : text.slice(lead.length + separator[0].length);
|
|
252
|
+
}
|
|
253
|
+
function shownTitle(brief) {
|
|
254
|
+
return brief.title === null ? brief.name : titleWithoutId(brief.title, brief.id);
|
|
255
|
+
}
|
|
256
|
+
/**
|
|
257
|
+
* A text padded to `width` columns of a terminal. `padEnd` counts UTF-16
|
|
258
|
+
* units, and a Han character is one unit and two columns, so `已接受` padded
|
|
259
|
+
* so fell three columns short. Every width here is the widest of the texts it
|
|
260
|
+
* pads, so none is longer than its width.
|
|
261
|
+
*/
|
|
262
|
+
function padEnd(text, width) {
|
|
263
|
+
return text + ' '.repeat(width - displayWidth(text));
|
|
264
|
+
}
|
|
265
|
+
/** A text padded on the left to `width` columns of a terminal, as {@link padEnd} pads on the right. */
|
|
266
|
+
function padStart(text, width) {
|
|
267
|
+
return ' '.repeat(width - displayWidth(text)) + text;
|
|
268
|
+
}
|
|
269
|
+
/** Columns padded to their widest cell, in a terminal's columns; every row has the header's length. */
|
|
208
270
|
function table(header, rows) {
|
|
209
271
|
const all = [header, ...rows];
|
|
210
|
-
const widths = header.map((_, c) => Math.max(...all.map((r) => r[c]
|
|
272
|
+
const widths = header.map((_, c) => Math.max(...all.map((r) => displayWidth(r[c]))));
|
|
211
273
|
return all.map((r) => r
|
|
212
|
-
.map((cell, c) => (c === r.length - 1 ? cell :
|
|
274
|
+
.map((cell, c) => (c === r.length - 1 ? cell : padEnd(cell, widths[c])))
|
|
213
275
|
.join(' ')
|
|
214
276
|
.trimEnd());
|
|
215
277
|
}
|
|
@@ -218,11 +280,11 @@ export function prettyList(rows, style) {
|
|
|
218
280
|
return 'no briefs';
|
|
219
281
|
const lines = table(['ID', 'STATUS', 'WAVE', 'TASKS', 'READY', 'TITLE'], rows.map(({ brief, ready, waitingOn }) => [
|
|
220
282
|
brief.id ?? '?',
|
|
221
|
-
brief.
|
|
283
|
+
brief.statusWord ?? brief.status ?? '?',
|
|
222
284
|
brief.wave === null ? '-' : String(brief.wave),
|
|
223
285
|
`${brief.tasks.filter((t) => t.checked).length}/${brief.tasks.length}`,
|
|
224
286
|
brief.phase === 'archived' ? '-' : ready ? 'yes' : waitingOn.length > 0 ? `after ${waitingOn.join(', ')}` : 'no',
|
|
225
|
-
brief
|
|
287
|
+
shownTitle(brief),
|
|
226
288
|
]));
|
|
227
289
|
return [paint(style, 'dim', lines[0]), ...lines.slice(1)].join('\n');
|
|
228
290
|
}
|
|
@@ -233,12 +295,12 @@ export function prettyMatrix(report, style) {
|
|
|
233
295
|
const title = wave.wave === null ? 'all live briefs' : `wave ${wave.wave}`;
|
|
234
296
|
out.push(paint(style, 'bold', `${title} \u00b7 ${plural(wave.briefs.length, 'brief')}`));
|
|
235
297
|
const names = wave.briefs.map(label);
|
|
236
|
-
const width = Math.max(3, ...names.map(
|
|
298
|
+
const width = Math.max(3, ...names.map(displayWidth));
|
|
237
299
|
const pairs = (list) => new Set(list.flatMap((p) => [`${label(p.a)}\u0000${label(p.b)}`, `${label(p.b)}\u0000${label(p.a)}`]));
|
|
238
300
|
const hits = pairs(wave.collisions);
|
|
239
301
|
const unknown = pairs(wave.undecided);
|
|
240
302
|
const near = pairs(wave.shared);
|
|
241
|
-
out.push(` ${''.
|
|
303
|
+
out.push(` ${' '.repeat(width)} ${names.map((n) => padStart(n, width)).join(' ')}`);
|
|
242
304
|
for (const row of names) {
|
|
243
305
|
const cells = names.map((col) => {
|
|
244
306
|
const key = `${row}\u0000${col}`;
|
|
@@ -253,12 +315,12 @@ export function prettyMatrix(report, style) {
|
|
|
253
315
|
: '\u00b7';
|
|
254
316
|
return `${' '.repeat(width - 1)}${mark}`;
|
|
255
317
|
});
|
|
256
|
-
out.push(` ${
|
|
318
|
+
out.push(` ${padEnd(row, width)} ${cells.join(' ')}`);
|
|
257
319
|
}
|
|
258
320
|
// One mark per pair of briefs; each further pair of patterns on a line beneath it.
|
|
259
321
|
for (const c of wave.collisions) {
|
|
260
322
|
c.overlaps.forEach((o, i) => {
|
|
261
|
-
out.push(` ${i === 0 ? paint(style, 'red', 'X') : ' '} ${label(c.a)} "${o.patterns[0]}" and ${label(c.b)} "${o.patterns[1]}" both cover ${o
|
|
323
|
+
out.push(` ${i === 0 ? paint(style, 'red', 'X') : ' '} ${label(c.a)} "${o.patterns[0]}" and ${label(c.b)} "${o.patterns[1]}" both cover ${witnessText(o)}`);
|
|
262
324
|
});
|
|
263
325
|
}
|
|
264
326
|
for (const u of wave.undecided) {
|
|
@@ -288,6 +350,15 @@ export function prettyMatrix(report, style) {
|
|
|
288
350
|
out.push('no live briefs');
|
|
289
351
|
return out.join('\n').trimEnd();
|
|
290
352
|
}
|
|
353
|
+
/**
|
|
354
|
+
* A pair of patterns that meets, and the file named: `inTree` is `true` for a
|
|
355
|
+
* file the tree holds, `false` for an example the search built, `null` when
|
|
356
|
+
* the tree could not be read. Added to schema 2: a reader of it that does not
|
|
357
|
+
* know the field reads the rest as before.
|
|
358
|
+
*/
|
|
359
|
+
function overlapJson(o) {
|
|
360
|
+
return { patterns: o.patterns, witness: o.witness, inTree: o.inTree };
|
|
361
|
+
}
|
|
291
362
|
/** The matrix as JSON: briefs by id, and a collision per pair of briefs. */
|
|
292
363
|
export function matrixJson(report) {
|
|
293
364
|
return {
|
|
@@ -297,7 +368,7 @@ export function matrixJson(report) {
|
|
|
297
368
|
collisions: w.collisions.map((c) => ({
|
|
298
369
|
a: c.a.id,
|
|
299
370
|
b: c.b.id,
|
|
300
|
-
overlaps: c.overlaps.map(
|
|
371
|
+
overlaps: c.overlaps.map(overlapJson),
|
|
301
372
|
})),
|
|
302
373
|
undecided: w.undecided.map((u) => ({ a: u.a.id, b: u.b.id, patterns: u.patterns })),
|
|
303
374
|
sharedDirectories: w.shared.map((s) => ({ a: s.a.id, b: s.b.id, directories: s.directories })),
|
|
@@ -323,21 +394,20 @@ function wavesOf(s) {
|
|
|
323
394
|
export function prettySchedule(s, written, style) {
|
|
324
395
|
const label = (b) => b.id ?? b.name;
|
|
325
396
|
const out = [];
|
|
326
|
-
const width = Math.max(3, ...s.placements.map((p) => label(p.brief)
|
|
327
|
-
const
|
|
328
|
-
const titles = Math.max(0, ...s.placements.map((p) => titleOf(p.brief).length));
|
|
397
|
+
const width = Math.max(3, ...s.placements.map((p) => displayWidth(label(p.brief))));
|
|
398
|
+
const titles = Math.max(0, ...s.placements.map((p) => displayWidth(shownTitle(p.brief))));
|
|
329
399
|
const waves = wavesOf(s);
|
|
330
400
|
for (const wave of waves) {
|
|
331
401
|
const here = s.placements.filter((p) => p.proposed === wave);
|
|
332
402
|
out.push(paint(style, 'bold', `wave ${wave} · ${plural(here.length, 'brief')}`));
|
|
333
403
|
for (const p of here) {
|
|
334
|
-
const title =
|
|
404
|
+
const title = shownTitle(p.brief);
|
|
335
405
|
if (p.proposed === p.declared) {
|
|
336
|
-
out.push(` ${label(p.brief)
|
|
406
|
+
out.push(` ${padEnd(label(p.brief), width)} ${title}`);
|
|
337
407
|
continue;
|
|
338
408
|
}
|
|
339
409
|
const from = p.declared === null ? 'no wave' : `wave ${p.declared}`;
|
|
340
|
-
out.push(` ${label(p.brief)
|
|
410
|
+
out.push(` ${padEnd(label(p.brief), width)} ${padEnd(title, titles)} ${paint(style, 'yellow', `moves from ${from}`)}`);
|
|
341
411
|
// Why the declared wave holds or does not comes first: it decides whether the move is asked for.
|
|
342
412
|
const verdict = p.declared === null ? [] : holds(p) ? [`wave ${p.declared} also holds`] : [`wave ${p.declared} does not hold: ${breachReasons(p).join('; ')}`];
|
|
343
413
|
for (const reason of [...verdict, ...reasons(p)])
|
|
@@ -379,12 +449,12 @@ export function prettySchedule(s, written, style) {
|
|
|
379
449
|
/** The schedule as JSON: a row per placed brief with its declared and proposed wave and why. */
|
|
380
450
|
export function scheduleJson(s) {
|
|
381
451
|
const breach = (b) => b.reason === 'collision'
|
|
382
|
-
? { reason: b.reason, brief: b.brief.id, overlaps: b.overlaps.map(
|
|
452
|
+
? { reason: b.reason, brief: b.brief.id, overlaps: b.overlaps.map(overlapJson) }
|
|
383
453
|
: { reason: b.reason, brief: b.brief.id, wave: b.wave };
|
|
384
454
|
const passed = (p) => {
|
|
385
455
|
const base = { wave: p.wave, reason: p.reason, brief: p.brief.id };
|
|
386
456
|
if (p.reason === 'collision')
|
|
387
|
-
return { ...base, overlaps: p.overlaps.map(
|
|
457
|
+
return { ...base, overlaps: p.overlaps.map(overlapJson) };
|
|
388
458
|
if (p.reason === 'undecided')
|
|
389
459
|
return { ...base, patterns: p.patterns };
|
|
390
460
|
return base;
|
package/dist/report.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"report.js","sourceRoot":"","sources":["../src/report.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Rendering: findings, lists, the collision matrix and plans, for a person at\n * a terminal or for the machine reading the job.\n *\n * `json` is a document with a version, for orchestrators. `sarif` is SARIF\n * 2.1.0, for code-scanning upload. `github` is workflow commands, which put a\n * finding on the line of the pull request with no upload and no permission.\n * `gitlab` is a Code Quality report, the artifact a GitLab merge request reads,\n * so the family is not GitHub's alone.\n */\n\nimport { createHash } from 'node:crypto';\n\nimport type { Plan } from './archive.js';\nimport type { Brief } from './brief.js';\nimport type { Config, SectionRule } from './config.js';\nimport type { CollisionReport } from './collisions.js';\nimport { summarise } from './lint.js';\nimport { ARCHIVE_RULES, COLLISION_RULES, RULES } from './rules.js';\nimport { type Breach, breachReasons, holds, moves, type Passed, reasons, type Schedule } from './schedule.js';\nimport { inWords } from './text.js';\nimport type { Finding, Severity } from './types.js';\n\nexport type Format = 'pretty' | 'json' | 'sarif' | 'github' | 'gitlab';\n\nexport const FORMATS: readonly Format[] = ['pretty', 'json', 'sarif', 'github', 'gitlab'];\n\n/**\n * The version of the JSON documents this tool prints, every command's alike.\n * Bumped when a field changes meaning. 2: a collision in `matrix` is a pair of\n * briefs, with every pair of patterns that meets and a witness that is always\n * a file; a shared-directory entry lists its directories; and deferred briefs,\n * and the briefs waiting on them, leave `waves[].briefs` for `deferred` and\n * `waiting`.\n */\nexport const JSON_SCHEMA_VERSION = 2;\n\nexport interface Style {\n readonly color: boolean;\n}\n\nconst CODES: Readonly<Record<string, readonly [number, number]>> = {\n red: [31, 39],\n yellow: [33, 39],\n cyan: [36, 39],\n green: [32, 39],\n dim: [2, 22],\n bold: [1, 22],\n};\n\nexport function paint(style: Style, color: keyof typeof CODES, text: string): string {\n const code = CODES[color];\n return style.color && code !== undefined ? `\\u001b[${code[0]}m${text}\\u001b[${code[1]}m` : text;\n}\n\nconst SEVERITY_COLOR: Readonly<Record<Severity, keyof typeof CODES>> = { error: 'red', warning: 'yellow', note: 'cyan' };\n\nfunction plural(count: number, word: string): string {\n return `${count} ${word}${count === 1 ? '' : 's'}`;\n}\n\nexport function summaryLine(findings: readonly Finding[]): string {\n const s = summarise(findings);\n return `${plural(s.errors, 'error')}, ${plural(s.warnings, 'warning')}, ${plural(s.notes, 'note')}`;\n}\n\nexport function prettyFindings(findings: readonly Finding[], style: Style): string {\n const out: string[] = [];\n let file: string | undefined;\n const width = Math.max(1, ...findings.map((f) => String(f.line).length));\n for (const f of findings) {\n if (f.file !== file) {\n if (file !== undefined) out.push('');\n out.push(paint(style, 'bold', f.file));\n file = f.file;\n }\n const severity = paint(style, SEVERITY_COLOR[f.severity], f.severity.padEnd(7));\n out.push(` ${String(f.line).padStart(width)} ${severity} ${f.message} ${paint(style, 'dim', f.rule)}`);\n if (f.hint !== undefined) out.push(` ${' '.repeat(width)} ${paint(style, 'dim', f.hint)}`);\n }\n return out.join('\\n');\n}\n\nexport function jsonDocument(command: string, version: string, body: Record<string, unknown>): string {\n return `${JSON.stringify({ tool: 'spec-brief', version, schemaVersion: JSON_SCHEMA_VERSION, command, ...body }, null, 2)}\\n`;\n}\n\nexport function findingJson(f: Finding): Record<string, unknown> {\n const out: Record<string, unknown> = { rule: f.rule, severity: f.severity, file: f.file, line: f.line, message: f.message };\n if (f.brief !== undefined) out['brief'] = f.brief;\n if (f.hint !== undefined) out['hint'] = f.hint;\n if (f.path !== undefined) out['path'] = f.path;\n if (f.paths !== undefined) out['paths'] = f.paths;\n return out;\n}\n\nconst SARIF_LEVEL: Readonly<Record<Severity, string>> = { error: 'error', warning: 'warning', note: 'note' };\n\nexport function sarif(findings: readonly Finding[], version: string): string {\n const described = new Map([...RULES, ...COLLISION_RULES, ...ARCHIVE_RULES].map((r) => [r.id, r]));\n const ids = [...new Set(findings.map((f) => f.rule))].sort();\n const document = {\n $schema: 'https://json.schemastore.org/sarif-2.1.0.json',\n version: '2.1.0',\n runs: [\n {\n tool: {\n driver: {\n name: 'spec-brief',\n version,\n informationUri: 'https://github.com/DescentVTT/spec-brief',\n rules: ids.map((id) => {\n const rule = described.get(id);\n return {\n id,\n shortDescription: { text: rule?.description ?? id },\n ...(rule !== undefined && rule.severity !== 'off'\n ? { defaultConfiguration: { level: SARIF_LEVEL[rule.severity] } }\n : {}),\n };\n }),\n },\n },\n results: findings.map((f) => ({\n ruleId: f.rule,\n level: SARIF_LEVEL[f.severity],\n message: { text: f.hint === undefined ? f.message : `${f.message}. ${f.hint}` },\n locations: [\n {\n physicalLocation: {\n artifactLocation: { uri: f.file, uriBaseId: '%SRCROOT%' },\n region: { startLine: f.line },\n },\n },\n ],\n })),\n },\n ],\n };\n return `${JSON.stringify(document, null, 2)}\\n`;\n}\n\n/**\n * GitLab's Code Quality severities. An error fails the run but is not a\n * security hole or a crash, which is what `critical` and `blocker` say in\n * GitLab's own reports, so the scale tops out at `major`.\n */\nconst GITLAB_SEVERITY: Readonly<Record<Severity, string>> = { error: 'major', warning: 'minor', note: 'info' };\n\n/**\n * GitLab Code Quality: a JSON array of issues, which a merge request shows\n * beside the lines they are on. The fingerprint is how GitLab tells a new\n * issue from one it has seen, so it hashes the rule, the file and the message\n * and not the line: a finding that moves down a page is the same finding. Two\n * findings with the same three - a section duplicated twice - are told apart\n * by their order.\n */\nexport function gitlabCodeQuality(findings: readonly Finding[]): string {\n const seen = new Map<string, number>();\n const issues = findings.map((f) => {\n const key = `${f.rule}\\u0000${f.file}\\u0000${f.message}`;\n const repeat = seen.get(key) ?? 0;\n seen.set(key, repeat + 1);\n return {\n description: f.hint === undefined ? f.message : `${f.message}. ${f.hint}`,\n check_name: f.rule,\n fingerprint: createHash('sha256').update(repeat === 0 ? key : `${key}\\u0000${repeat}`).digest('hex'),\n severity: GITLAB_SEVERITY[f.severity],\n location: { path: f.file, lines: { begin: f.line } },\n };\n });\n return `${JSON.stringify(issues, null, 2)}\\n`;\n}\n\nfunction escapeData(text: string): string {\n return text.replace(/%/g, '%25').replace(/\\r/g, '%0D').replace(/\\n/g, '%0A');\n}\n\nfunction escapeProperty(text: string): string {\n return escapeData(text).replace(/:/g, '%3A').replace(/,/g, '%2C');\n}\n\nconst GITHUB_COMMAND: Readonly<Record<Severity, string>> = { error: 'error', warning: 'warning', note: 'notice' };\n\nexport function githubCommands(findings: readonly Finding[]): string {\n return findings\n .map((f) => {\n const message = f.hint === undefined ? f.message : `${f.message}. ${f.hint}`;\n const properties = `file=${escapeProperty(f.file)},line=${f.line},title=${escapeProperty(`spec-brief ${f.rule}`)}`;\n return `::${GITHUB_COMMAND[f.severity]} ${properties}::${escapeData(message)}\\n`;\n })\n .join('');\n}\n\nexport function briefJson(brief: Brief, extra: Record<string, unknown> = {}): Record<string, unknown> {\n return {\n id: brief.id,\n file: brief.file,\n title: brief.title,\n phase: brief.phase,\n status: brief.status,\n type: brief.type,\n wave: brief.wave,\n dependsOn: brief.dependsOn,\n affectedFiles: brief.affectedFiles,\n protectedFiles: brief.protectedFiles,\n trigger: brief.trigger,\n tasks: { total: brief.tasks.length, checked: brief.tasks.filter((t) => t.checked).length },\n ...extra,\n };\n}\n\n/**\n * The sections the configuration asks for, each with what it must answer:\n * those every live brief carries, with `type` null, then those each type adds.\n * A tool that helps write a brief asks for these rather than for names it\n * knows in advance.\n */\nexport function sectionsJson(config: Config): Record<string, unknown>[] {\n const describe = (rule: SectionRule, type: string | null): Record<string, unknown> => ({\n name: rule.name,\n type,\n aliases: rule.aliases,\n optional: rule.optional,\n checklist: rule.checklist,\n mustContain: rule.mustContain,\n hint: rule.hint ?? null,\n });\n return [\n ...config.sections.map((rule) => describe(rule, null)),\n ...Object.entries(config.types).flatMap(([type, rules]) => rules.map((rule) => describe(rule, type))),\n ];\n}\n\n/** Columns padded to their widest cell; every row has the header's length. */\nfunction table(header: readonly string[], rows: readonly (readonly string[])[]): string[] {\n const all = [header, ...rows];\n const widths = header.map((_, c) => Math.max(...all.map((r) => (r[c] as string).length)));\n return all.map((r) =>\n r\n .map((cell, c) => (c === r.length - 1 ? cell : cell.padEnd(widths[c] as number)))\n .join(' ')\n .trimEnd(),\n );\n}\n\nexport interface ListRow {\n readonly brief: Brief;\n readonly ready: boolean;\n readonly waitingOn: readonly string[];\n}\n\nexport function prettyList(rows: readonly ListRow[], style: Style): string {\n if (rows.length === 0) return 'no briefs';\n const lines = table(\n ['ID', 'STATUS', 'WAVE', 'TASKS', 'READY', 'TITLE'],\n rows.map(({ brief, ready, waitingOn }) => [\n brief.id ?? '?',\n brief.status ?? brief.statusWord ?? '?',\n brief.wave === null ? '-' : String(brief.wave),\n `${brief.tasks.filter((t) => t.checked).length}/${brief.tasks.length}`,\n brief.phase === 'archived' ? '-' : ready ? 'yes' : waitingOn.length > 0 ? `after ${waitingOn.join(', ')}` : 'no',\n brief.title ?? brief.name,\n ]),\n );\n return [paint(style, 'dim', lines[0] as string), ...lines.slice(1)].join('\\n');\n}\n\nexport function prettyMatrix(report: CollisionReport, style: Style): string {\n const out: string[] = [];\n const label = (b: Brief): string => b.id ?? b.name;\n for (const wave of report.waves) {\n const title = wave.wave === null ? 'all live briefs' : `wave ${wave.wave}`;\n out.push(paint(style, 'bold', `${title} \\u00b7 ${plural(wave.briefs.length, 'brief')}`));\n const names = wave.briefs.map(label);\n const width = Math.max(3, ...names.map((n) => n.length));\n const pairs = (list: readonly { readonly a: Brief; readonly b: Brief }[]): Set<string> =>\n new Set(list.flatMap((p) => [`${label(p.a)}\\u0000${label(p.b)}`, `${label(p.b)}\\u0000${label(p.a)}`]));\n const hits = pairs(wave.collisions);\n const unknown = pairs(wave.undecided);\n const near = pairs(wave.shared);\n out.push(` ${''.padEnd(width)} ${names.map((n) => n.padStart(width)).join(' ')}`);\n for (const row of names) {\n const cells = names.map((col) => {\n const key = `${row}\\u0000${col}`;\n const mark =\n row === col\n ? '\\u00b7'\n : hits.has(key)\n ? paint(style, 'red', 'X')\n : unknown.has(key)\n ? paint(style, 'yellow', '?')\n : near.has(key)\n ? paint(style, 'yellow', '~')\n : '\\u00b7';\n return `${' '.repeat(width - 1)}${mark}`;\n });\n out.push(` ${row.padEnd(width)} ${cells.join(' ')}`);\n }\n // One mark per pair of briefs; each further pair of patterns on a line beneath it.\n for (const c of wave.collisions) {\n c.overlaps.forEach((o, i) => {\n out.push(` ${i === 0 ? paint(style, 'red', 'X') : ' '} ${label(c.a)} \"${o.patterns[0]}\" and ${label(c.b)} \"${o.patterns[1]}\" both cover ${o.witness}`);\n });\n }\n for (const u of wave.undecided) {\n u.patterns.forEach(([x, y], i) => {\n out.push(` ${i === 0 ? paint(style, 'yellow', '?') : ' '} ${label(u.a)} \"${x}\" and ${label(u.b)} \"${y}\": undecided within the search's budget`);\n });\n }\n for (const s of wave.shared) {\n out.push(` ${paint(style, 'yellow', '~')} ${label(s.a)} and ${label(s.b)} both write into ${inWords(s.directories.map((d) => `${d}/`))}`);\n }\n for (const b of wave.unscoped) {\n out.push(` ${paint(style, 'cyan', '?')} ${label(b)} declares no affectedFiles and cannot be checked`);\n }\n out.push('');\n }\n if (report.unscheduled.length > 0) {\n out.push(paint(style, 'dim', `no wave: ${report.unscheduled.map(label).join(', ')}`));\n }\n for (const w of report.waiting) {\n const why = w.waitsOn.status === 'deferred' ? 'which is deferred' : 'which waits on deferred work';\n out.push(`${paint(style, 'dim', 'waits:')} ${label(w.brief)} on ${label(w.waitsOn)}, ${why}`);\n }\n if (report.deferred.length > 0) {\n out.push(paint(style, 'dim', `deferred: ${report.deferred.map(label).join(', ')}`));\n }\n if (report.waves.length === 0 && report.unscheduled.length === 0 && report.deferred.length === 0) out.push('no live briefs');\n return out.join('\\n').trimEnd();\n}\n\n/** The matrix as JSON: briefs by id, and a collision per pair of briefs. */\nexport function matrixJson(report: CollisionReport): Record<string, unknown> {\n return {\n waves: report.waves.map((w) => ({\n wave: w.wave,\n briefs: w.briefs.map((b) => b.id),\n collisions: w.collisions.map((c) => ({\n a: c.a.id,\n b: c.b.id,\n overlaps: c.overlaps.map((o) => ({ patterns: o.patterns, witness: o.witness })),\n })),\n undecided: w.undecided.map((u) => ({ a: u.a.id, b: u.b.id, patterns: u.patterns })),\n sharedDirectories: w.shared.map((s) => ({ a: s.a.id, b: s.b.id, directories: s.directories })),\n unscoped: w.unscoped.map((b) => b.id),\n })),\n unscheduled: report.unscheduled.map((b) => b.id),\n deferred: report.deferred.map((b) => b.id),\n waiting: report.waiting.map((w) => ({ id: w.brief.id, file: w.brief.file, waitsOn: w.waitsOn.id })),\n };\n}\n\n/**\n * The waves a schedule uses, in order. They appear in order too: a brief goes\n * into a wave only when it is the first or the one before it is occupied.\n */\nfunction wavesOf(s: Schedule): number[] {\n return [...new Set(s.placements.map((p) => p.proposed))];\n}\n\n/**\n * The schedule for a person: each wave with its briefs, and under a brief whose\n * wave would change, why it goes where it goes. `written` is `null` when\n * nothing was asked to be written.\n */\nexport function prettySchedule(s: Schedule, written: readonly string[] | null, style: Style): string {\n const label = (b: Brief): string => b.id ?? b.name;\n const out: string[] = [];\n const width = Math.max(3, ...s.placements.map((p) => label(p.brief).length));\n const titleOf = (b: Brief): string => b.title ?? b.name;\n const titles = Math.max(0, ...s.placements.map((p) => titleOf(p.brief).length));\n const waves = wavesOf(s);\n for (const wave of waves) {\n const here = s.placements.filter((p) => p.proposed === wave);\n out.push(paint(style, 'bold', `wave ${wave} · ${plural(here.length, 'brief')}`));\n for (const p of here) {\n const title = titleOf(p.brief);\n if (p.proposed === p.declared) {\n out.push(` ${label(p.brief).padEnd(width)} ${title}`);\n continue;\n }\n const from = p.declared === null ? 'no wave' : `wave ${p.declared}`;\n out.push(` ${label(p.brief).padEnd(width)} ${title.padEnd(titles)} ${paint(style, 'yellow', `moves from ${from}`)}`);\n // Why the declared wave holds or does not comes first: it decides whether the move is asked for.\n const verdict = p.declared === null ? [] : holds(p) ? [`wave ${p.declared} also holds`] : [`wave ${p.declared} does not hold: ${breachReasons(p).join('; ')}`];\n for (const reason of [...verdict, ...reasons(p)]) out.push(` ${' '.repeat(width)} ${paint(style, 'dim', reason)}`);\n }\n }\n if (waves.length > 0) out.push('');\n for (const cycle of s.cycles) out.push(`${paint(style, 'red', 'cycle:')} ${cycle.map(label).join(' -> ')}`);\n for (const u of s.unplaced) {\n const why = u.because === 'deferred' ? 'which is deferred' : u.because === 'cycle' ? 'which is in a cycle' : 'which is not placed';\n out.push(`${paint(style, 'dim', 'waits:')} ${label(u.brief)} on ${label(u.waitsOn)}, ${why}`);\n }\n if (s.deferred.length > 0) out.push(paint(style, 'dim', `deferred: ${s.deferred.map(label).join(', ')}`));\n const moving = moves(s).length;\n if (written !== null && written.length > 0) {\n out.push(`wrote the wave of ${plural(written.length, 'brief')}: ${written.join(', ')}`);\n } else if (written !== null && moving > 0) {\n out.push(paint(style, 'red', s.cycles.length > 0 ? 'nothing was written: the dependencies form a cycle' : 'nothing was written: a front matter cannot be edited'));\n } else if (moving > 0 && moves(s).every(holds)) {\n out.push(`${plural(moving, 'brief')} could move, and the declared waves hold; \"spec-brief schedule --write\" writes the computed ones`);\n } else if (moving > 0) {\n out.push(`${plural(moving, 'brief')} would move; \"spec-brief schedule --write\" writes the waves`);\n } else if (s.placements.length > 0) {\n out.push('the declared waves hold');\n } else if (s.cycles.length === 0 && s.deferred.length === 0) {\n // A brief is unplaced only behind a cycle or a deferral, so this is a corpus with no live brief.\n out.push('no live briefs');\n }\n return out.join('\\n');\n}\n\n/** The schedule as JSON: a row per placed brief with its declared and proposed wave and why. */\nexport function scheduleJson(s: Schedule): Record<string, unknown> {\n const breach = (b: Breach): Record<string, unknown> =>\n b.reason === 'collision'\n ? { reason: b.reason, brief: b.brief.id, overlaps: b.overlaps.map((o) => ({ patterns: o.patterns, witness: o.witness })) }\n : { reason: b.reason, brief: b.brief.id, wave: b.wave };\n const passed = (p: Passed): Record<string, unknown> => {\n const base = { wave: p.wave, reason: p.reason, brief: p.brief.id };\n if (p.reason === 'collision') return { ...base, overlaps: p.overlaps.map((o) => ({ patterns: o.patterns, witness: o.witness })) };\n if (p.reason === 'undecided') return { ...base, patterns: p.patterns };\n return base;\n };\n const waves = wavesOf(s);\n return {\n first: s.first,\n waves: waves.map((wave) => ({ wave, briefs: s.placements.filter((p) => p.proposed === wave).map((p) => p.brief.id) })),\n briefs: s.placements.map((p) => ({\n id: p.brief.id,\n file: p.brief.file,\n declared: p.declared,\n proposed: p.proposed,\n moves: p.proposed !== p.declared,\n holds: holds(p),\n breaches: p.breaches.map(breach),\n after: p.after === null ? null : { brief: p.after.brief.id, wave: p.after.wave },\n passed: p.passed.map(passed),\n unscoped: p.unscoped,\n reasons: reasons(p),\n })),\n unplaced: s.unplaced.map((u) => ({ id: u.brief.id, file: u.brief.file, waitsOn: u.waitsOn.id, because: u.because })),\n cycles: s.cycles.map((cycle) => cycle.map((b) => b.id)),\n deferred: s.deferred.map((b) => b.id),\n };\n}\n\nexport function prettyPlan(plan: Plan, dryRun: boolean, style: Style): string {\n const out: string[] = [];\n const verb = plan.action === 'archive' ? 'archive' : 'unarchive';\n if (plan.done) return `${plan.brief.file} is already ${plan.action === 'archive' ? 'archived' : 'live'}; nothing to do`;\n if (plan.blocking.length > 0) {\n out.push(paint(style, 'red', `cannot ${verb} ${plan.brief.file}:`), prettyFindings(plan.blocking, style));\n if (plan.warnings.length > 0) out.push('', prettyFindings(plan.warnings, style));\n return out.join('\\n');\n }\n out.push(`${dryRun ? 'would move' : 'moved'} ${plan.from} -> ${plan.to}`);\n if (plan.linksRewritten > 0) out.push(` ${plural(plan.linksRewritten, 'relative link')} rewritten`);\n for (const file of plan.inboundRewritten) out.push(` ${file}: links to it rewritten`);\n for (const f of plan.inboundFrozen) out.push(` ${f.file}:${f.line}: links to the old path, and is frozen, so it was left as it is`);\n if (plan.changes.length > 0) out.push(` the round changed ${plural(plan.changes.length, 'file')}`);\n if (plan.warnings.length > 0) out.push('', prettyFindings(plan.warnings, style));\n if (dryRun && plan.banner.length > 0) out.push('', paint(style, 'dim', 'banner:'), ...plan.banner.map((l) => ` ${l}`));\n if (!dryRun) out.push('', paint(style, 'dim', 'nothing was committed; review the change and commit it with the round'));\n return out.join('\\n');\n}\n\nexport function planJson(plan: Plan): Record<string, unknown> {\n return {\n action: plan.action,\n brief: plan.brief.id,\n from: plan.from,\n to: plan.to,\n done: plan.done,\n refused: plan.blocking.length > 0,\n blocking: plan.blocking.map(findingJson),\n warnings: plan.warnings.map(findingJson),\n linksRewritten: plan.linksRewritten,\n inboundRewritten: plan.inboundRewritten,\n inboundFrozen: plan.inboundFrozen,\n operations: plan.ops.map((op) => ({ kind: op.kind, path: op.path })),\n banner: plan.banner,\n changes: plan.changes,\n };\n}\n"]}
|
|
1
|
+
{"version":3,"file":"report.js","sourceRoot":"","sources":["../src/report.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Rendering: findings, lists, the collision matrix and plans, for a person at\n * a terminal or for the machine reading the job.\n *\n * `json` is a document with a version, for orchestrators. `sarif` is SARIF\n * 2.1.0, for code-scanning upload. `github` is workflow commands, which put a\n * finding on the line of the pull request with no upload and no permission.\n * `gitlab` is a Code Quality report, the artifact a GitLab merge request reads,\n * so the family is not GitHub's alone.\n */\n\nimport { createHash } from 'node:crypto';\n\nimport type { Plan } from './archive.js';\nimport type { Brief } from './brief.js';\nimport type { Config, SectionRule } from './config.js';\nimport type { CollisionReport, Overlap } from './collisions.js';\nimport { idKey } from './corpus.js';\nimport { summarise } from './lint.js';\nimport { ARCHIVE_RULES, COLLISION_RULES, RULES } from './rules.js';\nimport { type Breach, breachReasons, holds, moves, type Passed, reasons, type Schedule } from './schedule.js';\nimport { witnessText } from './scope.js';\nimport { inWords } from './text.js';\nimport type { Finding, Severity } from './types.js';\nimport { displayWidth } from './vendor/spec-core/text/index.js';\n\nexport type Format = 'pretty' | 'json' | 'sarif' | 'github' | 'gitlab';\n\nexport const FORMATS: readonly Format[] = ['pretty', 'json', 'sarif', 'github', 'gitlab'];\n\n/**\n * The version of the JSON documents this tool prints, every command's alike.\n * Bumped when a field changes meaning. 2: a collision in `matrix` is a pair of\n * briefs, with every pair of patterns that meets and a witness that is always\n * a file; a shared-directory entry lists its directories; and deferred briefs,\n * and the briefs waiting on them, leave `waves[].briefs` for `deferred` and\n * `waiting`.\n */\nexport const JSON_SCHEMA_VERSION = 2;\n\nexport interface Style {\n readonly color: boolean;\n}\n\nconst CODES: Readonly<Record<string, readonly [number, number]>> = {\n red: [31, 39],\n yellow: [33, 39],\n cyan: [36, 39],\n green: [32, 39],\n dim: [2, 22],\n bold: [1, 22],\n};\n\nexport function paint(style: Style, color: keyof typeof CODES, text: string): string {\n const code = CODES[color];\n return style.color && code !== undefined ? `\\u001b[${code[0]}m${text}\\u001b[${code[1]}m` : text;\n}\n\nconst SEVERITY_COLOR: Readonly<Record<Severity, keyof typeof CODES>> = { error: 'red', warning: 'yellow', note: 'cyan' };\n\nfunction plural(count: number, word: string): string {\n return `${count} ${word}${count === 1 ? '' : 's'}`;\n}\n\nexport function summaryLine(findings: readonly Finding[]): string {\n const s = summarise(findings);\n return `${plural(s.errors, 'error')}, ${plural(s.warnings, 'warning')}, ${plural(s.notes, 'note')}`;\n}\n\nexport function prettyFindings(findings: readonly Finding[], style: Style): string {\n const out: string[] = [];\n let file: string | undefined;\n const width = Math.max(1, ...findings.map((f) => String(f.line).length));\n for (const f of findings) {\n if (f.file !== file) {\n if (file !== undefined) out.push('');\n out.push(paint(style, 'bold', f.file));\n file = f.file;\n }\n const severity = paint(style, SEVERITY_COLOR[f.severity], f.severity.padEnd(7));\n out.push(` ${String(f.line).padStart(width)} ${severity} ${f.message} ${paint(style, 'dim', f.rule)}`);\n if (f.hint !== undefined) out.push(` ${' '.repeat(width)} ${paint(style, 'dim', f.hint)}`);\n }\n return out.join('\\n');\n}\n\nexport function jsonDocument(command: string, version: string, body: Record<string, unknown>): string {\n return `${JSON.stringify({ tool: 'spec-brief', version, schemaVersion: JSON_SCHEMA_VERSION, command, ...body }, null, 2)}\\n`;\n}\n\nexport function findingJson(f: Finding): Record<string, unknown> {\n const out: Record<string, unknown> = { rule: f.rule, severity: f.severity, file: f.file, line: f.line, message: f.message };\n if (f.brief !== undefined) out['brief'] = f.brief;\n if (f.hint !== undefined) out['hint'] = f.hint;\n if (f.path !== undefined) out['path'] = f.path;\n if (f.paths !== undefined) out['paths'] = f.paths;\n return out;\n}\n\nconst SARIF_LEVEL: Readonly<Record<Severity, string>> = { error: 'error', warning: 'warning', note: 'note' };\n\nexport function sarif(findings: readonly Finding[], version: string): string {\n const described = new Map([...RULES, ...COLLISION_RULES, ...ARCHIVE_RULES].map((r) => [r.id, r]));\n const ids = [...new Set(findings.map((f) => f.rule))].sort();\n const document = {\n $schema: 'https://json.schemastore.org/sarif-2.1.0.json',\n version: '2.1.0',\n runs: [\n {\n tool: {\n driver: {\n name: 'spec-brief',\n version,\n informationUri: 'https://github.com/DescentVTT/spec-brief',\n rules: ids.map((id) => {\n const rule = described.get(id);\n return {\n id,\n shortDescription: { text: rule?.description ?? id },\n ...(rule !== undefined && rule.severity !== 'off'\n ? { defaultConfiguration: { level: SARIF_LEVEL[rule.severity] } }\n : {}),\n };\n }),\n },\n },\n results: findings.map((f) => ({\n ruleId: f.rule,\n level: SARIF_LEVEL[f.severity],\n message: { text: f.hint === undefined ? f.message : `${f.message}. ${f.hint}` },\n locations: [\n {\n physicalLocation: {\n artifactLocation: { uri: f.file, uriBaseId: '%SRCROOT%' },\n region: { startLine: f.line },\n },\n },\n ],\n })),\n },\n ],\n };\n return `${JSON.stringify(document, null, 2)}\\n`;\n}\n\n/**\n * GitLab's Code Quality severities, as the family maps them: an error is\n * `major`, a warning `minor`, a note `info`. An error fails the run but is not\n * a security hole or a crash, which is what `critical` and `blocker` say in\n * GitLab's own reports, so the scale tops out at `major`.\n */\nconst GITLAB_SEVERITY: Readonly<Record<Severity, string>> = { error: 'major', warning: 'minor', note: 'info' };\n\n/**\n * What a finding is, whatever it says: its rule, its file, its brief, and what\n * it is about there - a section, a pattern, the other brief of a pair, the one\n * path a refusal names. Never the message, the hint or the line.\n */\nfunction identity(f: Finding): readonly string[] {\n return [f.rule, f.file, f.brief ?? '', f.subject ?? f.path ?? ''];\n}\n\n/**\n * GitLab Code Quality: a JSON array of issues, which a merge request shows\n * beside the lines they are on. The fingerprint is how GitLab tells a new\n * issue from one it has seen, so it hashes the finding's identity and nothing\n * that changes while the problem stays: not the line, so a finding that moves\n * down a page is the same finding, and not the message, so rewording one, or\n * naming another file two colliding briefs both write, does not show as one\n * problem fixed and another found. Findings that share an identity - a front\n * matter with two problems - are told apart by their order, the second hashed\n * with a `2`, as spec-graph hashes them. The description carries the next\n * action as well as the message.\n */\nexport function gitlabCodeQuality(findings: readonly Finding[]): string {\n const seen = new Map<string, number>();\n const issues = findings.map((f) => {\n const key = JSON.stringify(identity(f));\n const occurrence = (seen.get(key) ?? 0) + 1;\n seen.set(key, occurrence);\n return {\n description: f.hint === undefined ? f.message : `${f.message}. ${f.hint}`,\n check_name: f.rule,\n fingerprint: createHash('sha256')\n .update(occurrence === 1 ? key : JSON.stringify([...identity(f), occurrence]))\n .digest('hex'),\n severity: GITLAB_SEVERITY[f.severity],\n location: { path: f.file, lines: { begin: f.line } },\n };\n });\n return `${JSON.stringify(issues, null, 2)}\\n`;\n}\n\nfunction escapeData(text: string): string {\n return text.replace(/%/g, '%25').replace(/\\r/g, '%0D').replace(/\\n/g, '%0A');\n}\n\nfunction escapeProperty(text: string): string {\n return escapeData(text).replace(/:/g, '%3A').replace(/,/g, '%2C');\n}\n\nconst GITHUB_COMMAND: Readonly<Record<Severity, string>> = { error: 'error', warning: 'warning', note: 'notice' };\n\nexport function githubCommands(findings: readonly Finding[]): string {\n return findings\n .map((f) => {\n const message = f.hint === undefined ? f.message : `${f.message}. ${f.hint}`;\n const properties = `file=${escapeProperty(f.file)},line=${f.line},title=${escapeProperty(`spec-brief ${f.rule}`)}`;\n return `::${GITHUB_COMMAND[f.severity]} ${properties}::${escapeData(message)}\\n`;\n })\n .join('');\n}\n\nexport function briefJson(brief: Brief, extra: Record<string, unknown> = {}): Record<string, unknown> {\n return {\n id: brief.id,\n file: brief.file,\n title: brief.title,\n phase: brief.phase,\n status: brief.status,\n type: brief.type,\n wave: brief.wave,\n dependsOn: brief.dependsOn,\n affectedFiles: brief.affectedFiles,\n protectedFiles: brief.protectedFiles,\n trigger: brief.trigger,\n tasks: { total: brief.tasks.length, checked: brief.tasks.filter((t) => t.checked).length },\n ...extra,\n };\n}\n\n/**\n * The sections the configuration asks for, each with what it must answer:\n * those every live brief carries, with `type` null, then those each type adds.\n * A tool that helps write a brief asks for these rather than for names it\n * knows in advance.\n */\nexport function sectionsJson(config: Config): Record<string, unknown>[] {\n const describe = (rule: SectionRule, type: string | null): Record<string, unknown> => ({\n name: rule.name,\n type,\n aliases: rule.aliases,\n optional: rule.optional,\n checklist: rule.checklist,\n mustContain: rule.mustContain,\n hint: rule.hint ?? null,\n });\n return [\n ...config.sections.map((rule) => describe(rule, null)),\n ...Object.entries(config.types).flatMap(([type, rules]) => rules.map((rule) => describe(rule, type))),\n ];\n}\n\n/**\n * What may stand between an id and the rest of a title: an em or an en dash,\n * a colon, ASCII or full-width, with or without spaces, or a hyphen with a\n * space on each side, so that `001-2 migration` keeps its id.\n */\nconst ID_SEPARATOR = /^(?:\\s*[\\u2014\\u2013:\\uff1a]|\\s+-(?=\\s))\\s*(?=\\S)/u;\n\n/**\n * A title as a table shows it, without the id it repeats: `new` writes\n * `# 012 — Rotate tokens`, and the table has an id column already. Only the\n * brief's own id comes off, compared as ids are, so that `12 - x` in brief\n * `012` loses it and `0010 — x` in brief `001` keeps it, and only before a\n * separator: `Fix - the login bug` and `2026:roadmap` are titles. For\n * display alone: `Brief.title`, and every JSON document, keep the title as\n * written.\n */\nexport function titleWithoutId(title: string, id: string | null): string {\n if (id === null) return title;\n const text = title.trimStart();\n // An id of digits is compared by value, so the title's own leading digits\n // are the candidate. A title with none has `''`, which no id's key equals;\n // any other text in its place fails `startsWith` and answers the same.\n const lead = /^\\d+$/.test(id) ? (/^\\d+/.exec(text)?.[0] ?? '') : id;\n if (!text.startsWith(lead) || idKey(lead) !== idKey(id)) return title;\n const separator = ID_SEPARATOR.exec(text.slice(lead.length));\n return separator === null ? title : text.slice(lead.length + separator[0].length);\n}\n\nfunction shownTitle(brief: Brief): string {\n return brief.title === null ? brief.name : titleWithoutId(brief.title, brief.id);\n}\n\n/**\n * A text padded to `width` columns of a terminal. `padEnd` counts UTF-16\n * units, and a Han character is one unit and two columns, so `已接受` padded\n * so fell three columns short. Every width here is the widest of the texts it\n * pads, so none is longer than its width.\n */\nfunction padEnd(text: string, width: number): string {\n return text + ' '.repeat(width - displayWidth(text));\n}\n\n/** A text padded on the left to `width` columns of a terminal, as {@link padEnd} pads on the right. */\nfunction padStart(text: string, width: number): string {\n return ' '.repeat(width - displayWidth(text)) + text;\n}\n\n/** Columns padded to their widest cell, in a terminal's columns; every row has the header's length. */\nfunction table(header: readonly string[], rows: readonly (readonly string[])[]): string[] {\n const all = [header, ...rows];\n const widths = header.map((_, c) => Math.max(...all.map((r) => displayWidth(r[c] as string))));\n return all.map((r) =>\n r\n .map((cell, c) => (c === r.length - 1 ? cell : padEnd(cell, widths[c] as number)))\n .join(' ')\n .trimEnd(),\n );\n}\n\nexport interface ListRow {\n readonly brief: Brief;\n readonly ready: boolean;\n readonly waitingOn: readonly string[];\n}\n\nexport function prettyList(rows: readonly ListRow[], style: Style): string {\n if (rows.length === 0) return 'no briefs';\n const lines = table(\n ['ID', 'STATUS', 'WAVE', 'TASKS', 'READY', 'TITLE'],\n rows.map(({ brief, ready, waitingOn }) => [\n brief.id ?? '?',\n brief.statusWord ?? brief.status ?? '?',\n brief.wave === null ? '-' : String(brief.wave),\n `${brief.tasks.filter((t) => t.checked).length}/${brief.tasks.length}`,\n brief.phase === 'archived' ? '-' : ready ? 'yes' : waitingOn.length > 0 ? `after ${waitingOn.join(', ')}` : 'no',\n shownTitle(brief),\n ]),\n );\n return [paint(style, 'dim', lines[0] as string), ...lines.slice(1)].join('\\n');\n}\n\nexport function prettyMatrix(report: CollisionReport, style: Style): string {\n const out: string[] = [];\n const label = (b: Brief): string => b.id ?? b.name;\n for (const wave of report.waves) {\n const title = wave.wave === null ? 'all live briefs' : `wave ${wave.wave}`;\n out.push(paint(style, 'bold', `${title} \\u00b7 ${plural(wave.briefs.length, 'brief')}`));\n const names = wave.briefs.map(label);\n const width = Math.max(3, ...names.map(displayWidth));\n const pairs = (list: readonly { readonly a: Brief; readonly b: Brief }[]): Set<string> =>\n new Set(list.flatMap((p) => [`${label(p.a)}\\u0000${label(p.b)}`, `${label(p.b)}\\u0000${label(p.a)}`]));\n const hits = pairs(wave.collisions);\n const unknown = pairs(wave.undecided);\n const near = pairs(wave.shared);\n out.push(` ${' '.repeat(width)} ${names.map((n) => padStart(n, width)).join(' ')}`);\n for (const row of names) {\n const cells = names.map((col) => {\n const key = `${row}\\u0000${col}`;\n const mark =\n row === col\n ? '\\u00b7'\n : hits.has(key)\n ? paint(style, 'red', 'X')\n : unknown.has(key)\n ? paint(style, 'yellow', '?')\n : near.has(key)\n ? paint(style, 'yellow', '~')\n : '\\u00b7';\n return `${' '.repeat(width - 1)}${mark}`;\n });\n out.push(` ${padEnd(row, width)} ${cells.join(' ')}`);\n }\n // One mark per pair of briefs; each further pair of patterns on a line beneath it.\n for (const c of wave.collisions) {\n c.overlaps.forEach((o, i) => {\n out.push(` ${i === 0 ? paint(style, 'red', 'X') : ' '} ${label(c.a)} \"${o.patterns[0]}\" and ${label(c.b)} \"${o.patterns[1]}\" both cover ${witnessText(o)}`);\n });\n }\n for (const u of wave.undecided) {\n u.patterns.forEach(([x, y], i) => {\n out.push(` ${i === 0 ? paint(style, 'yellow', '?') : ' '} ${label(u.a)} \"${x}\" and ${label(u.b)} \"${y}\": undecided within the search's budget`);\n });\n }\n for (const s of wave.shared) {\n out.push(` ${paint(style, 'yellow', '~')} ${label(s.a)} and ${label(s.b)} both write into ${inWords(s.directories.map((d) => `${d}/`))}`);\n }\n for (const b of wave.unscoped) {\n out.push(` ${paint(style, 'cyan', '?')} ${label(b)} declares no affectedFiles and cannot be checked`);\n }\n out.push('');\n }\n if (report.unscheduled.length > 0) {\n out.push(paint(style, 'dim', `no wave: ${report.unscheduled.map(label).join(', ')}`));\n }\n for (const w of report.waiting) {\n const why = w.waitsOn.status === 'deferred' ? 'which is deferred' : 'which waits on deferred work';\n out.push(`${paint(style, 'dim', 'waits:')} ${label(w.brief)} on ${label(w.waitsOn)}, ${why}`);\n }\n if (report.deferred.length > 0) {\n out.push(paint(style, 'dim', `deferred: ${report.deferred.map(label).join(', ')}`));\n }\n if (report.waves.length === 0 && report.unscheduled.length === 0 && report.deferred.length === 0) out.push('no live briefs');\n return out.join('\\n').trimEnd();\n}\n\n/**\n * A pair of patterns that meets, and the file named: `inTree` is `true` for a\n * file the tree holds, `false` for an example the search built, `null` when\n * the tree could not be read. Added to schema 2: a reader of it that does not\n * know the field reads the rest as before.\n */\nfunction overlapJson(o: Overlap): Record<string, unknown> {\n return { patterns: o.patterns, witness: o.witness, inTree: o.inTree };\n}\n\n/** The matrix as JSON: briefs by id, and a collision per pair of briefs. */\nexport function matrixJson(report: CollisionReport): Record<string, unknown> {\n return {\n waves: report.waves.map((w) => ({\n wave: w.wave,\n briefs: w.briefs.map((b) => b.id),\n collisions: w.collisions.map((c) => ({\n a: c.a.id,\n b: c.b.id,\n overlaps: c.overlaps.map(overlapJson),\n })),\n undecided: w.undecided.map((u) => ({ a: u.a.id, b: u.b.id, patterns: u.patterns })),\n sharedDirectories: w.shared.map((s) => ({ a: s.a.id, b: s.b.id, directories: s.directories })),\n unscoped: w.unscoped.map((b) => b.id),\n })),\n unscheduled: report.unscheduled.map((b) => b.id),\n deferred: report.deferred.map((b) => b.id),\n waiting: report.waiting.map((w) => ({ id: w.brief.id, file: w.brief.file, waitsOn: w.waitsOn.id })),\n };\n}\n\n/**\n * The waves a schedule uses, in order. They appear in order too: a brief goes\n * into a wave only when it is the first or the one before it is occupied.\n */\nfunction wavesOf(s: Schedule): number[] {\n return [...new Set(s.placements.map((p) => p.proposed))];\n}\n\n/**\n * The schedule for a person: each wave with its briefs, and under a brief whose\n * wave would change, why it goes where it goes. `written` is `null` when\n * nothing was asked to be written.\n */\nexport function prettySchedule(s: Schedule, written: readonly string[] | null, style: Style): string {\n const label = (b: Brief): string => b.id ?? b.name;\n const out: string[] = [];\n const width = Math.max(3, ...s.placements.map((p) => displayWidth(label(p.brief))));\n const titles = Math.max(0, ...s.placements.map((p) => displayWidth(shownTitle(p.brief))));\n const waves = wavesOf(s);\n for (const wave of waves) {\n const here = s.placements.filter((p) => p.proposed === wave);\n out.push(paint(style, 'bold', `wave ${wave} · ${plural(here.length, 'brief')}`));\n for (const p of here) {\n const title = shownTitle(p.brief);\n if (p.proposed === p.declared) {\n out.push(` ${padEnd(label(p.brief), width)} ${title}`);\n continue;\n }\n const from = p.declared === null ? 'no wave' : `wave ${p.declared}`;\n out.push(` ${padEnd(label(p.brief), width)} ${padEnd(title, titles)} ${paint(style, 'yellow', `moves from ${from}`)}`);\n // Why the declared wave holds or does not comes first: it decides whether the move is asked for.\n const verdict = p.declared === null ? [] : holds(p) ? [`wave ${p.declared} also holds`] : [`wave ${p.declared} does not hold: ${breachReasons(p).join('; ')}`];\n for (const reason of [...verdict, ...reasons(p)]) out.push(` ${' '.repeat(width)} ${paint(style, 'dim', reason)}`);\n }\n }\n if (waves.length > 0) out.push('');\n for (const cycle of s.cycles) out.push(`${paint(style, 'red', 'cycle:')} ${cycle.map(label).join(' -> ')}`);\n for (const u of s.unplaced) {\n const why = u.because === 'deferred' ? 'which is deferred' : u.because === 'cycle' ? 'which is in a cycle' : 'which is not placed';\n out.push(`${paint(style, 'dim', 'waits:')} ${label(u.brief)} on ${label(u.waitsOn)}, ${why}`);\n }\n if (s.deferred.length > 0) out.push(paint(style, 'dim', `deferred: ${s.deferred.map(label).join(', ')}`));\n const moving = moves(s).length;\n if (written !== null && written.length > 0) {\n out.push(`wrote the wave of ${plural(written.length, 'brief')}: ${written.join(', ')}`);\n } else if (written !== null && moving > 0) {\n out.push(paint(style, 'red', s.cycles.length > 0 ? 'nothing was written: the dependencies form a cycle' : 'nothing was written: a front matter cannot be edited'));\n } else if (moving > 0 && moves(s).every(holds)) {\n out.push(`${plural(moving, 'brief')} could move, and the declared waves hold; \"spec-brief schedule --write\" writes the computed ones`);\n } else if (moving > 0) {\n out.push(`${plural(moving, 'brief')} would move; \"spec-brief schedule --write\" writes the waves`);\n } else if (s.placements.length > 0) {\n out.push('the declared waves hold');\n } else if (s.cycles.length === 0 && s.deferred.length === 0) {\n // A brief is unplaced only behind a cycle or a deferral, so this is a corpus with no live brief.\n out.push('no live briefs');\n }\n return out.join('\\n');\n}\n\n/** The schedule as JSON: a row per placed brief with its declared and proposed wave and why. */\nexport function scheduleJson(s: Schedule): Record<string, unknown> {\n const breach = (b: Breach): Record<string, unknown> =>\n b.reason === 'collision'\n ? { reason: b.reason, brief: b.brief.id, overlaps: b.overlaps.map(overlapJson) }\n : { reason: b.reason, brief: b.brief.id, wave: b.wave };\n const passed = (p: Passed): Record<string, unknown> => {\n const base = { wave: p.wave, reason: p.reason, brief: p.brief.id };\n if (p.reason === 'collision') return { ...base, overlaps: p.overlaps.map(overlapJson) };\n if (p.reason === 'undecided') return { ...base, patterns: p.patterns };\n return base;\n };\n const waves = wavesOf(s);\n return {\n first: s.first,\n waves: waves.map((wave) => ({ wave, briefs: s.placements.filter((p) => p.proposed === wave).map((p) => p.brief.id) })),\n briefs: s.placements.map((p) => ({\n id: p.brief.id,\n file: p.brief.file,\n declared: p.declared,\n proposed: p.proposed,\n moves: p.proposed !== p.declared,\n holds: holds(p),\n breaches: p.breaches.map(breach),\n after: p.after === null ? null : { brief: p.after.brief.id, wave: p.after.wave },\n passed: p.passed.map(passed),\n unscoped: p.unscoped,\n reasons: reasons(p),\n })),\n unplaced: s.unplaced.map((u) => ({ id: u.brief.id, file: u.brief.file, waitsOn: u.waitsOn.id, because: u.because })),\n cycles: s.cycles.map((cycle) => cycle.map((b) => b.id)),\n deferred: s.deferred.map((b) => b.id),\n };\n}\n\nexport function prettyPlan(plan: Plan, dryRun: boolean, style: Style): string {\n const out: string[] = [];\n const verb = plan.action === 'archive' ? 'archive' : 'unarchive';\n if (plan.done) return `${plan.brief.file} is already ${plan.action === 'archive' ? 'archived' : 'live'}; nothing to do`;\n if (plan.blocking.length > 0) {\n out.push(paint(style, 'red', `cannot ${verb} ${plan.brief.file}:`), prettyFindings(plan.blocking, style));\n if (plan.warnings.length > 0) out.push('', prettyFindings(plan.warnings, style));\n return out.join('\\n');\n }\n out.push(`${dryRun ? 'would move' : 'moved'} ${plan.from} -> ${plan.to}`);\n if (plan.linksRewritten > 0) out.push(` ${plural(plan.linksRewritten, 'relative link')} rewritten`);\n for (const file of plan.inboundRewritten) out.push(` ${file}: links to it rewritten`);\n for (const f of plan.inboundFrozen) out.push(` ${f.file}:${f.line}: links to the old path, and is frozen, so it was left as it is`);\n if (plan.changes.length > 0) out.push(` the round changed ${plural(plan.changes.length, 'file')}`);\n if (plan.warnings.length > 0) out.push('', prettyFindings(plan.warnings, style));\n if (dryRun && plan.banner.length > 0) out.push('', paint(style, 'dim', 'banner:'), ...plan.banner.map((l) => ` ${l}`));\n if (!dryRun) out.push('', paint(style, 'dim', 'nothing was committed; review the change and commit it with the round'));\n return out.join('\\n');\n}\n\nexport function planJson(plan: Plan): Record<string, unknown> {\n return {\n action: plan.action,\n brief: plan.brief.id,\n from: plan.from,\n to: plan.to,\n done: plan.done,\n refused: plan.blocking.length > 0,\n blocking: plan.blocking.map(findingJson),\n warnings: plan.warnings.map(findingJson),\n linksRewritten: plan.linksRewritten,\n inboundRewritten: plan.inboundRewritten,\n inboundFrozen: plan.inboundFrozen,\n operations: plan.ops.map((op) => ({ kind: op.kind, path: op.path })),\n banner: plan.banner,\n changes: plan.changes,\n };\n}\n"]}
|
package/dist/rules.d.ts
CHANGED
|
@@ -20,6 +20,8 @@ export interface RuleResult {
|
|
|
20
20
|
readonly hint?: string | undefined;
|
|
21
21
|
/** Lower than the rule's severity for this one finding, as a draft's unwritten sections are. */
|
|
22
22
|
readonly severity?: Severity | undefined;
|
|
23
|
+
/** What the finding is about, where the rule can report more than one thing in a brief: a finding's `subject`. */
|
|
24
|
+
readonly subject?: string | undefined;
|
|
23
25
|
}
|
|
24
26
|
export interface RuleContext {
|
|
25
27
|
readonly brief: Brief;
|