Migrating from knip
Move from knip to fallow in minutes: one command converts your knip config. You also get duplication, complexity, and architecture boundary checks that knip does not have.
One command translates your knip configuration to fallow automatically. After the move, fallow also reports code duplication, complexity hotspots, maintainability scores, and architecture boundary violations. knip does not cover these.
Migration workflow
Preview the migration
Run
fallow migrate --dry-runto see the generated config. The command writes no files.fallow migrate --dry-runfallow looks for
knip.json,knip.jsonc,.knip.json,.knip.jsonc,knip.ts,knip.config.ts, and theknipfield inpackage.json. Fallow detects the TypeScript config files (knip.ts,knip.config.ts) but cannot parse them. Convert them toknip.jsonfirst.{ "$schema": "https://raw.githubusercontent.com/fallow-rs/fallow/main/schema.json", // Migrated from knip.json "entry": [ "src/index.ts", "src/cli.ts" ], "ignoreFindings": [ "**/*.generated.ts" ], "ignoreDependencies": [ "@types/node" ] } Migrated from: knip.json Warning (1): [knip] `ignoreBinaries`: Binary filtering is not configurable in fallow Note: knip and fallow use different glob engines; verify migrated entry / ignoreFindings with `fallow dead-code` before relying on CI. https://docs.fallow.tools/migration/from-knip Note: knip's ignore also suppresses dependency and manifest issues by file path; fallow's ignoreFindings never hides manifest-owned findings such as unused dependencies. https://docs.fallow.tools/migration/from-knipGenerate the config
When the preview looks correct, run the migration:
fallow migrate # Write .fallowrc.json fallow migrate --toml # Or output as fallow.tomlReview the config
Open the generated config. Check the translated entry points, ignore patterns, and plugin mappings. Fallow shows a warning for each field that it could not migrate automatically.
Run your first analysis
Run the dead code analysis and compare the results with knip. Then try the analyses that knip does not have:
fallow dead-code # Unused code + circular deps + boundaries fallow dupes # Code duplication fallow health # Complexity hotspots + maintainability scores fallow # All of the above in one pass
What gets migrated
| knip | Fallow |
|---|---|
entry | entry |
project | -- (fallow auto-discovers project files) |
ignore | ignoreFindings (matching files stay in the analysis graph) |
ignoreDependencies | ignoreDependencies (a regex becomes a glob when a glob matches the same packages, see Warnings and caveats) |
ignoreExportsUsedInFile | ignoreExportsUsedInFile (boolean and { type, interface } object form both supported) |
rules, include, exclude | rules (knip issue types map to fallow rule names) |
ignoreBinaries | -- (not applicable) |
| Plugin configs | -- (fallow's built-in plugins detect the framework; the migration warns you to remove the section) |
Warnings and caveats
fallow migrate warns about each setting that it cannot translate, so you do not lose a setting without notice.
Unknown rule names. Your knip rules, exclude, or include entries can reference a key that fallow does not know. The cause can be a typo, a future knip rule, or an issue type that the migrator does not know yet. The migration then prints a warning like this one:
Warning (1):
[knip] `rules.unsued-files`: unknown knip issue type `unsued-files`; not migrated (suggestion: check for a typo or report the missing mapping at https://docs.fallow.tools/migration/from-knip)
Some keys are on the documented list of keys that cannot be mapped: binaries, optionalPeerDependencies, and similar issue types that knip reports and fallow does not. For these keys, the warning reads issue type \X` has no fallow equivalent` and has no suggestion.
Glob-engine drift. knip and fallow use different glob engines. The migration copies entry and ignoreFindings verbatim, but they can match a slightly different set of files than in knip. When the migrated config has either field, the migrate command prints:
Note: knip and fallow use different glob engines; verify migrated entry /
ignoreFindings with `fallow dead-code` before relying on CI.
https://docs.fallow.tools/migration/from-knip
Common patterns (brace expansion {ts,tsx}, double-star **, src/**) match the same files in both engines. ignoreFindings keeps a leading ! as an exception to the earlier patterns. Run fallow dead-code on a representative subset before you use the migrated globs in CI.
Dependency regexes. knip reads an ignoreDependencies entry as a regex when it contains one of * + \ ( | { ^ $. Fallow reads ignoreDependencies entries as exact names or as globs, see ignoreDependencies. The migration converts a regex to a glob only when the glob matches exactly the same package names:
| knip regex | Migrated glob |
|---|---|
@acme/.+ or ^@acme/.+$ | @acme/* |
^@types/ | @types/* |
^eslint-plugin-.*$ | eslint-plugin-* |
-loader$ | *-loader |
^react$ | react |
A regex that has no exact glob form stays out of the config, for example an alternation such as ^(react|vue)$, a character class such as ^@acme/[a-z]+$, or .+ in the middle of a name. The migration prints a warning for each such entry:
Warning (1):
[knip] `ignoreDependencies`: regex pattern `^(react|vue)$` skipped (no glob matches the same packages) (suggestion: rewrite it as a glob such as `@scope/*`, or add each dependency name)
Add the skipped entries by hand as globs or as exact names. After the migration, fallow dead-code names every ignoreDependencies glob that matches no declared dependency, so a glob with a typo does not go unnoticed. See Unmatched config patterns.
Ignore scope. knip's ignore also hides dependency and manifest issues by file path. Fallow's ignoreFindings never hides manifest-owned findings, such as unused dependencies. The migrate command prints a note about this difference for every knip migration.
Comparison
fallow is a standalone binary written in Rust. It needs no Node.js runtime, and has no JIT warmup and no garbage collection pauses.
The table shows cold runs (no cache) on real open-source projects (174 to 38,146 files). The fastest tool in each row is in bold.
| Project | Files | Fallow | knip | Faster |
|---|---|---|---|---|
| zod | 174 | 47ms | 279ms | Fallow 5.9x |
| preact | 244 | 74ms | 2.01s | Fallow 27.1x |
| fastify | 286 | 64ms | 205ms | Fallow 3.2x |
| vue/core | 522 | 138ms | errors* | Fallow only |
| TanStack/query | 901 | 560ms | 1.04s | Fallow 1.9x |
| vite | 1,420 | 595ms | errors* | Fallow only |
| astro | 2,859 | 3.76s | 1.21s | knip 3.1x |
| svelte | 3,337 | 611ms | 632ms | Fallow 1.0x |
| next.js | 20,558 | 2.95s | errors* | Fallow only |
| TypeScript | 38,146 | 2.22s | 736ms | knip 3.0x |
* Current knip (v5 and v6) exits without valid output on next.js, vite, and vue/core, because it fails to load the projects' own config files. Fallow analyzes them.
| Metric | Fallow | knip |
|---|---|---|
| Runtime dependency | None (standalone binary) | Node.js |
| CI setup | Download binary | Install Node + npm dependencies |
The knip numbers are for knip v6 (knip 6.6.1). Fallow is faster on the small and mid-size projects (fastify, preact, query, svelte, zod). Current knip is faster on astro and TypeScript. Fallow's advantage is that one tool does more, and it is not always faster at dead code analysis alone. It also analyzes the three projects that knip cannot load here. Against knip v5 (knip 5.87.0), fallow's lead is wider (for example 13.7x on fastify, 13.0x on zod, 10.3x on preact).
| Feature | Fallow | knip |
|---|---|---|
| Duplication detection | Built-in (fallow dupes) | Not included |
| SARIF output | Yes | Yes (sarif reporter) |
| Baseline comparison | Yes (--baseline) | No |
| Git-aware analysis | --changed-since | No |
| Production mode | --production | --production |
| Auto-fix | Exports + dependencies | Exports + dependencies |
| Config format | JSONC, JSON, TOML | JSON, TS |
| Capability | Fallow | knip |
|---|---|---|
| Built-in catalogue | Major frameworks and tools | Broader niche and legacy coverage |
| Dead code coverage | Files, exports, dependencies, members, cycles, boundaries, and more | Comparable core coverage |
| Custom plugins | Yes | Yes |