@bridge-ds/core 0.3.0 → 0.5.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/README.md +16 -5
- package/audit-report.schema.json +135 -1
- package/dist/audit/code.d.ts +50 -0
- package/dist/audit/ignore.d.ts +34 -0
- package/dist/audit/index.d.ts +3 -0
- package/dist/audit/index.js +45 -29
- package/dist/audit/markup.d.ts +21 -0
- package/dist/audit/report.d.ts +5 -7
- package/dist/audit/style.d.ts +25 -0
- package/dist/audit/types.d.ts +39 -1
- package/dist/{component-spec-IRFGJ7XK.js → component-spec-cvrSvIZj.js} +160 -160
- package/dist/{component-spec-IRFGJ7XK.js.map → component-spec-cvrSvIZj.js.map} +1 -1
- package/dist/css-overrides.d.ts +11 -0
- package/dist/explorations-github.d.ts +4 -1
- package/dist/explorations.d.ts +6 -0
- package/dist/github-client.d.ts +19 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.js +685 -398
- package/dist/index.js.map +1 -1
- package/dist/{layered-DGate4nv.js → layered-BnbmToGs.js} +10 -10
- package/dist/{layered-DGate4nv.js.map → layered-BnbmToGs.js.map} +1 -1
- package/dist/node/audit.d.ts +5 -1
- package/dist/node/index.js +8 -4
- package/dist/node/index.js.map +1 -1
- package/dist/{report-tNzTriGF.js → report-4Z008HSf.js} +599 -144
- package/dist/report-4Z008HSf.js.map +1 -0
- package/dist/token-combine.d.ts +78 -0
- package/dist/token-merge.d.ts +72 -0
- package/package.json +1 -1
- package/dist/report-tNzTriGF.js.map +0 -1
package/README.md
CHANGED
|
@@ -297,12 +297,12 @@ conflicts table.
|
|
|
297
297
|
## audit (`@bridge-ds/core/audit`)
|
|
298
298
|
|
|
299
299
|
Design system adoption and drift in a product codebase that consumes the DS. Pure (file texts in, report
|
|
300
|
-
out); it reads TSX/JSX
|
|
301
|
-
Figma plugin never loads it. `@bridge-ds/core/node` adds the disk side.
|
|
300
|
+
out); it reads TSX/JSX, and the frontmatter and scripts of Astro, Vue and Svelte files, with the TypeScript
|
|
301
|
+
compiler API (syntax only), which is why it is its own entry and the Figma plugin never loads it. `@bridge-ds/core/node` adds the disk side.
|
|
302
302
|
|
|
303
303
|
```ts
|
|
304
304
|
import { DesignSystemIndex, buildAuditReport, compareWithBaseline, auditMarkdown, planCssFixes, auditFile } from '@bridge-ds/core/audit';
|
|
305
|
-
import { loadDesignSystem, runAudit, collectAuditFiles, fixCss, findDesignSystemRoot } from '@bridge-ds/core/node';
|
|
305
|
+
import { loadDesignSystem, runAudit, collectAuditFiles, fixCss, findDesignSystemRoot, loadAllowlist } from '@bridge-ds/core/node';
|
|
306
306
|
|
|
307
307
|
const ds = loadDesignSystem('/path/to/ds-repo'); // bridge.config.json: tokens in every mode, components, packages
|
|
308
308
|
const report = runAudit('apps/admin/src', { ds: ds.root, label: 'admin', baseline }); // AuditReport, schemaVersion 1
|
|
@@ -310,7 +310,9 @@ const report = runAudit('apps/admin/src', { ds: ds.root, label: 'admin', baselin
|
|
|
310
310
|
|
|
311
311
|
- **Scanned**: CSS, SCSS, Less, CSS modules; `style`, MUI `sx`, `styled()`, `makeStyles`, `createTheme` and theme
|
|
312
312
|
objects, styled-components / emotion templates; Tailwind class strings (`className`, `cn()`, `clsx()`, `cva()`,
|
|
313
|
-
`@apply`); any color literal in code.
|
|
313
|
+
`@apply`); any color literal in code. Astro, Vue and Svelte files: the frontmatter and `<script>` blocks as
|
|
314
|
+
TS, `<style>` blocks as CSS/SCSS/Less, and the template markup (tags, `style` and `class` attributes, static
|
|
315
|
+
`style="..."`, `style={{ ... }}`, Vue `:style`, Svelte `style:prop`, color attributes such as `fill="#..."`).
|
|
314
316
|
- **Hardcoded values**: colors (hex, rgb, hsl, named, bare HSL channels), spacing, sizes, radii, border widths,
|
|
315
317
|
shadows, durations, easings, z-index, font family, size, weight and line height. Each gets the closest token:
|
|
316
318
|
colors by deltaE in OKLab across every mode (semantic tokens and tokens that fit the property win near-ties),
|
|
@@ -323,7 +325,16 @@ const report = runAudit('apps/admin/src', { ds: ds.root, label: 'admin', baselin
|
|
|
323
325
|
(`button`, `input`, `select`, `textarea`, `dialog`, `table`, `a` with `href`, `img`), router links (react-router,
|
|
324
326
|
ra-core `LinkBase`, next/link) unless passed as a DS component's `render` element, chart libraries (recharts,
|
|
325
327
|
Nivo, Chart.js...: foreign with no DS equivalent) and local components named like a DS component. Providers and
|
|
326
|
-
other non-visual parts never count, DS ones included.
|
|
328
|
+
other non-visual parts never count, DS ones included. In Astro, Vue and Svelte templates a tag is a DS component
|
|
329
|
+
when the frontmatter or `<script>` imports it from a DS package (Vue kebab case `<ds-button>` included); a local
|
|
330
|
+
`Button.astro`, `Button.vue` or `Button.svelte` is a re-created DS component. `<input type="hidden">`, anchors
|
|
331
|
+
without `href` and anything inside `<noscript>` are not UI instances.
|
|
332
|
+
- **Escape hatches**: `bridge-audit-ignore-next-line: reason` in any comment (`<!-- -->`, `{/* */}`, `/* */`,
|
|
333
|
+
`//`) leaves the findings of the next line out of the counts. The reason is required: without one, or when the
|
|
334
|
+
next line has no finding, nothing is ignored and the file lists it under `ignoreErrors`. An allowlist
|
|
335
|
+
(`runAudit(..., { allowlist: loadAllowlist(path) })`, `{ "entries": [{ "file", "line", "what"?, "reason" }] }`) does
|
|
336
|
+
the same for known file:line violations. Ignored items stay in the report (`files[].ignored`, `ignored.items`),
|
|
337
|
+
with their reason; allowlist entries that match nothing are listed in `ignored.staleAllowlist`.
|
|
327
338
|
- **Metrics**: token adoption = token references / (token references + hardcoded values); component adoption =
|
|
328
339
|
DS instances / all UI instances. By category, top files, top fixes, per-file findings with line numbers.
|
|
329
340
|
- **Baseline**: `compareWithBaseline(report, previous)` adds deltas per metric, category and file, and carries the
|
package/audit-report.schema.json
CHANGED
|
@@ -358,6 +358,43 @@
|
|
|
358
358
|
"baseline": {
|
|
359
359
|
"$ref": "#/$defs/baseline"
|
|
360
360
|
},
|
|
361
|
+
"ignored": {
|
|
362
|
+
"type": "object",
|
|
363
|
+
"description": "What was left out of the counts on purpose, and allowlist entries that match nothing any more.",
|
|
364
|
+
"required": [
|
|
365
|
+
"total",
|
|
366
|
+
"comment",
|
|
367
|
+
"allowlist",
|
|
368
|
+
"items",
|
|
369
|
+
"staleAllowlist"
|
|
370
|
+
],
|
|
371
|
+
"properties": {
|
|
372
|
+
"total": {
|
|
373
|
+
"type": "integer",
|
|
374
|
+
"minimum": 0
|
|
375
|
+
},
|
|
376
|
+
"comment": {
|
|
377
|
+
"type": "integer",
|
|
378
|
+
"minimum": 0
|
|
379
|
+
},
|
|
380
|
+
"allowlist": {
|
|
381
|
+
"type": "integer",
|
|
382
|
+
"minimum": 0
|
|
383
|
+
},
|
|
384
|
+
"items": {
|
|
385
|
+
"type": "array",
|
|
386
|
+
"items": {
|
|
387
|
+
"$ref": "#/$defs/ignored"
|
|
388
|
+
}
|
|
389
|
+
},
|
|
390
|
+
"staleAllowlist": {
|
|
391
|
+
"type": "array",
|
|
392
|
+
"items": {
|
|
393
|
+
"$ref": "#/$defs/allowlistEntry"
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
},
|
|
361
398
|
"history": {
|
|
362
399
|
"type": "array",
|
|
363
400
|
"items": {
|
|
@@ -438,7 +475,10 @@
|
|
|
438
475
|
"tsx",
|
|
439
476
|
"jsx",
|
|
440
477
|
"ts",
|
|
441
|
-
"js"
|
|
478
|
+
"js",
|
|
479
|
+
"astro",
|
|
480
|
+
"vue",
|
|
481
|
+
"svelte"
|
|
442
482
|
]
|
|
443
483
|
},
|
|
444
484
|
"tokenUsages": {
|
|
@@ -563,6 +603,32 @@
|
|
|
563
603
|
}
|
|
564
604
|
}
|
|
565
605
|
}
|
|
606
|
+
},
|
|
607
|
+
"ignored": {
|
|
608
|
+
"type": "array",
|
|
609
|
+
"items": {
|
|
610
|
+
"$ref": "#/$defs/ignored"
|
|
611
|
+
}
|
|
612
|
+
},
|
|
613
|
+
"ignoreErrors": {
|
|
614
|
+
"type": "array",
|
|
615
|
+
"description": "bridge-audit-ignore-next-line comments that ignored nothing (no reason, or nothing on the next line).",
|
|
616
|
+
"items": {
|
|
617
|
+
"type": "object",
|
|
618
|
+
"required": [
|
|
619
|
+
"line",
|
|
620
|
+
"message"
|
|
621
|
+
],
|
|
622
|
+
"properties": {
|
|
623
|
+
"line": {
|
|
624
|
+
"type": "integer",
|
|
625
|
+
"minimum": 0
|
|
626
|
+
},
|
|
627
|
+
"message": {
|
|
628
|
+
"type": "string"
|
|
629
|
+
}
|
|
630
|
+
}
|
|
631
|
+
}
|
|
566
632
|
}
|
|
567
633
|
}
|
|
568
634
|
},
|
|
@@ -727,6 +793,74 @@
|
|
|
727
793
|
"minimum": 0
|
|
728
794
|
}
|
|
729
795
|
}
|
|
796
|
+
},
|
|
797
|
+
"ignored": {
|
|
798
|
+
"type": "object",
|
|
799
|
+
"description": "A finding or component left out of the counts on purpose, kept in the report so it stays visible.",
|
|
800
|
+
"required": [
|
|
801
|
+
"line",
|
|
802
|
+
"column",
|
|
803
|
+
"kind",
|
|
804
|
+
"what",
|
|
805
|
+
"reason",
|
|
806
|
+
"via"
|
|
807
|
+
],
|
|
808
|
+
"properties": {
|
|
809
|
+
"line": {
|
|
810
|
+
"type": "integer",
|
|
811
|
+
"minimum": 0
|
|
812
|
+
},
|
|
813
|
+
"column": {
|
|
814
|
+
"type": "integer",
|
|
815
|
+
"minimum": 0
|
|
816
|
+
},
|
|
817
|
+
"kind": {
|
|
818
|
+
"enum": [
|
|
819
|
+
"value",
|
|
820
|
+
"component"
|
|
821
|
+
]
|
|
822
|
+
},
|
|
823
|
+
"what": {
|
|
824
|
+
"type": "string",
|
|
825
|
+
"description": "The value as written or the element or component name."
|
|
826
|
+
},
|
|
827
|
+
"reason": {
|
|
828
|
+
"type": "string"
|
|
829
|
+
},
|
|
830
|
+
"via": {
|
|
831
|
+
"enum": [
|
|
832
|
+
"comment",
|
|
833
|
+
"allowlist"
|
|
834
|
+
],
|
|
835
|
+
"description": "A bridge-audit-ignore-next-line comment, or an allowlist entry."
|
|
836
|
+
},
|
|
837
|
+
"file": {
|
|
838
|
+
"type": "string"
|
|
839
|
+
}
|
|
840
|
+
}
|
|
841
|
+
},
|
|
842
|
+
"allowlistEntry": {
|
|
843
|
+
"type": "object",
|
|
844
|
+
"required": [
|
|
845
|
+
"file",
|
|
846
|
+
"line",
|
|
847
|
+
"reason"
|
|
848
|
+
],
|
|
849
|
+
"properties": {
|
|
850
|
+
"file": {
|
|
851
|
+
"type": "string"
|
|
852
|
+
},
|
|
853
|
+
"line": {
|
|
854
|
+
"type": "integer",
|
|
855
|
+
"minimum": 1
|
|
856
|
+
},
|
|
857
|
+
"what": {
|
|
858
|
+
"type": "string"
|
|
859
|
+
},
|
|
860
|
+
"reason": {
|
|
861
|
+
"type": "string"
|
|
862
|
+
}
|
|
863
|
+
}
|
|
730
864
|
}
|
|
731
865
|
}
|
|
732
866
|
}
|
package/dist/audit/code.d.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { type TailwindHit } from './tailwind';
|
|
1
2
|
import type { DesignSystemIndex } from './ds-index';
|
|
2
3
|
import type { ComponentFinding, StyleFinding } from './types';
|
|
3
4
|
export interface CodeScan {
|
|
@@ -13,4 +14,53 @@ export interface CodeScan {
|
|
|
13
14
|
line: number;
|
|
14
15
|
}[];
|
|
15
16
|
}
|
|
17
|
+
/** The DS component a DOM renderer stands for: `checklistRowHtml` -> ChecklistRow, else the longest DS name it starts with. */
|
|
18
|
+
export declare function domRendererComponent(fn: string, components: Set<string>): string | undefined;
|
|
19
|
+
/**
|
|
20
|
+
* Homemade look-alikes in markup a script builds (`class="pill"`, `data-tip="..."`): the DS component they imitate.
|
|
21
|
+
* Exact class tokens only, so app classes that merely contain the word (`cm-pill-row`) are not counted.
|
|
22
|
+
*/
|
|
23
|
+
export declare const LOOKALIKE_CLASSES: Record<string, string>;
|
|
24
|
+
export declare const LOOKALIKE_ATTRS: Record<string, string>;
|
|
25
|
+
/** Look-alikes in a class list (`pill is-pass`): one finding per imitated component. */
|
|
26
|
+
export declare function lookalikesInClassList(list: string, components: Set<string>): {
|
|
27
|
+
token: string;
|
|
28
|
+
component: string;
|
|
29
|
+
}[];
|
|
30
|
+
/** Imported name -> module and exported name ('default', '*' for a namespace). */
|
|
31
|
+
export type ImportMap = Map<string, {
|
|
32
|
+
module: string;
|
|
33
|
+
imported: string;
|
|
34
|
+
}>;
|
|
35
|
+
/** Import declarations of a script (TS or JS), for markup files whose tags use what the script imports. */
|
|
36
|
+
export declare function importsOf(path: string, text: string): ImportMap;
|
|
37
|
+
/** One element as written in JSX or in a template (Astro, Vue, Svelte). */
|
|
38
|
+
export interface TagUse {
|
|
39
|
+
name: string;
|
|
40
|
+
line: number;
|
|
41
|
+
column: number;
|
|
42
|
+
/** Static `type` attribute. */
|
|
43
|
+
type?: string;
|
|
44
|
+
hasHref: boolean;
|
|
45
|
+
/** The element only gives a component its tag or router (`render={<a href="/x" />}`). */
|
|
46
|
+
inRenderProp?: boolean;
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* What an element is: a DS component instance, a foreign, native or re-created component, or nothing (providers,
|
|
50
|
+
* hidden inputs, anchors without href). `localCandidate`: an unimported DS-named tag, re-created only when the file
|
|
51
|
+
* defines it.
|
|
52
|
+
*/
|
|
53
|
+
export declare function classifyTag(t: TagUse, imports: ImportMap, ds: DesignSystemIndex): {
|
|
54
|
+
ds?: string;
|
|
55
|
+
component?: ComponentFinding;
|
|
56
|
+
localCandidate?: ComponentFinding;
|
|
57
|
+
};
|
|
58
|
+
/** Findings for Tailwind classes (arbitrary values and palette classes); scale classes count as theme references. */
|
|
59
|
+
export declare function tailwindFindings(hits: TailwindHit[], offset: number, pos: (offset: number) => {
|
|
60
|
+
line: number;
|
|
61
|
+
column: number;
|
|
62
|
+
}, ds: DesignSystemIndex): {
|
|
63
|
+
findings: StyleFinding[];
|
|
64
|
+
themeRefs: number;
|
|
65
|
+
};
|
|
16
66
|
export declare function scanCode(path: string, text: string, ds: DesignSystemIndex): CodeScan;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import type { AllowlistEntry, ComponentFinding, IgnoredItem, StyleFinding } from './types';
|
|
2
|
+
export declare const IGNORE_DIRECTIVE = "bridge-audit-ignore-next-line";
|
|
3
|
+
export interface IgnoreDirective {
|
|
4
|
+
/** Line of the comment (1-based). */
|
|
5
|
+
line: number;
|
|
6
|
+
/** Line it applies to: the one after the comment ends. */
|
|
7
|
+
target: number;
|
|
8
|
+
/** Empty when the comment gives none: such a comment ignores nothing. */
|
|
9
|
+
reason: string;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Every `bridge-audit-ignore-next-line` comment in a file: `<!-- ...: reason -->` (HTML, Astro, Vue, Svelte),
|
|
13
|
+
* `{/* ...: reason *\/}` (JSX, Astro expressions), `/* ...: reason *\/` (CSS) and `// ...: reason` (scripts).
|
|
14
|
+
* The text after the colon is the reason. A mention outside a comment is not a directive.
|
|
15
|
+
*/
|
|
16
|
+
export declare function ignoreDirectives(text: string): IgnoreDirective[];
|
|
17
|
+
export interface IgnoreResult {
|
|
18
|
+
findings: StyleFinding[];
|
|
19
|
+
components: ComponentFinding[];
|
|
20
|
+
ignored: IgnoredItem[];
|
|
21
|
+
}
|
|
22
|
+
/** Apply the file's ignore comments. Comments without a reason, or that match nothing, are reported as errors. */
|
|
23
|
+
export declare function applyIgnoreComments(text: string, findings: StyleFinding[], components: ComponentFinding[]): IgnoreResult & {
|
|
24
|
+
errors: {
|
|
25
|
+
line: number;
|
|
26
|
+
message: string;
|
|
27
|
+
}[];
|
|
28
|
+
};
|
|
29
|
+
/** Apply allowlist entries for one file; returns what each entry matched (index in `entries`). */
|
|
30
|
+
export declare function applyAllowlist(entries: AllowlistEntry[], findings: StyleFinding[], components: ComponentFinding[]): IgnoreResult & {
|
|
31
|
+
used: Set<number>;
|
|
32
|
+
};
|
|
33
|
+
/** Validate an allowlist file's JSON: `{ "entries": [{ "file", "line", "what"?, "reason" }] }`, a reason on each entry. */
|
|
34
|
+
export declare function parseAllowlist(json: unknown): AllowlistEntry[];
|
package/dist/audit/index.d.ts
CHANGED
package/dist/audit/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { A, a, b, C, D, c, F,
|
|
1
|
+
import { A, a, b, C, D, c, F, I, L, d, M, N, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, y, z, B, E, G, H, J, K, O, P, Q, R, S, T, U, V, W, X, Y, Z } from "../report-4Z008HSf.js";
|
|
2
2
|
export {
|
|
3
3
|
A as AUDIT_EXTENSIONS,
|
|
4
4
|
a as AUDIT_IGNORE_DIRS,
|
|
@@ -7,34 +7,50 @@ export {
|
|
|
7
7
|
D as DEFAULT_NATIVE_ELEMENTS,
|
|
8
8
|
c as DesignSystemIndex,
|
|
9
9
|
F as FINDING_CATEGORIES,
|
|
10
|
+
I as IGNORE_DIRECTIVE,
|
|
11
|
+
L as LOOKALIKE_ATTRS,
|
|
12
|
+
d as LOOKALIKE_CLASSES,
|
|
13
|
+
M as MARKUP_EXTENSIONS,
|
|
10
14
|
N as NAMED_COLORS,
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
15
|
+
e as applyAllowlist,
|
|
16
|
+
f as applyIgnoreComments,
|
|
17
|
+
g as auditCssText,
|
|
18
|
+
h as auditFile,
|
|
19
|
+
i as auditMarkdown,
|
|
20
|
+
j as blankComments,
|
|
21
|
+
k as buildAuditReport,
|
|
22
|
+
l as classifyModule,
|
|
23
|
+
m as classifyTag,
|
|
24
|
+
n as compareWithBaseline,
|
|
25
|
+
o as cssPropertyOf,
|
|
26
|
+
p as deltaE,
|
|
27
|
+
q as domRendererComponent,
|
|
28
|
+
r as dsEquivalent,
|
|
29
|
+
s as historyPoint,
|
|
30
|
+
t as ignoreDirectives,
|
|
31
|
+
u as importsOf,
|
|
32
|
+
v as isAuditable,
|
|
33
|
+
w as isColorLiteral,
|
|
34
|
+
x as isNonVisual,
|
|
35
|
+
y as isRouterLink,
|
|
36
|
+
z as isSafeFix,
|
|
37
|
+
B as libraryLabel,
|
|
38
|
+
E as lineCol,
|
|
39
|
+
G as lookalikesInClassList,
|
|
40
|
+
H as markupBlocks,
|
|
41
|
+
J as nativeEquivalent,
|
|
42
|
+
K as packageName,
|
|
43
|
+
O as parseAllowlist,
|
|
44
|
+
P as parseCssColor,
|
|
45
|
+
Q as planCssFixes,
|
|
46
|
+
R as scanClassString,
|
|
47
|
+
S as scanCode,
|
|
48
|
+
T as scanCssText,
|
|
49
|
+
U as scanCssValue,
|
|
50
|
+
V as scanJsStyle,
|
|
51
|
+
W as scanMarkup,
|
|
52
|
+
X as tailwindColor,
|
|
53
|
+
Y as tailwindFindings,
|
|
54
|
+
Z as toOklab
|
|
39
55
|
};
|
|
40
56
|
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { type CodeScan } from './code';
|
|
2
|
+
import type { DesignSystemIndex } from './ds-index';
|
|
3
|
+
export type MarkupLang = 'astro' | 'vue' | 'svelte';
|
|
4
|
+
export declare const MARKUP_EXTENSIONS: string[];
|
|
5
|
+
interface Range {
|
|
6
|
+
start: number;
|
|
7
|
+
end: number;
|
|
8
|
+
}
|
|
9
|
+
interface Block extends Range {
|
|
10
|
+
attrs: string;
|
|
11
|
+
}
|
|
12
|
+
/** Frontmatter (Astro), script and style blocks, and the template ranges between them. */
|
|
13
|
+
export declare function markupBlocks(text: string, lang: MarkupLang): {
|
|
14
|
+
frontmatter?: Range;
|
|
15
|
+
scripts: Block[];
|
|
16
|
+
styles: Block[];
|
|
17
|
+
nonTemplate: Range[];
|
|
18
|
+
};
|
|
19
|
+
/** Audit an Astro, Vue or Svelte file. Line and column numbers are the file's own. */
|
|
20
|
+
export declare function scanMarkup(path: string, text: string, lang: MarkupLang, ds: DesignSystemIndex): CodeScan;
|
|
21
|
+
export {};
|
package/dist/audit/report.d.ts
CHANGED
|
@@ -1,14 +1,9 @@
|
|
|
1
1
|
import type { DesignSystemIndex } from './ds-index';
|
|
2
|
-
import { type AuditReport, type FileReport, type
|
|
2
|
+
import { type AuditReport, type FileReport, type AllowlistEntry, type HistoryPoint } from './types';
|
|
3
3
|
export declare const AUDIT_EXTENSIONS: string[];
|
|
4
4
|
export declare const AUDIT_IGNORE_DIRS: string[];
|
|
5
5
|
/** Should the audit read this repo-relative path? */
|
|
6
6
|
export declare function isAuditable(path: string): boolean;
|
|
7
|
-
/** A literal the CSS autofix may replace: exact token value, same spelling for lengths and durations. */
|
|
8
|
-
export declare function isSafeFix(h: {
|
|
9
|
-
category: FindingCategory;
|
|
10
|
-
text: string;
|
|
11
|
-
}, s: TokenSuggestion | undefined): boolean;
|
|
12
7
|
export type AuditedFile = FileReport & {
|
|
13
8
|
definitions: {
|
|
14
9
|
name: string;
|
|
@@ -16,7 +11,7 @@ export type AuditedFile = FileReport & {
|
|
|
16
11
|
}[];
|
|
17
12
|
dsByName: Record<string, number>;
|
|
18
13
|
};
|
|
19
|
-
/** Audit one file. */
|
|
14
|
+
/** Audit one file. `bridge-audit-ignore-next-line: reason` comments leave the next line's findings out of the counts. */
|
|
20
15
|
export declare function auditFile(path: string, text: string, ds: DesignSystemIndex): AuditedFile;
|
|
21
16
|
export interface AuditInput {
|
|
22
17
|
files: {
|
|
@@ -28,6 +23,8 @@ export interface AuditInput {
|
|
|
28
23
|
label?: string;
|
|
29
24
|
version?: string;
|
|
30
25
|
generatedAt?: string;
|
|
26
|
+
/** Known violations left out of the counts, each with a reason (an allowlist file, see parseAllowlist). */
|
|
27
|
+
allowlist?: AllowlistEntry[];
|
|
31
28
|
}
|
|
32
29
|
/** Build the report for a set of files. */
|
|
33
30
|
export declare function buildAuditReport(input: AuditInput, ds: DesignSystemIndex): AuditReport;
|
|
@@ -38,6 +35,7 @@ export declare function compareWithBaseline(report: AuditReport, baseline: Audit
|
|
|
38
35
|
export declare function auditMarkdown(r: AuditReport, opts?: {
|
|
39
36
|
topFiles?: number;
|
|
40
37
|
topFixes?: number;
|
|
38
|
+
ignored?: number;
|
|
41
39
|
}): string;
|
|
42
40
|
export interface CssFixEdit {
|
|
43
41
|
line: number;
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { DesignSystemIndex } from './ds-index';
|
|
2
|
+
import type { FindingCategory, FindingSource, StyleFinding, TokenSuggestion } from './types';
|
|
3
|
+
/** A literal the CSS autofix may replace: exact token value, same spelling for lengths and durations. */
|
|
4
|
+
export declare function isSafeFix(h: {
|
|
5
|
+
category: FindingCategory;
|
|
6
|
+
text: string;
|
|
7
|
+
}, s: TokenSuggestion | undefined): boolean;
|
|
8
|
+
export interface CssAudit {
|
|
9
|
+
findings: StyleFinding[];
|
|
10
|
+
tokenUsages: number;
|
|
11
|
+
themeRefs: number;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Audit style sheet text. `offset` places the text inside a larger file (a <style> block, a style attribute) and
|
|
15
|
+
* `pos` maps a file offset to its line and column. `source` labels the findings (`css` for sheets, `style` for
|
|
16
|
+
* style attributes); only `css` findings are marked for the autofix, which rewrites CSS files.
|
|
17
|
+
*/
|
|
18
|
+
export declare function auditCssText(text: string, lang: 'css' | 'scss' | 'less', ds: DesignSystemIndex, opts: {
|
|
19
|
+
pos: (offset: number) => {
|
|
20
|
+
line: number;
|
|
21
|
+
column: number;
|
|
22
|
+
};
|
|
23
|
+
offset?: number;
|
|
24
|
+
source?: FindingSource;
|
|
25
|
+
}): CssAudit;
|
package/dist/audit/types.d.ts
CHANGED
|
@@ -48,7 +48,7 @@ export interface ComponentFinding {
|
|
|
48
48
|
export interface FileReport {
|
|
49
49
|
/** Path relative to the audited root, with forward slashes. */
|
|
50
50
|
path: string;
|
|
51
|
-
lang: 'css' | 'scss' | 'less' | 'tsx' | 'jsx' | 'ts' | 'js';
|
|
51
|
+
lang: 'css' | 'scss' | 'less' | 'tsx' | 'jsx' | 'ts' | 'js' | 'astro' | 'vue' | 'svelte';
|
|
52
52
|
tokenUsages: number;
|
|
53
53
|
/** References to another theme (MUI theme, Tailwind scale classes): not hardcoded, not the DS either. */
|
|
54
54
|
themeRefs: number;
|
|
@@ -58,6 +58,34 @@ export interface FileReport {
|
|
|
58
58
|
otherComponents: number;
|
|
59
59
|
findings: StyleFinding[];
|
|
60
60
|
components: ComponentFinding[];
|
|
61
|
+
/** Findings and components left out of the counts on purpose, each with its reason. */
|
|
62
|
+
ignored?: IgnoredItem[];
|
|
63
|
+
/** `bridge-audit-ignore-next-line` comments that ignored nothing because they give no reason. */
|
|
64
|
+
ignoreErrors?: {
|
|
65
|
+
line: number;
|
|
66
|
+
message: string;
|
|
67
|
+
}[];
|
|
68
|
+
}
|
|
69
|
+
/** Where an ignore comes from: an escape-hatch comment in the file, or an entry of the allowlist file. */
|
|
70
|
+
export type IgnoreVia = 'comment' | 'allowlist';
|
|
71
|
+
/** A finding or component the audit saw but does not count, kept in the report so it stays visible. */
|
|
72
|
+
export interface IgnoredItem {
|
|
73
|
+
line: number;
|
|
74
|
+
column: number;
|
|
75
|
+
kind: 'value' | 'component';
|
|
76
|
+
/** The value as written ("13px") or the element or component name ("select"). */
|
|
77
|
+
what: string;
|
|
78
|
+
reason: string;
|
|
79
|
+
via: IgnoreVia;
|
|
80
|
+
}
|
|
81
|
+
/** One entry of an allowlist file: a known violation, left out of the counts for a stated reason. */
|
|
82
|
+
export interface AllowlistEntry {
|
|
83
|
+
/** Path relative to the audited folder, as in the report. */
|
|
84
|
+
file: string;
|
|
85
|
+
line: number;
|
|
86
|
+
/** Element, component or value on that line ("select", "13px"). Absent: everything on the line. */
|
|
87
|
+
what?: string;
|
|
88
|
+
reason: string;
|
|
61
89
|
}
|
|
62
90
|
export interface CategoryCount {
|
|
63
91
|
hardcoded: number;
|
|
@@ -176,6 +204,16 @@ export interface AuditReport {
|
|
|
176
204
|
topFixes: TopFix[];
|
|
177
205
|
files: FileReport[];
|
|
178
206
|
baseline?: BaselineDiff;
|
|
207
|
+
/** What was left out of the counts on purpose (escape-hatch comments, allowlist), and allowlist entries that match nothing. */
|
|
208
|
+
ignored?: {
|
|
209
|
+
total: number;
|
|
210
|
+
comment: number;
|
|
211
|
+
allowlist: number;
|
|
212
|
+
items: (IgnoredItem & {
|
|
213
|
+
file: string;
|
|
214
|
+
})[];
|
|
215
|
+
staleAllowlist: AllowlistEntry[];
|
|
216
|
+
};
|
|
179
217
|
/** Earlier runs, oldest first (carried over from the baseline). */
|
|
180
218
|
history: HistoryPoint[];
|
|
181
219
|
}
|