knip 6.17.1 → 6.18.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.
@@ -1017,4 +1017,5 @@ export declare class ConfigurationChief {
1017
1017
  };
1018
1018
  findWorkspaceByFilePath(filePath: string): Workspace | undefined;
1019
1019
  getUnusedIgnoredWorkspaces(): string[];
1020
+ getUnusedConfiguredWorkspaces(): string[];
1020
1021
  }
@@ -392,4 +392,27 @@ export class ConfigurationChief {
392
392
  return !isDirectory(dir) || isFile(dir, 'package.json');
393
393
  });
394
394
  }
395
+ getUnusedConfiguredWorkspaces() {
396
+ if (!this.rawConfig?.workspaces)
397
+ return [];
398
+ const unused = [];
399
+ for (const key of Object.keys(this.rawConfig.workspaces)) {
400
+ if (key.includes('*')) {
401
+ const isMatch = picomatch(key);
402
+ let isUsed = false;
403
+ for (const name of this.workspacePackages.keys()) {
404
+ if (isMatch(name)) {
405
+ isUsed = true;
406
+ break;
407
+ }
408
+ }
409
+ if (!isUsed)
410
+ unused.push(key);
411
+ }
412
+ else if (!this.workspacePackages.has(key)) {
413
+ unused.push(key);
414
+ }
415
+ }
416
+ return unused;
417
+ }
395
418
  }
@@ -20,8 +20,10 @@ export declare class IssueCollector {
20
20
  private isTrackUnusedIgnorePatterns;
21
21
  private unusedIgnorePatterns;
22
22
  private unusedIgnoreFilesPatterns;
23
+ private selectedWorkspaces;
23
24
  constructor(options: MainOptions);
24
25
  setWorkspaceFilter(workspaceFilePathFilter: WorkspaceFilePathFilter | undefined): void;
26
+ setSelectedWorkspaces(selectedWorkspaces: Set<string> | undefined): void;
25
27
  private collectIgnorePatterns;
26
28
  addIgnorePatterns(entries: {
27
29
  pattern: string;
@@ -1,4 +1,5 @@
1
1
  import picomatch from 'picomatch';
2
+ import { ROOT_WORKSPACE_NAME } from './constants.js';
2
3
  import { partition } from './util/array.js';
3
4
  import { prependDirToPattern } from './util/glob.js';
4
5
  import { initCounters, initIssues } from './util/issue-initializers.js';
@@ -29,6 +30,7 @@ export class IssueCollector {
29
30
  isTrackUnusedIgnorePatterns;
30
31
  unusedIgnorePatterns = new Map();
31
32
  unusedIgnoreFilesPatterns = new Map();
33
+ selectedWorkspaces;
32
34
  constructor(options) {
33
35
  this.cwd = options.cwd;
34
36
  this.rules = options.rules;
@@ -41,6 +43,9 @@ export class IssueCollector {
41
43
  if (workspaceFilePathFilter)
42
44
  this.workspaceFilter = workspaceFilePathFilter;
43
45
  }
46
+ setSelectedWorkspaces(selectedWorkspaces) {
47
+ this.selectedWorkspaces = selectedWorkspaces;
48
+ }
44
49
  collectIgnorePatterns(entries, patterns, unused, type) {
45
50
  for (const entry of entries) {
46
51
  patterns.add(entry.pattern);
@@ -145,6 +150,11 @@ export class IssueCollector {
145
150
  return true;
146
151
  }
147
152
  addConfigurationHint(issue) {
153
+ if (this.selectedWorkspaces) {
154
+ const workspaceName = issue.workspaceName ?? ROOT_WORKSPACE_NAME;
155
+ if (workspaceName === ROOT_WORKSPACE_NAME || !this.selectedWorkspaces.has(workspaceName))
156
+ return;
157
+ }
148
158
  const key = `${issue.workspaceName}::${issue.type}::${issue.identifier}`;
149
159
  if (!this.configurationHints.has(key))
150
160
  this.configurationHints.set(key, issue);
@@ -15,7 +15,8 @@ export const resolve = (_binary, args, options) => {
15
15
  const command = parsed.call ? fromArgs([parsed.call]) : [];
16
16
  const restArgs = argsFrom(args, packageSpecifier);
17
17
  const isBinary = specifier && !packageSpecifier.includes('@') && !isInternal(specifier);
18
- const dependency = isBinary ? toBinary(specifier) : toDependency(specifier, { optional: !parsed.no });
18
+ const opts = parsed.no ? undefined : { optional: true };
19
+ const dependency = isBinary ? toBinary(specifier, opts) : toDependency(specifier, opts);
19
20
  const specifiers = dependency && !parsed.yes ? [dependency] : [];
20
21
  return [
21
22
  ...specifiers,
@@ -233,6 +233,10 @@ export const analyze = async ({ analyzedFiles, counselor, chief, collector, depu
233
233
  const catalogIssues = await counselor.settleCatalogIssues(options);
234
234
  for (const issue of catalogIssues)
235
235
  collector.addIssue(issue);
236
+ const unusedConfiguredWorkspaces = chief.getUnusedConfiguredWorkspaces();
237
+ for (const identifier of unusedConfiguredWorkspaces) {
238
+ collector.addConfigurationHint({ type: 'workspaces', identifier });
239
+ }
236
240
  const unusedIgnoredWorkspaces = chief.getUnusedIgnoredWorkspaces();
237
241
  for (const identifier of unusedIgnoredWorkspaces) {
238
242
  collector.addConfigurationHint({ type: 'ignoreWorkspaces', identifier });
@@ -59,7 +59,7 @@ export async function build({ chief, collector, counselor, deputy, principal, is
59
59
  const dependencies = deputy.getDependencies(name);
60
60
  const baseConfig = chief.getConfigForWorkspace(name);
61
61
  const tsConfigFilePath = join(dir, options.tsConfigFile ?? 'tsconfig.json');
62
- const { isFile, compilerOptions, fileNames, include, exclude, sourceMapPairs } = await loadTSConfig(tsConfigFilePath);
62
+ const { isFile, compilerOptions, fileNames, include, exclude, sourceMapPairs, paths: tsConfigPaths, } = await loadTSConfig(tsConfigFilePath);
63
63
  const [definitionPaths, tscSourcePaths] = partition(fileNames, filePath => IS_DTS.test(filePath));
64
64
  const worker = new WorkspaceWorker({
65
65
  name,
@@ -129,6 +129,8 @@ export async function build({ chief, collector, counselor, deputy, principal, is
129
129
  for (const dep of getManifestImportDependencies(manifest))
130
130
  deputy.addReferencedDependency(name, dep);
131
131
  principal.addPaths(config.paths, dir, dir);
132
+ if (tsConfigPaths)
133
+ principal.addPaths(tsConfigPaths, dir, dir);
132
134
  principal.addRootDirs(compilerOptions.rootDirs, dir);
133
135
  const inputsFromPlugins = await worker.runPlugins();
134
136
  for (const id of inputsFromPlugins)
@@ -4,7 +4,11 @@ import { toCosmiconfig } from '../../util/plugin-config.js';
4
4
  const title = 'commitlint';
5
5
  const enablers = ['@commitlint/cli'];
6
6
  const isEnabled = ({ dependencies }) => hasDependency(dependencies, enablers);
7
- const config = ['package.json', 'package.yaml', ...toCosmiconfig('commitlint', { additionalExtensions: ['cts', 'mts'] })];
7
+ const config = [
8
+ 'package.json',
9
+ 'package.yaml',
10
+ ...toCosmiconfig('commitlint', { additionalExtensions: ['cts', 'mts'] }),
11
+ ];
8
12
  const resolveConfig = async (config) => {
9
13
  const extendsConfigs = config.extends
10
14
  ? [config.extends]
@@ -1,3 +1,4 @@
1
+ import { arrayify } from '../../util/array.js';
1
2
  import { _glob, _dirGlob } from '../../util/glob.js';
2
3
  import { toDeferResolve, toEntry } from '../../util/input.js';
3
4
  import { isInternal, join, normalize, toAbsolute } from '../../util/path.js';
@@ -8,7 +9,7 @@ const enablers = ['jest'];
8
9
  const isEnabled = ({ dependencies, manifest }) => hasDependency(dependencies, enablers) || Boolean(manifest.name?.startsWith('jest-presets'));
9
10
  const config = ['jest.config.{js,ts,mjs,cjs,mts,cts,json}', 'package.json'];
10
11
  const mocks = ['**/__mocks__/**/*.[jt]s?(x)'];
11
- const entry = ['**/__tests__/**/*.[jt]s?(x)', '**/?(*.)+(spec|test).[jt]s?(x)', ...mocks];
12
+ const entry = ['**/__tests__/**/*.?(c|m)[jt]s?(x)', '**/?(*.)+(spec|test).?(c|m)[jt]s?(x)', ...mocks];
12
13
  const rootDirRe = /<rootDir>/;
13
14
  const resolveDependencies = async (config, rootDir, options) => {
14
15
  const { configFileDir } = options;
@@ -35,7 +36,7 @@ const resolveDependencies = async (config, rootDir, options) => {
35
36
  projects.push(dependency);
36
37
  }
37
38
  }
38
- const runner = config.runner ? [config.runner] : [];
39
+ const runner = config.runner ? [typeof config.runner === 'string' ? config.runner : config.runner[0]] : [];
39
40
  const runtime = config.runtime && config.runtime !== 'jest-circus' ? [config.runtime] : [];
40
41
  const environments = config.testEnvironment === 'jsdom'
41
42
  ? ['jest-environment-jsdom']
@@ -88,7 +89,9 @@ const resolveConfig = async (localConfig, options) => {
88
89
  const replaceRootDir = (name) => name.replace(rootDirRe, rootDir);
89
90
  const inputs = await resolveDependencies(localConfig, rootDir, options);
90
91
  const entries = localConfig.testMatch
91
- ? localConfig.testMatch.map(replaceRootDir).map(id => toEntry(id))
92
+ ? arrayify(localConfig.testMatch)
93
+ .map(replaceRootDir)
94
+ .map(id => toEntry(id))
92
95
  : entry.map(id => toEntry(id));
93
96
  if (localConfig.testMatch && !options.config.entry)
94
97
  entries.push(...mocks.map(id => toEntry(id)));
@@ -10,7 +10,7 @@ const args = {
10
10
  resolveInputs: (parsed, { manifest }) => {
11
11
  const inputs = [];
12
12
  if (previewCommands.has(parsed._[0])) {
13
- const dep = (manifest.getMajor('react-email') ?? 0) >= 6 ? '@react-email/ui' : '@react-email/preview-server';
13
+ const dep = (manifest.getMajor('react-email') ?? 6) >= 6 ? '@react-email/ui' : '@react-email/preview-server';
14
14
  inputs.push(toDependency(dep));
15
15
  }
16
16
  if (parsed.dir)
@@ -1,6 +1,6 @@
1
1
  import { compact } from '../../util/array.js';
2
- import { toAlias, toConfig, toDeferResolve, toProductionDependency } from '../../util/input.js';
3
- import { dirname, join } from '../../util/path.js';
2
+ import { toConfig, toDeferResolve, toProductionDependency } from '../../util/input.js';
3
+ import { join } from '../../util/path.js';
4
4
  import { hasDependency } from '../../util/plugin.js';
5
5
  const title = 'TypeScript';
6
6
  const enablers = ['typescript', '@typescript/native-preview'];
@@ -24,18 +24,12 @@ const resolveConfig = async (localConfig, options) => {
24
24
  ? compilerOptions.plugins.map(plugin => (typeof plugin === 'object' && 'name' in plugin ? plugin.name : ''))
25
25
  : [];
26
26
  const importHelpers = compilerOptions?.importHelpers ? ['tslib'] : [];
27
- const paths = compilerOptions.paths;
28
- const configFileDir = dirname(options.configFilePath);
29
- const aliases = paths && configFileDir !== options.cwd
30
- ? Object.entries(paths).map(([key, prefixes]) => toAlias(key, prefixes, { dir: join(configFileDir, compilerOptions.baseUrl ?? '.') }))
31
- : [];
32
27
  return compact([
33
28
  ...extend,
34
29
  ...references,
35
30
  ...types.map(id => toDeferResolve(id, { isTypeOnly: true, dir: options.cwd })),
36
31
  ...[...plugins, ...importHelpers].map(id => toDeferResolve(id)),
37
32
  ...jsx,
38
- ...aliases,
39
33
  ]);
40
34
  };
41
35
  const args = {
@@ -9,7 +9,7 @@ const title = 'Vitest';
9
9
  const enablers = ['vitest'];
10
10
  const isEnabled = ({ dependencies }) => hasDependency(dependencies, enablers);
11
11
  const config = ['vitest.config.{js,mjs,ts,cjs,mts,cts}', 'vitest.{workspace,projects}.{js,mjs,ts,cjs,mts,cts,json}'];
12
- const mocks = ['**/__mocks__/**/*.[jt]s?(x)'];
12
+ const mocks = ['**/__mocks__/**/*.?(c|m)[jt]s?(x)'];
13
13
  const entry = ['**/*.{bench,test,test-d,spec,spec-d}.?(c|m)[jt]s?(x)', ...mocks];
14
14
  const findConfigDependencies = (localConfig, options, vitestRoot) => {
15
15
  const { configFileDir: dir } = options;
@@ -162,6 +162,9 @@ const args = {
162
162
  if (typeof parsed['coverage'] === 'object' && parsed['coverage'].provider) {
163
163
  inputs.push(toDependency(`@vitest/coverage-${parsed['coverage'].provider}`));
164
164
  }
165
+ else if (parsed['coverage']) {
166
+ inputs.push(toDependency('@vitest/coverage-v8', { optional: true }));
167
+ }
165
168
  if (parsed['reporter']) {
166
169
  for (const reporter of getExternalReporters([parsed['reporter']].flat())) {
167
170
  inputs.push(toDependency(reporter));
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: ({ report, issues, cwd }: ReporterOptions) => Promise<void>;
3
2
  export default _default;
3
+ declare function _default({ report, issues, cwd }: ReporterOptions): Promise<void>;
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: ({ report, issues, isShowProgress, options, cwd }: ReporterOptions) => void;
3
2
  export default _default;
3
+ declare function _default({ report, issues, isShowProgress, options, cwd }: ReporterOptions): void;
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: ({ report, issues, isShowProgress, cwd }: ReporterOptions) => void;
3
2
  export default _default;
3
+ declare function _default({ report, issues, isShowProgress, cwd }: ReporterOptions): void;
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: ({ report, issues, cwd }: ReporterOptions) => void;
3
2
  export default _default;
3
+ declare function _default({ report, issues, cwd }: ReporterOptions): void;
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: ({ report, issues, cwd, configurationHints, tagHints, isDisableConfigHints, isDisableTagHints, isTreatConfigHintsAsErrors, isTreatTagHintsAsErrors, configFilePath, }: ReporterOptions) => void;
3
2
  export default _default;
3
+ declare function _default({ report, issues, cwd, configurationHints, tagHints, isDisableConfigHints, isDisableTagHints, isTreatConfigHintsAsErrors, isTreatTagHintsAsErrors, configFilePath, }: ReporterOptions): void;
@@ -30,5 +30,5 @@ export type JSONReportEntry = {
30
30
  export type JSONReport = {
31
31
  issues: Array<JSONReportEntry>;
32
32
  };
33
- declare const _default: ({ report, issues, options, cwd }: ReporterOptions) => Promise<void>;
34
33
  export default _default;
34
+ declare function _default({ report, issues, options, cwd }: ReporterOptions): Promise<void>;
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: ({ report, issues, cwd }: ReporterOptions) => void;
3
2
  export default _default;
3
+ declare function _default({ report, issues, cwd }: ReporterOptions): void;
@@ -1,3 +1,3 @@
1
1
  import type { ReporterOptions } from '../types/issues.ts';
2
- declare const _default: (options: ReporterOptions) => void;
3
2
  export default _default;
3
+ declare function _default(options: ReporterOptions): void;
@@ -10,5 +10,5 @@ interface TraceReporterOptions {
10
10
  workspaceFilePathFilter: WorkspaceFilePathFilter;
11
11
  issues: Issues;
12
12
  }
13
- declare const _default: ({ graph, explorer, options, workspaceFilePathFilter, issues }: TraceReporterOptions) => void;
14
13
  export default _default;
14
+ declare function _default({ graph, explorer, options, workspaceFilePathFilter, issues }: TraceReporterOptions): void;
@@ -46,6 +46,7 @@ export const hintPrinters = new Map([
46
46
  ['ignoreBinaries', { print: unused }],
47
47
  ['ignoreDependencies', { print: unused }],
48
48
  ['ignoreUnresolved', { print: unused }],
49
+ ['workspaces', { print: unused }],
49
50
  ['ignoreWorkspaces', { print: unused }],
50
51
  ['entry-empty', { print: empty }],
51
52
  ['project-empty', { print: empty }],
@@ -61,6 +62,7 @@ export const hintPrinters = new Map([
61
62
  const hintTypesOrder = [
62
63
  ['top-level-unconfigured', 'workspace-unconfigured'],
63
64
  ['entry-top-level', 'project-top-level'],
65
+ ['workspaces'],
64
66
  ['ignore', 'ignoreFiles'],
65
67
  ['ignoreWorkspaces'],
66
68
  ['ignoreDependencies'],
@@ -7,5 +7,5 @@ interface WatchReporter {
7
7
  duration?: number;
8
8
  size: number;
9
9
  }
10
- declare const _default: (options: MainOptions, { issues, streamer, duration, size }: WatchReporter) => void;
11
10
  export default _default;
11
+ declare function _default(options: MainOptions, { issues, streamer, duration, size }: WatchReporter): void;
package/dist/run.js CHANGED
@@ -33,6 +33,7 @@ export const run = async (options) => {
33
33
  const findWorkspaceManifestImports = getWorkspaceManifestHandler(chief);
34
34
  const principal = new ProjectPrincipal(options, toSourceFilePath, findWorkspaceManifestImports);
35
35
  collector.setWorkspaceFilter(chief.workspaceFilePathFilter);
36
+ collector.setSelectedWorkspaces(chief.selectedWorkspaces);
36
37
  collector.setIgnoreIssues(chief.getIgnoreIssues());
37
38
  debugLogObject('*', 'Included workspaces', () => workspaces.map(w => w.pkgName));
38
39
  debugLogObject('*', 'Included workspace configs', () => workspaces.map(w => ({ pkgName: w.pkgName, name: w.name, config: w.config, ancestors: w.ancestors })));
@@ -72,7 +72,7 @@ export type Preprocessor = (options: ReporterOptions) => ReporterOptions;
72
72
  export type IssueSeverity = 'error' | 'warn' | 'off';
73
73
  export type Rules = Record<IssueType, IssueSeverity>;
74
74
  export type ConfigurationHints = Map<string, ConfigurationHint>;
75
- export type ConfigurationHintType = 'ignore' | 'ignoreFiles' | 'ignoreBinaries' | 'ignoreDependencies' | 'ignoreUnresolved' | 'ignoreWorkspaces' | 'entry-redundant' | 'project-redundant' | 'entry-top-level' | 'project-top-level' | 'entry-empty' | 'project-empty' | 'project-extension-unregistered' | 'package-entry' | 'top-level-unconfigured' | 'workspace-unconfigured';
75
+ export type ConfigurationHintType = 'ignore' | 'ignoreFiles' | 'ignoreBinaries' | 'ignoreDependencies' | 'ignoreUnresolved' | 'workspaces' | 'ignoreWorkspaces' | 'entry-redundant' | 'project-redundant' | 'entry-top-level' | 'project-top-level' | 'entry-empty' | 'project-empty' | 'project-extension-unregistered' | 'package-entry' | 'top-level-unconfigured' | 'workspace-unconfigured';
76
76
  export type ConfigurationHint = {
77
77
  type: ConfigurationHintType;
78
78
  identifier: string | RegExp;
@@ -106,7 +106,7 @@ export const createOptions = async (options) => {
106
106
  includedIssueTypes,
107
107
  isCache: args.cache ?? false,
108
108
  isDebug,
109
- isDisableConfigHints: args['no-config-hints'] || isProduction || Boolean(workspace),
109
+ isDisableConfigHints: args['no-config-hints'] || isProduction,
110
110
  isDisableTagHints: Boolean(args['no-tag-hints']),
111
111
  isFix: args.fix ?? options.isFix ?? isFixFiles ?? fixTypes.length > 0,
112
112
  isFixCatalog: fixTypes.length === 0 || fixTypes.includes('catalog'),
@@ -7,6 +7,7 @@ interface TSConfigInfo {
7
7
  include: string[] | undefined;
8
8
  exclude: string[] | undefined;
9
9
  sourceMapPairs: SourceMap[];
10
+ paths: Record<string, string[]> | undefined;
10
11
  }
11
12
  export declare const loadTSConfig: (tsConfigFilePath: string) => Promise<TSConfigInfo>;
12
13
  export {};
@@ -1,4 +1,5 @@
1
1
  import { parseTsconfig } from 'get-tsconfig';
2
+ import { compact } from './array.js';
2
3
  import { isFile } from './fs.js';
3
4
  import { _syncGlob } from './glob.js';
4
5
  import { dirname, isAbsolute, join, toAbsolute } from './path.js';
@@ -16,6 +17,15 @@ const resolvePatterns = (patterns, dir, expandDirs = false) => {
16
17
  return expandDirs && !hasGlobChar(p) && !hasExtension(p) ? join(resolved, '**/*') : resolved;
17
18
  });
18
19
  };
20
+ const pathsBaseDir = (baseUrl, dir) => (baseUrl ? toAbsolute(baseUrl, dir) : dir);
21
+ const collectPaths = (acc, paths, baseDir) => {
22
+ if (!paths)
23
+ return;
24
+ for (const key in paths) {
25
+ const resolved = paths[key].map(p => toAbsolute(p, baseDir));
26
+ acc[key] = key in acc ? compact([...acc[key], ...resolved]) : resolved;
27
+ }
28
+ };
19
29
  const DEFAULT_INCLUDE = ['**/*'];
20
30
  const TS_EXTENSIONS = new Set(['.ts', '.tsx', '.mts', '.cts', '.js', '.jsx', '.mjs', '.cjs']);
21
31
  const isDtsExt = /\.d\.(m|c)?ts$/;
@@ -53,7 +63,7 @@ const resolveReference = (refPath, dir) => {
53
63
  return isFile(withTsconfig) ? withTsconfig : undefined;
54
64
  };
55
65
  const absDir = (path, dir) => toAbsolute(path, dir).replace(/\/+$/, '');
56
- const walkReferences = (target, references, dir, visited, pairs) => {
66
+ const walkReferences = (target, references, dir, visited, pairs, paths) => {
57
67
  if (!references?.length)
58
68
  return;
59
69
  for (const ref of references) {
@@ -64,6 +74,7 @@ const walkReferences = (target, references, dir, visited, pairs) => {
64
74
  const refConfig = parseTsconfig(refPath);
65
75
  const refDir = dirname(refPath);
66
76
  const refOpts = refConfig.compilerOptions;
77
+ collectPaths(paths, refOpts?.paths, pathsBaseDir(refOpts?.baseUrl, refDir));
67
78
  const refOutDir = refOpts?.outDir ? absDir(refOpts.outDir, refDir) : undefined;
68
79
  const refRootDir = refOpts?.rootDir ? absDir(refOpts.rootDir, refDir) : undefined;
69
80
  if (refOutDir && refRootDir && refOutDir !== refRootDir)
@@ -73,7 +84,7 @@ const walkReferences = (target, references, dir, visited, pairs) => {
73
84
  if (refRootDir && !target.rootDir)
74
85
  target.rootDir = refRootDir;
75
86
  if (!refOutDir || !refRootDir)
76
- walkReferences(target, refConfig.references, refDir, visited, pairs);
87
+ walkReferences(target, refConfig.references, refDir, visited, pairs, paths);
77
88
  }
78
89
  };
79
90
  const EMPTY = {
@@ -82,6 +93,7 @@ const EMPTY = {
82
93
  include: undefined,
83
94
  exclude: undefined,
84
95
  sourceMapPairs: [],
96
+ paths: undefined,
85
97
  };
86
98
  export const loadTSConfig = async (tsConfigFilePath) => {
87
99
  if (!isFile(tsConfigFilePath))
@@ -96,15 +108,18 @@ export const loadTSConfig = async (tsConfigFilePath) => {
96
108
  compilerOptions.rootDir = absDir(compilerOptions.rootDir, dir);
97
109
  if (compilerOptions.rootDirs)
98
110
  compilerOptions.rootDirs = compilerOptions.rootDirs.map(d => absDir(d, dir));
111
+ const tsconfigPaths = {};
112
+ collectPaths(tsconfigPaths, compilerOptions.paths, pathsBaseDir(compilerOptions.baseUrl, dir));
99
113
  const sourceMapPairs = [];
100
114
  if (config.references?.length) {
101
- walkReferences(compilerOptions, config.references, dir, new Set([tsConfigFilePath]), sourceMapPairs);
115
+ walkReferences(compilerOptions, config.references, dir, new Set([tsConfigFilePath]), sourceMapPairs, tsconfigPaths);
102
116
  }
103
117
  const include = resolvePatterns(config.include, dir, true);
104
118
  const exclude = resolvePatterns(config.exclude, dir, true);
105
119
  const files = resolvePatterns(config.files, dir);
106
120
  const fileNames = expandFileNames(dir, compilerOptions, include, exclude, files);
107
- return { isFile: true, compilerOptions, fileNames, include, exclude, sourceMapPairs };
121
+ const paths = Object.keys(tsconfigPaths).length > 0 ? tsconfigPaths : undefined;
122
+ return { isFile: true, compilerOptions, fileNames, include, exclude, sourceMapPairs, paths };
108
123
  }
109
124
  catch {
110
125
  return { isFile: true, ...EMPTY };
@@ -15,7 +15,7 @@ export default async function mapWorkspaces(cwd, workspaces) {
15
15
  const manifestPatterns = patterns.map(p => join(p, 'package.json'));
16
16
  const matches = await glob(manifestPatterns, {
17
17
  cwd,
18
- ignore: ['**/node_modules/**', ...negatedPatterns.map(p => p.slice(1))],
18
+ ignore: ['**/node_modules/**', ...negatedPatterns.map(p => join(p.slice(1), 'package.json'))],
19
19
  });
20
20
  for (const match of matches.sort()) {
21
21
  const name = match === 'package.json' ? '.' : match.replace(/\/package\.json$/, '');
@@ -8,6 +8,6 @@ export type WorkspaceManifestHandler = (filePath: string) => {
8
8
  } | undefined;
9
9
  export declare const getWorkspaceManifestHandler: (chief: ConfigurationChief) => WorkspaceManifestHandler;
10
10
  export declare const getModuleSourcePathHandler: (chief: ConfigurationChief) => (filePath: string) => string | undefined;
11
- export declare const getToSourcePathsHandler: (chief: ConfigurationChief) => (specifiers: Set<string>, dir: string, extensions: (string | undefined) | undefined, label: string) => Promise<string[]>;
11
+ export declare const getToSourcePathsHandler: (chief: ConfigurationChief) => (specifiers: Set<string>, dir: string, extensions: string | undefined, label: string) => Promise<string[]>;
12
12
  export declare const toSourceMappedSpecifiers: (ws: Workspace | undefined, absSpecifier: string, extensions?: string) => string[];
13
13
  export type ToSourceFilePath = ReturnType<typeof getModuleSourcePathHandler>;
package/dist/version.d.ts CHANGED
@@ -1 +1 @@
1
- export declare const version = "6.17.1";
1
+ export declare const version = "6.18.0";
package/dist/version.js CHANGED
@@ -1 +1 @@
1
- export const version = '6.17.1';
1
+ export const version = '6.18.0';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "knip",
3
- "version": "6.17.1",
3
+ "version": "6.18.0",
4
4
  "description": "Find and fix unused dependencies, exports and files in your TypeScript and JavaScript projects",
5
5
  "keywords": [
6
6
  "analysis",
@@ -81,8 +81,8 @@
81
81
  "formatly": "^0.3.0",
82
82
  "get-tsconfig": "4.14.0",
83
83
  "jiti": "^2.7.0",
84
- "oxc-parser": "^0.135.0",
85
- "oxc-resolver": "^11.20.0",
84
+ "oxc-parser": "^0.137.0",
85
+ "oxc-resolver": "11.21.3",
86
86
  "picomatch": "^4.0.4",
87
87
  "smol-toml": "^1.6.1",
88
88
  "strip-json-comments": "5.0.3",
@@ -96,7 +96,7 @@
96
96
  "@types/bun": "^1.3.14",
97
97
  "@types/picomatch": "^4.0.3",
98
98
  "@types/webpack": "^5.28.5",
99
- "@typescript/native-preview": "7.0.0-dev.20260612.1",
99
+ "@typescript/native-preview": "7.0.0-dev.20260619.1",
100
100
  "codeclimate-types": "^0.3.1",
101
101
  "prettier": "^3.8.4",
102
102
  "tsx": "^4.22.4"