pruneguard 0.3.0 → 0.4.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 CHANGED
@@ -60,9 +60,6 @@ Commands:
60
60
  debug entrypoints List detected entrypoints
61
61
  debug runtime Print runtime diagnostics
62
62
  daemon start|stop|status Manage the background daemon
63
- migrate knip Convert knip config to pruneguard
64
- migrate depcruise Convert dependency-cruiser config to pruneguard
65
-
66
63
  Options:
67
64
  -c, --config <FILE> Config file path [default: pruneguard.json]
68
65
  --format <FORMAT> Output format: text, json, sarif, dot
@@ -127,8 +124,6 @@ import {
127
124
  loadConfig,
128
125
  schemaPath,
129
126
  scanDot,
130
- migrateKnip,
131
- migrateDepcruise,
132
127
  } from "pruneguard";
133
128
  ```
134
129
 
@@ -204,8 +199,6 @@ const config = await loadConfig();
204
199
  const schema = schemaPath();
205
200
  const dot = await scanDot();
206
201
  const rules = await suggestRules();
207
- const knip = await migrateKnip();
208
- const dc = await migrateDepcruise();
209
202
  ```
210
203
 
211
204
  ### Error handling
@@ -374,17 +367,6 @@ jobs:
374
367
 
375
368
  ---
376
369
 
377
- ## Migrating from other tools
378
-
379
- ```sh
380
- pruneguard migrate knip # reads knip.json or package.json#knip
381
- pruneguard migrate depcruise # reads .dependency-cruiser.* files
382
- ```
383
-
384
- Both commands emit an equivalent `pruneguard.json` with migration notes.
385
-
386
- ---
387
-
388
370
  ## Framework detection
389
371
 
390
372
  | Framework | Auto-detected via | Entrypoints added |
@@ -21,7 +21,10 @@
21
21
  "cycles": "warn",
22
22
  "boundaries": "warn",
23
23
  "ownership": "warn",
24
- "impact": "warn"
24
+ "impact": "warn",
25
+ "unusedMembers": "warn",
26
+ "duplicateExports": "warn",
27
+ "ignoreExportsUsedInFile": false
25
28
  },
26
29
  "allOf": [
27
30
  {
@@ -34,7 +37,8 @@
34
37
  "default": {
35
38
  "auto": true,
36
39
  "includeTests": false,
37
- "includeStories": false
40
+ "includeStories": false,
41
+ "includeEntryExports": false
38
42
  },
39
43
  "allOf": [
40
44
  {
@@ -63,6 +67,13 @@
63
67
  }
64
68
  ]
65
69
  },
70
+ "ignoreIssues": {
71
+ "description": "Suppress specific finding kinds from the report.",
72
+ "type": "array",
73
+ "items": {
74
+ "$ref": "#/definitions/IgnoreIssueRule"
75
+ }
76
+ },
66
77
  "ignorePatterns": {
67
78
  "description": "Glob patterns for files to ignore entirely.",
68
79
  "type": "array",
@@ -92,7 +103,18 @@
92
103
  "description": "Module resolver configuration.",
93
104
  "default": {
94
105
  "respectExports": true,
95
- "preserveSymlinks": false
106
+ "preserveSymlinks": false,
107
+ "detectRequireResolve": true,
108
+ "detectImportMetaResolve": true,
109
+ "detectImportMetaGlob": true,
110
+ "detectRequireContext": true,
111
+ "detectUrlConstructor": true,
112
+ "detectJsdocImports": true,
113
+ "detectTripleSlash": true,
114
+ "detectImportEquals": true,
115
+ "detectTypeImports": true,
116
+ "detectWebpackAliases": true,
117
+ "detectBabelAliases": true
96
118
  },
97
119
  "allOf": [
98
120
  {
@@ -143,6 +165,20 @@
143
165
  }
144
166
  ]
145
167
  },
168
+ "duplicateExports": {
169
+ "description": "Report duplicate exports (same symbol re-exported from multiple paths).",
170
+ "default": "warn",
171
+ "allOf": [
172
+ {
173
+ "$ref": "#/definitions/AnalysisSeverity"
174
+ }
175
+ ]
176
+ },
177
+ "ignoreExportsUsedInFile": {
178
+ "description": "When true, exports consumed only within the same file are still reported as unused.",
179
+ "default": false,
180
+ "type": "boolean"
181
+ },
146
182
  "impact": {
147
183
  "default": "warn",
148
184
  "allOf": [
@@ -183,6 +219,15 @@
183
219
  }
184
220
  ]
185
221
  },
222
+ "unusedMembers": {
223
+ "description": "Report unused exported class/enum members (methods, properties, variants).",
224
+ "default": "warn",
225
+ "allOf": [
226
+ {
227
+ "$ref": "#/definitions/AnalysisSeverity"
228
+ }
229
+ ]
230
+ },
186
231
  "unusedPackages": {
187
232
  "default": "warn",
188
233
  "allOf": [
@@ -225,6 +270,11 @@
225
270
  "type": "string"
226
271
  }
227
272
  },
273
+ "includeEntryExports": {
274
+ "description": "When true, runtime entrypoint exports are eligible to be reported as unused. By default (`false`), only public-API entrypoint exports are checked.",
275
+ "default": false,
276
+ "type": "boolean"
277
+ },
228
278
  "includeStories": {
229
279
  "description": "Whether to include story files as entrypoints.",
230
280
  "default": false,
@@ -259,6 +309,46 @@
259
309
  "FrameworksConfig": {
260
310
  "type": "object",
261
311
  "properties": {
312
+ "angular": {
313
+ "anyOf": [
314
+ {
315
+ "$ref": "#/definitions/FrameworkToggle"
316
+ },
317
+ {
318
+ "type": "null"
319
+ }
320
+ ]
321
+ },
322
+ "astro": {
323
+ "anyOf": [
324
+ {
325
+ "$ref": "#/definitions/FrameworkToggle"
326
+ },
327
+ {
328
+ "type": "null"
329
+ }
330
+ ]
331
+ },
332
+ "cypress": {
333
+ "anyOf": [
334
+ {
335
+ "$ref": "#/definitions/FrameworkToggle"
336
+ },
337
+ {
338
+ "type": "null"
339
+ }
340
+ ]
341
+ },
342
+ "docusaurus": {
343
+ "anyOf": [
344
+ {
345
+ "$ref": "#/definitions/FrameworkToggle"
346
+ },
347
+ {
348
+ "type": "null"
349
+ }
350
+ ]
351
+ },
262
352
  "jest": {
263
353
  "anyOf": [
264
354
  {
@@ -279,6 +369,46 @@
279
369
  }
280
370
  ]
281
371
  },
372
+ "nuxt": {
373
+ "anyOf": [
374
+ {
375
+ "$ref": "#/definitions/FrameworkToggle"
376
+ },
377
+ {
378
+ "type": "null"
379
+ }
380
+ ]
381
+ },
382
+ "nx": {
383
+ "anyOf": [
384
+ {
385
+ "$ref": "#/definitions/FrameworkToggle"
386
+ },
387
+ {
388
+ "type": "null"
389
+ }
390
+ ]
391
+ },
392
+ "playwright": {
393
+ "anyOf": [
394
+ {
395
+ "$ref": "#/definitions/FrameworkToggle"
396
+ },
397
+ {
398
+ "type": "null"
399
+ }
400
+ ]
401
+ },
402
+ "remix": {
403
+ "anyOf": [
404
+ {
405
+ "$ref": "#/definitions/FrameworkToggle"
406
+ },
407
+ {
408
+ "type": "null"
409
+ }
410
+ ]
411
+ },
282
412
  "storybook": {
283
413
  "anyOf": [
284
414
  {
@@ -289,6 +419,26 @@
289
419
  }
290
420
  ]
291
421
  },
422
+ "sveltekit": {
423
+ "anyOf": [
424
+ {
425
+ "$ref": "#/definitions/FrameworkToggle"
426
+ },
427
+ {
428
+ "type": "null"
429
+ }
430
+ ]
431
+ },
432
+ "turborepo": {
433
+ "anyOf": [
434
+ {
435
+ "$ref": "#/definitions/FrameworkToggle"
436
+ },
437
+ {
438
+ "type": "null"
439
+ }
440
+ ]
441
+ },
292
442
  "vite": {
293
443
  "anyOf": [
294
444
  {
@@ -299,6 +449,16 @@
299
449
  }
300
450
  ]
301
451
  },
452
+ "vitepress": {
453
+ "anyOf": [
454
+ {
455
+ "$ref": "#/definitions/FrameworkToggle"
456
+ },
457
+ {
458
+ "type": "null"
459
+ }
460
+ ]
461
+ },
302
462
  "vitest": {
303
463
  "anyOf": [
304
464
  {
@@ -311,6 +471,68 @@
311
471
  }
312
472
  }
313
473
  },
474
+ "IgnoreIssueRule": {
475
+ "description": "Rule for suppressing specific finding kinds.",
476
+ "type": "object",
477
+ "required": [
478
+ "kind"
479
+ ],
480
+ "properties": {
481
+ "codes": {
482
+ "description": "Additional finding codes to match (beyond the primary `kind`).",
483
+ "type": "array",
484
+ "items": {
485
+ "type": "string"
486
+ }
487
+ },
488
+ "comment": {
489
+ "description": "Optional comment explaining why this is suppressed.",
490
+ "type": [
491
+ "string",
492
+ "null"
493
+ ]
494
+ },
495
+ "files": {
496
+ "description": "Optional glob patterns — only suppress in matching files.",
497
+ "type": "array",
498
+ "items": {
499
+ "type": "string"
500
+ }
501
+ },
502
+ "kind": {
503
+ "description": "The finding kind to suppress (e.g. \"unusedExport\", \"unusedFile\", \"cycle\").",
504
+ "type": "string"
505
+ },
506
+ "packages": {
507
+ "description": "Package names to scope this rule to.",
508
+ "type": "array",
509
+ "items": {
510
+ "type": "string"
511
+ }
512
+ },
513
+ "parentSymbols": {
514
+ "description": "Parent symbol names to scope this rule to.",
515
+ "type": "array",
516
+ "items": {
517
+ "type": "string"
518
+ }
519
+ },
520
+ "symbols": {
521
+ "description": "Symbol names to scope this rule to.",
522
+ "type": "array",
523
+ "items": {
524
+ "type": "string"
525
+ }
526
+ },
527
+ "workspaces": {
528
+ "description": "Workspace names to scope this rule to.",
529
+ "type": "array",
530
+ "items": {
531
+ "type": "string"
532
+ }
533
+ }
534
+ }
535
+ },
314
536
  "OverrideConfig": {
315
537
  "type": "object",
316
538
  "properties": {
@@ -444,6 +666,61 @@
444
666
  "type": "string"
445
667
  }
446
668
  },
669
+ "detectBabelAliases": {
670
+ "description": "Whether to detect Babel alias patterns.",
671
+ "default": true,
672
+ "type": "boolean"
673
+ },
674
+ "detectImportEquals": {
675
+ "description": "Whether to detect TypeScript `import =` statements.",
676
+ "default": true,
677
+ "type": "boolean"
678
+ },
679
+ "detectImportMetaGlob": {
680
+ "description": "Whether to detect `import.meta.glob()` calls.",
681
+ "default": true,
682
+ "type": "boolean"
683
+ },
684
+ "detectImportMetaResolve": {
685
+ "description": "Whether to detect `import.meta.resolve()` calls.",
686
+ "default": true,
687
+ "type": "boolean"
688
+ },
689
+ "detectJsdocImports": {
690
+ "description": "Whether to detect JSDoc `@import` tags.",
691
+ "default": true,
692
+ "type": "boolean"
693
+ },
694
+ "detectRequireContext": {
695
+ "description": "Whether to detect `require.context()` calls.",
696
+ "default": true,
697
+ "type": "boolean"
698
+ },
699
+ "detectRequireResolve": {
700
+ "description": "Whether to detect `require.resolve()` calls.",
701
+ "default": true,
702
+ "type": "boolean"
703
+ },
704
+ "detectTripleSlash": {
705
+ "description": "Whether to detect triple-slash reference directives.",
706
+ "default": true,
707
+ "type": "boolean"
708
+ },
709
+ "detectTypeImports": {
710
+ "description": "Whether to detect type-only imports.",
711
+ "default": true,
712
+ "type": "boolean"
713
+ },
714
+ "detectUrlConstructor": {
715
+ "description": "Whether to detect `new URL()` constructor patterns.",
716
+ "default": true,
717
+ "type": "boolean"
718
+ },
719
+ "detectWebpackAliases": {
720
+ "description": "Whether to detect webpack alias patterns.",
721
+ "default": true,
722
+ "type": "boolean"
723
+ },
447
724
  "extensions": {
448
725
  "description": "File extensions to resolve.",
449
726
  "type": "array",
@@ -0,0 +1,183 @@
1
+ {
2
+ "$schema": "http://json-schema.org/draft-07/schema#",
3
+ "title": "DaemonStatusReport",
4
+ "description": "Daemon status report for querying daemon health from JS or CLI.",
5
+ "type": "object",
6
+ "required": [
7
+ "running"
8
+ ],
9
+ "properties": {
10
+ "binaryPath": {
11
+ "description": "Absolute path to the daemon binary.",
12
+ "type": [
13
+ "string",
14
+ "null"
15
+ ]
16
+ },
17
+ "configChangePending": {
18
+ "description": "Whether a config-level change is pending that requires full rebuild.",
19
+ "type": [
20
+ "boolean",
21
+ "null"
22
+ ]
23
+ },
24
+ "generation": {
25
+ "description": "Current generation (rebuild counter) of the index.",
26
+ "type": [
27
+ "integer",
28
+ "null"
29
+ ],
30
+ "format": "uint64",
31
+ "minimum": 0.0
32
+ },
33
+ "graphEdges": {
34
+ "description": "Number of edges in the module graph.",
35
+ "type": [
36
+ "integer",
37
+ "null"
38
+ ],
39
+ "format": "uint",
40
+ "minimum": 0.0
41
+ },
42
+ "graphNodes": {
43
+ "description": "Number of nodes in the module graph.",
44
+ "type": [
45
+ "integer",
46
+ "null"
47
+ ],
48
+ "format": "uint",
49
+ "minimum": 0.0
50
+ },
51
+ "incrementalRebuilds": {
52
+ "description": "Number of incremental rebuilds since daemon start.",
53
+ "type": [
54
+ "integer",
55
+ "null"
56
+ ],
57
+ "format": "uint64",
58
+ "minimum": 0.0
59
+ },
60
+ "indexWarm": {
61
+ "description": "Whether the hot index has been warmed (initial build complete).",
62
+ "type": [
63
+ "boolean",
64
+ "null"
65
+ ]
66
+ },
67
+ "initialBuildMs": {
68
+ "description": "Milliseconds the initial graph build took.",
69
+ "type": [
70
+ "integer",
71
+ "null"
72
+ ],
73
+ "format": "uint64",
74
+ "minimum": 0.0
75
+ },
76
+ "lastRebuildMs": {
77
+ "description": "Milliseconds the last incremental rebuild took.",
78
+ "type": [
79
+ "integer",
80
+ "null"
81
+ ],
82
+ "format": "uint64",
83
+ "minimum": 0.0
84
+ },
85
+ "lastUpdateMs": {
86
+ "description": "Milliseconds since the last graph update.",
87
+ "type": [
88
+ "integer",
89
+ "null"
90
+ ],
91
+ "format": "uint64",
92
+ "minimum": 0.0
93
+ },
94
+ "pendingInvalidations": {
95
+ "description": "Number of files pending invalidation.",
96
+ "type": [
97
+ "integer",
98
+ "null"
99
+ ],
100
+ "format": "uint",
101
+ "minimum": 0.0
102
+ },
103
+ "pid": {
104
+ "description": "Process ID of the running daemon, if any.",
105
+ "type": [
106
+ "integer",
107
+ "null"
108
+ ],
109
+ "format": "uint32",
110
+ "minimum": 0.0
111
+ },
112
+ "port": {
113
+ "description": "TCP port the daemon is listening on, if any.",
114
+ "type": [
115
+ "integer",
116
+ "null"
117
+ ],
118
+ "format": "uint16",
119
+ "minimum": 0.0
120
+ },
121
+ "projectRoot": {
122
+ "description": "Absolute path to the project root the daemon is serving.",
123
+ "type": [
124
+ "string",
125
+ "null"
126
+ ]
127
+ },
128
+ "running": {
129
+ "description": "Whether a daemon process is currently running.",
130
+ "type": "boolean"
131
+ },
132
+ "startedAt": {
133
+ "description": "ISO-8601 timestamp when the daemon started.",
134
+ "type": [
135
+ "string",
136
+ "null"
137
+ ]
138
+ },
139
+ "totalInvalidations": {
140
+ "description": "Total number of files invalidated since daemon start.",
141
+ "type": [
142
+ "integer",
143
+ "null"
144
+ ],
145
+ "format": "uint64",
146
+ "minimum": 0.0
147
+ },
148
+ "uptimeSecs": {
149
+ "description": "Uptime of the daemon in seconds.",
150
+ "type": [
151
+ "integer",
152
+ "null"
153
+ ],
154
+ "format": "uint64",
155
+ "minimum": 0.0
156
+ },
157
+ "version": {
158
+ "description": "Version of the running daemon binary.",
159
+ "type": [
160
+ "string",
161
+ "null"
162
+ ]
163
+ },
164
+ "watchedFiles": {
165
+ "description": "Number of files being watched for changes.",
166
+ "type": [
167
+ "integer",
168
+ "null"
169
+ ],
170
+ "format": "uint",
171
+ "minimum": 0.0
172
+ },
173
+ "watcherLagMs": {
174
+ "description": "Milliseconds of watcher lag (time since last fs event was processed).",
175
+ "type": [
176
+ "integer",
177
+ "null"
178
+ ],
179
+ "format": "uint64",
180
+ "minimum": 0.0
181
+ }
182
+ }
183
+ }