fallow 3.10.0 → 3.12.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/capabilities.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "fallow",
3
- "version": "3.10.0",
3
+ "version": "3.12.0",
4
4
  "manifest_version": "1",
5
5
  "description": "Codebase analyzer for TypeScript/JavaScript: unused code, circular dependencies, code duplication, complexity hotspots, and architecture boundary violations",
6
6
  "global_flags": [
@@ -128,6 +128,16 @@
128
128
  "required": false,
129
129
  "description": "Compare against a previously saved baseline file"
130
130
  },
131
+ {
132
+ "name": "--baseline-mode",
133
+ "type": "string",
134
+ "required": false,
135
+ "description": "How `--baseline` matches health findings: per file and category (`count`, the default) or per function identity (`identity`, strict, and only against a baseline that was saved with `--baseline-mode identity`; such a baseline still reads in count mode)",
136
+ "possible_values": [
137
+ "count",
138
+ "identity"
139
+ ]
140
+ },
131
141
  {
132
142
  "name": "--parent-run",
133
143
  "type": "string",
@@ -479,6 +489,16 @@
479
489
  "false"
480
490
  ]
481
491
  },
492
+ {
493
+ "name": "--no-type-aware",
494
+ "type": "bool",
495
+ "required": false,
496
+ "description": "Disable TypeScript semantic analysis even when `typeAware.enabled` or `FALLOW_TYPE_AWARE` opts in, keeping this run fully syntactic",
497
+ "possible_values": [
498
+ "true",
499
+ "false"
500
+ ]
501
+ },
482
502
  {
483
503
  "name": "--type-aware-project",
484
504
  "type": "string",
@@ -5904,6 +5924,7 @@
5904
5924
  "FALLOW_PRODUCTION_HEALTH": "Set to true/false to override production mode for health analysis.",
5905
5925
  "FALLOW_PRODUCTION_DUPES": "Set to true/false to override production mode for duplication analysis.",
5906
5926
  "FALLOW_REVIEW_GUIDANCE": "Set to true to append collapsed guidance blocks to review-github/review-gitlab inline comment bodies.",
5927
+ "FALLOW_REVIEW_ID": "Stable 1-64 character identifier that isolates inline comments when multiple review jobs target the same PR/MR.",
5907
5928
  "FALLOW_SUMMARY_SCOPE": "Summary scope for pr-comment-github/pr-comment-gitlab: all (default) keeps project-level dependency/catalog/override findings outside the diff filter; diff applies the diff filter to them too. Inline review comments are unaffected.",
5908
5929
  "FALLOW_PR_COMMENT_LAYOUT": "Sticky PR comment layout: default, compact, gate-only, or details.",
5909
5930
  "FALLOW_CONSOLIDATED_STATUS": "When split PR gate check runs are enabled, truthy values add one aggregate Fallow check alongside the per-gate checks.",
@@ -5916,6 +5937,7 @@
5916
5937
  "FALLOW_EXTENDS_TIMEOUT_SECS": "Timeout in seconds for fetching https:// configs referenced via the extends field (default 5).",
5917
5938
  "FALLOW_COVERAGE": "Path to Istanbul coverage data (coverage-final.json) for accurate per-function CRAP scores. CLI --coverage flag overrides this.",
5918
5939
  "FALLOW_MAX_FILE_SIZE": "Per-file size ceiling in megabytes for source discovery (default 5; 0 = no limit). CLI --max-file-size flag overrides this.",
5940
+ "FALLOW_TYPE_AWARE": "Enable or disable TypeScript semantic (type-aware) analysis for the run (true/false/1/0/yes/no/on/off). Precedence: --type-aware/--no-type-aware CLI flags, then FALLOW_TYPE_AWARE, then the audit.typeAware config field, then typeAware.enabled.",
5919
5941
  "FALLOW_AUDIT_BASE": "Pins the fallow audit comparison base ref when no --base/--changed-since is passed (e.g. upstream/main).",
5920
5942
  "FALLOW_AUDIT_CACHE_MAX_AGE_DAYS": "GC threshold in days for reusable audit base-snapshot caches (default 30; 0 disables the sweep).",
5921
5943
  "FALLOW_IMPACT_STORE_MAX_AGE_DAYS": "GC threshold in days for per-project fallow impact stores; a recorded run reclaims stores older than this (unset/0 keeps every store forever).",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "fallow",
3
- "version": "3.10.0",
3
+ "version": "3.12.0",
4
4
  "description": "Codebase intelligence for TypeScript and JavaScript. Free static analysis of code and styles, optional paid runtime intelligence (Fallow Runtime). Quality, risk, architecture, dependencies, duplication, and design-system drift for humans, CI, and the agents writing your code. Zero-config framework support.",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -87,14 +87,14 @@
87
87
  "@tanstack/intent": "0.3.6"
88
88
  },
89
89
  "optionalDependencies": {
90
- "@fallow-cli/darwin-arm64": "3.10.0",
91
- "@fallow-cli/darwin-x64": "3.10.0",
92
- "@fallow-cli/linux-x64-gnu": "3.10.0",
93
- "@fallow-cli/linux-arm64-gnu": "3.10.0",
94
- "@fallow-cli/linux-x64-musl": "3.10.0",
95
- "@fallow-cli/linux-arm64-musl": "3.10.0",
96
- "@fallow-cli/win32-arm64-msvc": "3.10.0",
97
- "@fallow-cli/win32-x64-msvc": "3.10.0",
98
- "fallow-type-aware": "3.10.0"
90
+ "@fallow-cli/darwin-arm64": "3.12.0",
91
+ "@fallow-cli/darwin-x64": "3.12.0",
92
+ "@fallow-cli/linux-x64-gnu": "3.12.0",
93
+ "@fallow-cli/linux-arm64-gnu": "3.12.0",
94
+ "@fallow-cli/linux-x64-musl": "3.12.0",
95
+ "@fallow-cli/linux-arm64-musl": "3.12.0",
96
+ "@fallow-cli/win32-arm64-msvc": "3.12.0",
97
+ "@fallow-cli/win32-x64-msvc": "3.12.0",
98
+ "fallow-type-aware": "3.12.0"
99
99
  }
100
100
  }
package/schema.json CHANGED
@@ -2705,6 +2705,13 @@
2705
2705
  ],
2706
2706
  "format": "uint32",
2707
2707
  "minimum": 0
2708
+ },
2709
+ "typeAware": {
2710
+ "description": "Overrides the top-level `typeAware.enabled` opt-in for `fallow audit` only: set `false` to keep persistent type-aware analysis on for cleanup commands (`dead-code`, `fix`, `health`) while the audit gate stays syntactic, or `true` to enable it for audit alone. Unset inherits `typeAware.enabled`. The `--type-aware`/`--no-type-aware` CLI flags and the `FALLOW_TYPE_AWARE` environment variable both take precedence over this field.",
2711
+ "type": [
2712
+ "boolean",
2713
+ "null"
2714
+ ]
2708
2715
  }
2709
2716
  }
2710
2717
  },
@@ -420,7 +420,7 @@ Angular templates contribute synthetic `<template>` complexity findings whenever
420
420
  | `--min-observation-volume` | `string` | - | Minimum total trace volume before the sidecar may emit high-confidence `safe_to_delete` / `review_required` verdicts. Below this, confidence is capped at `medium`. |
421
421
  | `--low-traffic-threshold` | `string` | - | Fraction of total trace count below which an invoked function is classified `low_traffic` rather than `active`. Expressed as a decimal (0.001 = 0.1%). |
422
422
 
423
- Common global flags for this command: [`--format`](#global-flags), [`--quiet`](#global-flags), [`--changed-since`](#global-flags), [`--churn-file`](#global-flags), [`--workspace`](#global-flags), [`--group-by`](#global-flags), [`--baseline`](#global-flags), [`--save-baseline`](#global-flags), [`--production`](#global-flags), [`--no-production`](#global-flags), [`--explain`](#global-flags).
423
+ Common global flags for this command: [`--format`](#global-flags), [`--quiet`](#global-flags), [`--changed-since`](#global-flags), [`--churn-file`](#global-flags), [`--workspace`](#global-flags), [`--group-by`](#global-flags), [`--baseline`](#global-flags), [`--baseline-mode`](#global-flags), [`--save-baseline`](#global-flags), [`--production`](#global-flags), [`--no-production`](#global-flags), [`--explain`](#global-flags).
424
424
  <!-- generated:flags:health:end -->
425
425
  ### Exit Codes
426
426
 
@@ -473,6 +473,10 @@ fallow health --format json --quiet --workspace my-package
473
473
  fallow health --format json --quiet --save-baseline fallow-baselines/health.json
474
474
  fallow health --format json --quiet --baseline fallow-baselines/health.json
475
475
 
476
+ # Strict adoption: a hotspot that replaces a baselined hotspot is reported
477
+ fallow health --format json --quiet --save-baseline fallow-baselines/health.json --baseline-mode identity
478
+ fallow health --format json --quiet --baseline fallow-baselines/health.json --baseline-mode identity
479
+
476
480
  # CI: fail if any function is too complex
477
481
  fallow health --max-cyclomatic 25 --max-cognitive 20 --quiet
478
482
 
@@ -513,7 +517,7 @@ fallow health --format json --quiet --trend
513
517
  {
514
518
  "kind": "health",
515
519
  "schema_version": 7,
516
- "version": "3.9.1",
520
+ "version": "3.12.0",
517
521
  "elapsed_ms": 32,
518
522
  "summary": {
519
523
  "files_analyzed": 482,
@@ -911,7 +915,7 @@ fallow audit \
911
915
  {
912
916
  "kind": "audit",
913
917
  "schema_version": 7,
914
- "version": "3.9.1",
918
+ "version": "3.12.0",
915
919
  "command": "audit",
916
920
  "verdict": "fail",
917
921
  "changed_files_count": 12,
@@ -988,7 +992,7 @@ fallow flags --format json --quiet --workspace my-package
988
992
  ```json
989
993
  {
990
994
  "schema_version": 7,
991
- "version": "3.9.1",
995
+ "version": "3.12.0",
992
996
  "elapsed_ms": 116,
993
997
  "feature_flags": [],
994
998
  "total_flags": 0
@@ -1089,7 +1093,7 @@ fallow security --gate newly-reachable --changed-since origin/main
1089
1093
  {
1090
1094
  "kind": "security",
1091
1095
  "schema_version": "4",
1092
- "version": "3.9.1",
1096
+ "version": "3.12.0",
1093
1097
  "elapsed_ms": 42,
1094
1098
  "config": {
1095
1099
  "rules": {
@@ -1118,7 +1122,7 @@ fallow security --gate newly-reachable --changed-since origin/main
1118
1122
  {
1119
1123
  "kind": "security",
1120
1124
  "schema_version": "4",
1121
- "version": "3.9.1",
1125
+ "version": "3.12.0",
1122
1126
  "elapsed_ms": 42,
1123
1127
  "config": {
1124
1128
  "rules": {
@@ -1677,6 +1681,7 @@ Available on all commands:
1677
1681
  | `--churn-file` | `string` | - | Import change history from a `fallow-churn/v1` JSON file instead of `git log`, powering hotspots, ownership, and bus-factor on projects with no git repository (Yandex Arc, Mercurial, Perforce). A small wrapper translates your VCS log into the contract. Resolved relative to `--root`. Affects `health --hotspots` / `--ownership` / `--targets` only; `audit`, `impact`, and `--changed-since` still require git |
1678
1682
  | `--max-file-size` | `string` | - | Skip source files larger than this many megabytes (default 5) instead of parsing them, guarding against the out-of-memory blowup a single multi-MB generated/vendored/bundled file causes on large repos. Use `0` for no limit. Declaration files (`.d.ts`) are always analyzed. Skipped files are reported and excluded from every analysis. Also settable via `FALLOW_MAX_FILE_SIZE` |
1679
1683
  | `--baseline` | `string` | - | Compare to baseline |
1684
+ | `--baseline-mode` | `count\|identity` | - | How `--baseline` matches health findings: per file and category (`count`, the default) or per function identity (`identity`, strict, and only against a baseline saved with `--baseline-mode identity`; such a baseline still reads in count mode). Identity is file path plus function name, so renaming or moving a function that is still in the baseline reports it as new; re-save after that kind of refactor. |
1680
1685
  | `--parent-run` | `string` | - | Correlate this run with a previous telemetry analysis run |
1681
1686
  | `--save-baseline` | `string` | - | Save results as baseline |
1682
1687
  | `--production` | `bool` | `false` | Exclude test/dev files, only start/build scripts (applies to every analysis) |
@@ -1718,6 +1723,7 @@ Available on all commands:
1718
1723
  | `--coverage-root` | `string` | - | Absolute prefix to strip from Istanbul file paths in combined mode. Also settable via `FALLOW_COVERAGE_ROOT` or `health.coverageRoot` |
1719
1724
  | `--include-entry-exports` | `bool` | `false` | Report unused exports in entry files instead of auto-marking them as used |
1720
1725
  | `--type-aware` | `bool` | `false` | Opt in to TypeScript semantic analysis for project-wide symbol evidence. This does not emit compiler diagnostics or typed lint findings |
1726
+ | `--no-type-aware` | `bool` | `false` | Disable TypeScript semantic analysis even when `typeAware.enabled` or `FALLOW_TYPE_AWARE` opts in, keeping this run fully syntactic |
1721
1727
  | `--type-aware-project` | `string` | - | TypeScript project config to use for type-aware analysis (repeatable) |
1722
1728
  | `--type-aware-require` | `best-effort\|complete` | - | Decide whether incomplete type-aware analysis is advisory or gating |
1723
1729
  <!-- generated:flags:global:end -->
@@ -1774,6 +1780,7 @@ These are global flags with behavior specific to bare `fallow` combined mode.
1774
1780
  | `FALLOW_CACHE_MAX_SIZE` | Maximum on-disk extraction cache (`.fallow/cache.bin`) size in megabytes (default: `256`). Triggers LRU eviction when crossed. Wins over `cache.maxSizeMb` config field. Intended for CI runners with disk quotas. `--no-cache` short-circuits this knob. |
1775
1781
  | `FALLOW_COVERAGE` | Path to Istanbul coverage data for exact CRAP scoring in `health`, `audit`, and bare `fallow`. |
1776
1782
  | `FALLOW_COVERAGE_ROOT` | Absolute coverage-data prefix to strip before matching Istanbul paths in `health`, `audit`, and bare `fallow`. |
1783
+ | `FALLOW_TYPE_AWARE` | Enable or disable TypeScript semantic (type-aware) analysis for the run. Accepts `true`/`false`/`1`/`0`/`yes`/`no`/`on`/`off`; any other value is a hard error. Sits mid-chain in the precedence: the `--type-aware`/`--no-type-aware` CLI flags win over it, and it wins over the `audit.typeAware` config field, which wins over `typeAware.enabled`. |
1777
1784
  | `FALLOW_AUDIT_BASE` | Pin the `fallow audit` comparison base when `--base` / `--changed-since` is unset (precedence: flag > env > auto-detect). Escape hatch for the agent gate and forks, e.g. `FALLOW_AUDIT_BASE=upstream/main`. When unset, audit auto-detects the `git merge-base` against the branch's upstream or the remote default. A malformed value exits 2. |
1778
1785
  | `FALLOW_AUDIT_CACHE_MAX_AGE_DAYS` | Max age (in days since last reuse or fresh create) of a persistent reusable `fallow audit` base-snapshot worktree cache. Older entries are reclaimed at the top of the next `fallow audit` invocation (default: `30`). Wins over `audit.cacheMaxAgeDays` config field. `0` disables the GC; invalid values silently fall back to config / default. |
1779
1786
  | `FALLOW_UPDATE_CHECK` | Set to `off`, `0`, `false`, `disabled`, or `no` to disable the human-TTY upgrade nudge and its background latest-version check. `DO_NOT_TRACK`, `FALLOW_TELEMETRY_DISABLED`, and CI also suppress it. |
@@ -1879,7 +1886,7 @@ The HTTP layer mirrors the bash `gh_api_retry` / `curl_retry` helpers: `FALLOW_A
1879
1886
  {
1880
1887
  "kind": "dead-code",
1881
1888
  "schema_version": 7,
1882
- "version": "3.9.1",
1889
+ "version": "3.12.0",
1883
1890
  "elapsed_ms": 45,
1884
1891
  "total_issues": 12,
1885
1892
  "entry_points": {
@@ -2039,7 +2046,7 @@ When `--baseline` is used in combined output, the JSON includes a `baseline_delt
2039
2046
  {
2040
2047
  "kind": "dupes",
2041
2048
  "schema_version": 7,
2042
- "version": "3.9.1",
2049
+ "version": "3.12.0",
2043
2050
  "elapsed_ms": 82,
2044
2051
  "total_clones": 15,
2045
2052
  "total_lines_duplicated": 230,
@@ -2083,11 +2090,11 @@ When running `fallow` with no subcommand (all analyses), the JSON output combine
2083
2090
  {
2084
2091
  "kind": "combined",
2085
2092
  "schema_version": 7,
2086
- "version": "3.9.1",
2093
+ "version": "3.12.0",
2087
2094
  "elapsed_ms": 159,
2088
2095
  "check": {
2089
2096
  "schema_version": 7,
2090
- "version": "3.9.1",
2097
+ "version": "3.12.0",
2091
2098
  "elapsed_ms": 45,
2092
2099
  "total_issues": 12,
2093
2100
  "unused_files": [],
@@ -747,6 +747,11 @@ export type ReviewProvider = ("github" | "gitlab")
747
747
  * GitHub Checks API conclusion field.
748
748
  */
749
749
  export type ReviewCheckConclusion = ("success" | "neutral" | "failure")
750
+ /**
751
+ * Stable identifier used to isolate independent review integrations on the
752
+ * same pull or merge request.
753
+ */
754
+ export type ReviewId = string
750
755
  /**
751
756
  * Schema-version discriminator for the review reconcile envelope.
752
757
  */
@@ -2124,19 +2129,21 @@ empty_catalog_groups?: EmptyCatalogGroupFinding[]
2124
2129
  */
2125
2130
  unresolved_catalog_references?: UnresolvedCatalogReferenceFinding[]
2126
2131
  /**
2127
- * Entries in pnpm-workspace.yaml's overrides: section, or package.json's
2128
- * pnpm.overrides block, whose target package is not declared by any
2129
- * workspace package and is not present in pnpm-lock.yaml. Default severity
2132
+ * Entries in pnpm-workspace.yaml's overrides: section, package.json's
2133
+ * pnpm.overrides block, or package.json's top-level npm overrides object,
2134
+ * whose target package is not declared by any workspace package and is
2135
+ * not present in pnpm-lock.yaml or package-lock.json. Default severity
2130
2136
  * is warn because projects without a readable lockfile fall back to
2131
2137
  * manifest-only checks; the hint field flags those conservative cases.
2132
2138
  * Wrapped in [`UnusedDependencyOverrideFinding`].
2133
2139
  */
2134
2140
  unused_dependency_overrides?: UnusedDependencyOverrideFinding[]
2135
2141
  /**
2136
- * pnpm.overrides entries whose key or value does not parse as a valid
2137
- * override spec (empty key, empty value, malformed selector, unbalanced
2138
- * parent matcher). pnpm install will reject these. Default severity is
2139
- * error. Wrapped in [`MisconfiguredDependencyOverrideFinding`].
2142
+ * pnpm.overrides or npm overrides entries whose key or value does not
2143
+ * parse as a valid override spec (empty key, empty value, malformed
2144
+ * selector, unbalanced parent matcher). The package manager will reject
2145
+ * these at install time. Default severity is error. Wrapped in
2146
+ * [`MisconfiguredDependencyOverrideFinding`].
2140
2147
  */
2141
2148
  misconfigured_dependency_overrides?: MisconfiguredDependencyOverrideFinding[]
2142
2149
  /**
@@ -5321,6 +5328,53 @@ istanbul_total?: (number | null)
5321
5328
  severity_critical_count: number
5322
5329
  severity_high_count: number
5323
5330
  severity_moderate_count: number
5331
+ /**
5332
+ * Baseline staleness data, present only when a baseline was loaded.
5333
+ */
5334
+ baseline_staleness?: (HealthBaselineStaleness | null)
5335
+ }
5336
+ /**
5337
+ * Staleness of a loaded health baseline.
5338
+ *
5339
+ * Reports how many saved complexity and CRAP finding entries still matched a
5340
+ * current finding on this run, so consumers can see a rotting baseline before
5341
+ * it degrades to zero overlap. Runtime-coverage suppressions and refactoring
5342
+ * target keys carried by the same baseline are not counted here. Present in
5343
+ * the summary only when a baseline was loaded.
5344
+ */
5345
+ export interface HealthBaselineStaleness {
5346
+ /**
5347
+ * Complexity and CRAP finding entries carried by the loaded baseline.
5348
+ */
5349
+ baseline_entries: number
5350
+ /**
5351
+ * Entries that matched a current finding in the active baseline mode,
5352
+ * including entries matched through a followed file move.
5353
+ */
5354
+ matched_entries: number
5355
+ /**
5356
+ * Entries that matched no current finding on this run.
5357
+ */
5358
+ stale_entries: number
5359
+ /**
5360
+ * Entries that matched only by following a file move in identity mode.
5361
+ * Always zero in count mode.
5362
+ */
5363
+ moved_entries: number
5364
+ /**
5365
+ * True when this run analyzed a subset of the project (changed-file,
5366
+ * diff, or workspace scoping), so the baseline was compared against a
5367
+ * narrowed finding set and staleness cannot be judged. `stale` is always
5368
+ * false on scoped runs.
5369
+ */
5370
+ change_scoped: boolean
5371
+ /**
5372
+ * True exactly when the run was not change-scoped, at least one current
5373
+ * finding existed before baseline filtering, and `stale_entries` reached
5374
+ * a quarter of `baseline_entries`. Mirrors the human warning so machine
5375
+ * consumers do not have to reimplement the threshold.
5376
+ */
5377
+ stale: boolean
5324
5378
  }
5325
5379
  /**
5326
5380
  * Report entry describing whether a threshold override is active, stale, or
@@ -8613,6 +8667,7 @@ export interface ReviewEnvelopeMeta {
8613
8667
  schema: ReviewEnvelopeSchema
8614
8668
  provider: ReviewProvider
8615
8669
  check_conclusion?: (ReviewCheckConclusion | null)
8670
+ review_id?: (ReviewId | null)
8616
8671
  }
8617
8672
  /**
8618
8673
  * Envelope emitted by `fallow ci reconcile-review --format json`. Used by
@@ -9401,19 +9456,21 @@ empty_catalog_groups?: EmptyCatalogGroupFinding[]
9401
9456
  */
9402
9457
  unresolved_catalog_references?: UnresolvedCatalogReferenceFinding[]
9403
9458
  /**
9404
- * Entries in pnpm-workspace.yaml's overrides: section, or package.json's
9405
- * pnpm.overrides block, whose target package is not declared by any
9406
- * workspace package and is not present in pnpm-lock.yaml. Default severity
9459
+ * Entries in pnpm-workspace.yaml's overrides: section, package.json's
9460
+ * pnpm.overrides block, or package.json's top-level npm overrides object,
9461
+ * whose target package is not declared by any workspace package and is
9462
+ * not present in pnpm-lock.yaml or package-lock.json. Default severity
9407
9463
  * is warn because projects without a readable lockfile fall back to
9408
9464
  * manifest-only checks; the hint field flags those conservative cases.
9409
9465
  * Wrapped in [`UnusedDependencyOverrideFinding`].
9410
9466
  */
9411
9467
  unused_dependency_overrides?: UnusedDependencyOverrideFinding[]
9412
9468
  /**
9413
- * pnpm.overrides entries whose key or value does not parse as a valid
9414
- * override spec (empty key, empty value, malformed selector, unbalanced
9415
- * parent matcher). pnpm install will reject these. Default severity is
9416
- * error. Wrapped in [`MisconfiguredDependencyOverrideFinding`].
9469
+ * pnpm.overrides or npm overrides entries whose key or value does not
9470
+ * parse as a valid override spec (empty key, empty value, malformed
9471
+ * selector, unbalanced parent matcher). The package manager will reject
9472
+ * these at install time. Default severity is error. Wrapped in
9473
+ * [`MisconfiguredDependencyOverrideFinding`].
9417
9474
  */
9418
9475
  misconfigured_dependency_overrides?: MisconfiguredDependencyOverrideFinding[]
9419
9476
  /**