UNPKG

5.7 kBJavaScriptView Raw
1"use strict";
2Object.defineProperty(exports, "__esModule", { value: true });
3exports.getExtensions = void 0;
4const util_1 = require("./util");
5const nodeEquivalents = new Map([
6 ['.ts', '.js'],
7 ['.tsx', '.js'],
8 ['.jsx', '.js'],
9 ['.mts', '.mjs'],
10 ['.cts', '.cjs'],
11]);
12const tsResolverEquivalents = new Map([
13 ['.ts', ['.js']],
14 ['.tsx', ['.js', '.jsx']],
15 ['.mts', ['.mjs']],
16 ['.cts', ['.cjs']],
17]);
18// All extensions understood by vanilla node
19const vanillaNodeExtensions = [
20 '.js',
21 '.json',
22 '.node',
23 '.mjs',
24 '.cjs',
25];
26// Extensions added by vanilla node's require() if you omit them:
27// js, json, node
28// Extensions added by vanilla node if you omit them with --experimental-specifier-resolution=node
29// js, json, node, mjs
30// Extensions added by ESM codepath's legacy package.json "main" resolver
31// js, json, node (not mjs!)
32const nodeDoesNotUnderstand = [
33 '.ts',
34 '.tsx',
35 '.jsx',
36 '.cts',
37 '.mts',
38];
39/**
40 * [MUST_UPDATE_FOR_NEW_FILE_EXTENSIONS]
41 * @internal
42 */
43function getExtensions(config, options, tsVersion) {
44 // TS 4.5 is first version to understand .cts, .mts, .cjs, and .mjs extensions
45 const tsSupportsMtsCtsExts = (0, util_1.versionGteLt)(tsVersion, '4.5.0');
46 const requiresHigherTypescriptVersion = [];
47 if (!tsSupportsMtsCtsExts)
48 requiresHigherTypescriptVersion.push('.cts', '.cjs', '.mts', '.mjs');
49 const allPossibleExtensionsSortedByPreference = Array.from(new Set([
50 ...(options.preferTsExts ? nodeDoesNotUnderstand : []),
51 ...vanillaNodeExtensions,
52 ...nodeDoesNotUnderstand,
53 ]));
54 const compiledJsUnsorted = ['.ts'];
55 const compiledJsxUnsorted = [];
56 if (config.options.jsx)
57 compiledJsxUnsorted.push('.tsx');
58 if (tsSupportsMtsCtsExts)
59 compiledJsUnsorted.push('.mts', '.cts');
60 if (config.options.allowJs) {
61 compiledJsUnsorted.push('.js');
62 if (config.options.jsx)
63 compiledJsxUnsorted.push('.jsx');
64 if (tsSupportsMtsCtsExts)
65 compiledJsUnsorted.push('.mjs', '.cjs');
66 }
67 const compiledUnsorted = [...compiledJsUnsorted, ...compiledJsxUnsorted];
68 const compiled = allPossibleExtensionsSortedByPreference.filter((ext) => compiledUnsorted.includes(ext));
69 const compiledNodeDoesNotUnderstand = nodeDoesNotUnderstand.filter((ext) => compiled.includes(ext));
70 /**
71 * TS's resolver can resolve foo.js to foo.ts, by replacing .js extension with several source extensions.
72 * IMPORTANT: Must preserve ordering according to preferTsExts!
73 * Must include the .js/.mjs/.cjs extension in the array!
74 * This affects resolution behavior!
75 * [MUST_UPDATE_FOR_NEW_FILE_EXTENSIONS]
76 */
77 const r = allPossibleExtensionsSortedByPreference.filter((ext) => [...compiledUnsorted, '.js', '.mjs', '.cjs', '.mts', '.cts'].includes(ext));
78 const replacementsForJs = r.filter((ext) => ['.js', '.jsx', '.ts', '.tsx'].includes(ext));
79 const replacementsForJsx = r.filter((ext) => ['.jsx', '.tsx'].includes(ext));
80 const replacementsForMjs = r.filter((ext) => ['.mjs', '.mts'].includes(ext));
81 const replacementsForCjs = r.filter((ext) => ['.cjs', '.cts'].includes(ext));
82 const replacementsForJsOrMjs = r.filter((ext) => ['.js', '.jsx', '.ts', '.tsx', '.mjs', '.mts'].includes(ext));
83 // Node allows omitting .js or .mjs extension in certain situations (CJS, ESM w/experimental flag)
84 // So anything that compiles to .js or .mjs can also be omitted.
85 const experimentalSpecifierResolutionAddsIfOmitted = Array.from(new Set([...replacementsForJsOrMjs, '.json', '.node']));
86 // Same as above, except node curiuosly doesn't do .mjs here
87 const legacyMainResolveAddsIfOmitted = Array.from(new Set([...replacementsForJs, '.json', '.node']));
88 return {
89 /** All file extensions we transform, ordered by resolution preference according to preferTsExts */
90 compiled,
91 /** Resolved extensions that vanilla node will not understand; we should handle them */
92 nodeDoesNotUnderstand,
93 /** Like the above, but only the ones we're compiling */
94 compiledNodeDoesNotUnderstand,
95 /**
96 * Mapping from extensions understood by tsc to the equivalent for node,
97 * as far as getFormat is concerned.
98 */
99 nodeEquivalents,
100 /**
101 * Mapping from extensions rejected by TSC in import specifiers, to the
102 * possible alternatives that TS's resolver will accept.
103 *
104 * When we allow users to opt-in to .ts extensions in import specifiers, TS's
105 * resolver requires us to replace the .ts extensions with .js alternatives.
106 * Otherwise, resolution fails.
107 *
108 * Note TS's resolver is only used by, and only required for, typechecking.
109 * This is separate from node's resolver, which we hook separately and which
110 * does not require this mapping.
111 */
112 tsResolverEquivalents,
113 /**
114 * Extensions that we can support if the user upgrades their typescript version.
115 * Used when raising hints.
116 */
117 requiresHigherTypescriptVersion,
118 /**
119 * --experimental-specifier-resolution=node will add these extensions.
120 */
121 experimentalSpecifierResolutionAddsIfOmitted,
122 /**
123 * ESM loader will add these extensions to package.json "main" field
124 */
125 legacyMainResolveAddsIfOmitted,
126 replacementsForMjs,
127 replacementsForCjs,
128 replacementsForJsx,
129 replacementsForJs,
130 };
131}
132exports.getExtensions = getExtensions;
133//# sourceMappingURL=file-extensions.js.map
\No newline at end of file