ts-repo-utils 4.0.1 → 5.0.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/dist/functions/gen-index.d.mts +11 -9
- package/dist/functions/gen-index.d.mts.map +1 -1
- package/dist/functions/gen-index.mjs +41 -22
- package/dist/functions/gen-index.mjs.map +1 -1
- package/dist/index.d.mts.map +1 -1
- package/package.json +3 -3
- package/src/functions/gen-index.mts +74 -46
- package/src/functions/gen-index.test.mts +18 -0
- package/src/index.mts +2 -0
- package/dist/globals.d.mjs +0 -2
- package/dist/globals.d.mjs.map +0 -1
- package/dist/globals.d.mts +0 -1
- package/src/globals.d.mts +0 -1
|
@@ -3,21 +3,23 @@ import '../node-global.mjs';
|
|
|
3
3
|
* Configuration for index file generation.
|
|
4
4
|
*/
|
|
5
5
|
export type GenIndexConfig = DeepReadonly<{
|
|
6
|
-
/** Command to run for formatting generated files (default: 'npm run fmt') */
|
|
7
|
-
formatCommand: string;
|
|
8
6
|
/** Target directories to generate index files for (string or array of strings) */
|
|
9
|
-
targetDirectory: string | string[];
|
|
10
|
-
/**
|
|
11
|
-
|
|
12
|
-
/** File
|
|
7
|
+
targetDirectory: string | readonly string[];
|
|
8
|
+
/** Glob patterns of files to exclude from exports (default: excludes `'**\/*.{test,spec}.?(c|m)[jt]s?(x)'`) */
|
|
9
|
+
excludePatterns?: readonly string[];
|
|
10
|
+
/** File extensions of source files to export (default: ['.ts', '.tsx']) */
|
|
11
|
+
sourceExtensions?: readonly `.${string}`[];
|
|
12
|
+
/** File extension of index files to generate (default: '.ts') */
|
|
13
|
+
indexExtension?: `.${string}`;
|
|
14
|
+
/** File extension to use in export statements (default: '.js') */
|
|
13
15
|
exportExtension?: `.${string}`;
|
|
14
|
-
/**
|
|
15
|
-
|
|
16
|
+
/** Command to run for formatting generated files (default: 'npm run fmt') */
|
|
17
|
+
formatCommand?: string;
|
|
16
18
|
/** Whether to suppress output during execution (default: false) */
|
|
17
19
|
silent?: boolean;
|
|
18
20
|
}>;
|
|
19
21
|
/**
|
|
20
|
-
* Generates index.
|
|
22
|
+
* Generates index.ts files recursively in `config.targetDirectory`.
|
|
21
23
|
* @param config - Configuration for index file generation
|
|
22
24
|
* @throws Error if any step fails.
|
|
23
25
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"gen-index.d.mts","sourceRoot":"","sources":["../../src/functions/gen-index.mts"],"names":[],"mappings":"AAEA,OAAO,oBAAoB,CAAC;AAG5B;;GAEG;AACH,MAAM,MAAM,cAAc,GAAG,YAAY,CAAC;IACxC,
|
|
1
|
+
{"version":3,"file":"gen-index.d.mts","sourceRoot":"","sources":["../../src/functions/gen-index.mts"],"names":[],"mappings":"AAEA,OAAO,oBAAoB,CAAC;AAG5B;;GAEG;AACH,MAAM,MAAM,cAAc,GAAG,YAAY,CAAC;IACxC,kFAAkF;IAClF,eAAe,EAAE,MAAM,GAAG,SAAS,MAAM,EAAE,CAAC;IAE5C,+GAA+G;IAC/G,eAAe,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IAEpC,2EAA2E;IAC3E,gBAAgB,CAAC,EAAE,SAAS,IAAI,MAAM,EAAE,EAAE,CAAC;IAE3C,iEAAiE;IACjE,cAAc,CAAC,EAAE,IAAI,MAAM,EAAE,CAAC;IAE9B,kEAAkE;IAClE,eAAe,CAAC,EAAE,IAAI,MAAM,EAAE,CAAC;IAE/B,6EAA6E;IAC7E,aAAa,CAAC,EAAE,MAAM,CAAC;IAEvB,mEAAmE;IACnE,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB,CAAC,CAAC;AAYH;;;;GAIG;AACH,eAAO,MAAM,QAAQ,GAAU,QAAQ,cAAc,KAAG,OAAO,CAAC,IAAI,CA8CnE,CAAC"}
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import micromatch from 'micromatch';
|
|
2
|
-
import { Result } from 'ts-data-forge';
|
|
2
|
+
import { Result, ISet, Arr, isString } from 'ts-data-forge';
|
|
3
3
|
import '../node-global.mjs';
|
|
4
4
|
import { assertPathExists } from './assert-path-exists.mjs';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
|
-
* Generates index.
|
|
7
|
+
* Generates index.ts files recursively in `config.targetDirectory`.
|
|
8
8
|
* @param config - Configuration for index file generation
|
|
9
9
|
* @throws Error if any step fails.
|
|
10
10
|
*/
|
|
@@ -32,14 +32,16 @@ const genIndex = async (config) => {
|
|
|
32
32
|
}
|
|
33
33
|
echo('✓ Index files generated\n');
|
|
34
34
|
// Step 3: Format generated files
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
35
|
+
if (filledConfig.formatCommand !== undefined) {
|
|
36
|
+
echo('3. Formatting generated files...');
|
|
37
|
+
const fmtResult = await $(filledConfig.formatCommand, {
|
|
38
|
+
silent: filledConfig.silent,
|
|
39
|
+
});
|
|
40
|
+
if (Result.isErr(fmtResult)) {
|
|
41
|
+
throw new Error(`Formatting failed: ${fmtResult.value.message}`);
|
|
42
|
+
}
|
|
43
|
+
echo('✓ Formatting completed\n');
|
|
41
44
|
}
|
|
42
|
-
echo('✓ Formatting completed\n');
|
|
43
45
|
echo('✅ Index file generation completed successfully!\n');
|
|
44
46
|
}
|
|
45
47
|
catch (error) {
|
|
@@ -49,26 +51,37 @@ const genIndex = async (config) => {
|
|
|
49
51
|
};
|
|
50
52
|
/**
|
|
51
53
|
* Fills the configuration with default values.
|
|
54
|
+
* Default values:
|
|
55
|
+
* - sourceExtensions: ['.ts']
|
|
56
|
+
* - indexExtension: '.ts'
|
|
57
|
+
* - exportExtension: '.js'
|
|
58
|
+
* - excludePatterns: ['**\/*.{test,spec}.?(c|m)[jt]s?(x)']
|
|
59
|
+
* - silent: false
|
|
52
60
|
* @param config - The input configuration object.
|
|
53
61
|
* @returns The configuration object with all required properties filled with defaults.
|
|
54
62
|
*/
|
|
55
63
|
const fillConfig = (config) => {
|
|
56
|
-
const
|
|
57
|
-
const exportExtension = config.exportExtension ?? '.
|
|
64
|
+
const sourceExtensions = config.sourceExtensions ?? ['.ts'];
|
|
65
|
+
const exportExtension = config.exportExtension ?? '.js'; // For ESM imports, .mts resolves to .mjs
|
|
58
66
|
return {
|
|
59
67
|
formatCommand: config.formatCommand,
|
|
60
|
-
targetDirectory: config.targetDirectory
|
|
61
|
-
|
|
68
|
+
targetDirectory: ISet.create(isString(config.targetDirectory)
|
|
69
|
+
? [config.targetDirectory]
|
|
70
|
+
: config.targetDirectory),
|
|
71
|
+
excludePatterns: ISet.create(Arr.generate(function* () {
|
|
72
|
+
if (config.excludePatterns !== undefined) {
|
|
73
|
+
yield* config.excludePatterns;
|
|
74
|
+
}
|
|
75
|
+
yield '**/*.{test,spec}.?(c|m)[jt]s?(x)';
|
|
76
|
+
})),
|
|
77
|
+
sourceExtensions: ISet.create(sourceExtensions),
|
|
78
|
+
indexExtension: config.indexExtension ?? '.ts',
|
|
62
79
|
exportExtension,
|
|
63
|
-
excludePatterns: config.excludePatterns ?? [
|
|
64
|
-
`*.d${sourceExtension}`,
|
|
65
|
-
`*.test${sourceExtension}`,
|
|
66
|
-
],
|
|
67
80
|
silent: config.silent ?? false,
|
|
68
81
|
};
|
|
69
82
|
};
|
|
70
83
|
/**
|
|
71
|
-
* Generates an index.
|
|
84
|
+
* Generates an index.ts file for the given directory.
|
|
72
85
|
* Recursively calls itself for subdirectories.
|
|
73
86
|
* @param dirPath - The absolute path to the directory to process.
|
|
74
87
|
* @param config - The merged configuration object.
|
|
@@ -96,7 +109,7 @@ const generateIndexFileForDir = async (dirPath, config, baseDir) => {
|
|
|
96
109
|
}
|
|
97
110
|
}
|
|
98
111
|
const indexContent = generateIndexContent(subDirectories, filesToExport, config);
|
|
99
|
-
const indexPath = path.join(dirPath, `index${config.
|
|
112
|
+
const indexPath = path.join(dirPath, `index${config.indexExtension}`);
|
|
100
113
|
await fs.writeFile(indexPath, indexContent);
|
|
101
114
|
echo(`Generated: ${path.relative(process.cwd(), indexPath)}`);
|
|
102
115
|
}
|
|
@@ -106,18 +119,24 @@ const generateIndexFileForDir = async (dirPath, config, baseDir) => {
|
|
|
106
119
|
};
|
|
107
120
|
/**
|
|
108
121
|
* Determines if a file should be exported in the index file.
|
|
122
|
+
* A file is exported if:
|
|
123
|
+
* - It has one of the configured source extensions
|
|
124
|
+
* - It's not an index file itself
|
|
125
|
+
* - It doesn't match any exclusion patterns
|
|
109
126
|
* @param filePath - The relative path to the file from the target directory.
|
|
110
127
|
* @param config - The merged configuration object.
|
|
111
128
|
* @returns True if the file should be exported.
|
|
112
129
|
*/
|
|
113
130
|
const shouldExportFile = (filePath, config) => {
|
|
114
131
|
const fileName = path.basename(filePath);
|
|
132
|
+
const ext = path.extname(fileName);
|
|
115
133
|
// Must have the correct source extension
|
|
116
|
-
if (!
|
|
134
|
+
if (!config.sourceExtensions.has(ext)) {
|
|
117
135
|
return false;
|
|
118
136
|
}
|
|
119
137
|
// Don't export the index file itself
|
|
120
|
-
if (fileName
|
|
138
|
+
if (/^index\.[cm]?[jt]s[x]?$/u.test(fileName) // Matches index.ts, index.mts, index.js, index.tsx
|
|
139
|
+
) {
|
|
121
140
|
return false;
|
|
122
141
|
}
|
|
123
142
|
// Check against exclusion patterns
|
|
@@ -140,7 +159,7 @@ const generateIndexContent = (subDirectories, filesToExport, config) => {
|
|
|
140
159
|
const exportStatements = [
|
|
141
160
|
...subDirectories.map((subDir) => `export * from "./${subDir}/index${config.exportExtension}";`),
|
|
142
161
|
...filesToExport.map((file) => {
|
|
143
|
-
const fileNameWithoutExt = path.basename(file,
|
|
162
|
+
const fileNameWithoutExt = path.basename(file, path.extname(file));
|
|
144
163
|
return `export * from "./${fileNameWithoutExt}${config.exportExtension}";`;
|
|
145
164
|
}),
|
|
146
165
|
];
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"gen-index.mjs","sources":["../../src/functions/gen-index.mts"],"sourcesContent":[null],"names":[],"mappings":";;;;;
|
|
1
|
+
{"version":3,"file":"gen-index.mjs","sources":["../../src/functions/gen-index.mts"],"sourcesContent":[null],"names":[],"mappings":"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"}
|
package/dist/index.d.mts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.mts","sourceRoot":"","sources":["../src/index.mts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.d.mts","sourceRoot":"","sources":["../src/index.mts"],"names":[],"mappings":"AAEA,cAAc,uBAAuB,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ts-repo-utils",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "5.0.0",
|
|
4
4
|
"private": false,
|
|
5
5
|
"keywords": [
|
|
6
6
|
"typescript"
|
|
@@ -21,8 +21,8 @@
|
|
|
21
21
|
}
|
|
22
22
|
}
|
|
23
23
|
},
|
|
24
|
-
"module": "./dist/index.
|
|
25
|
-
"types": "./dist/index.d.
|
|
24
|
+
"module": "./dist/index.mjs",
|
|
25
|
+
"types": "./dist/index.d.mts",
|
|
26
26
|
"files": [
|
|
27
27
|
"src",
|
|
28
28
|
"dist",
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import micromatch from 'micromatch';
|
|
2
|
-
import { Result } from 'ts-data-forge';
|
|
2
|
+
import { Arr, ISet, isString, Result } from 'ts-data-forge';
|
|
3
3
|
import '../node-global.mjs';
|
|
4
4
|
import { assertPathExists } from './assert-path-exists.mjs';
|
|
5
5
|
|
|
@@ -7,27 +7,40 @@ import { assertPathExists } from './assert-path-exists.mjs';
|
|
|
7
7
|
* Configuration for index file generation.
|
|
8
8
|
*/
|
|
9
9
|
export type GenIndexConfig = DeepReadonly<{
|
|
10
|
-
/** Command to run for formatting generated files (default: 'npm run fmt') */
|
|
11
|
-
formatCommand: string;
|
|
12
|
-
|
|
13
10
|
/** Target directories to generate index files for (string or array of strings) */
|
|
14
|
-
targetDirectory: string | string[];
|
|
11
|
+
targetDirectory: string | readonly string[];
|
|
12
|
+
|
|
13
|
+
/** Glob patterns of files to exclude from exports (default: excludes `'**\/*.{test,spec}.?(c|m)[jt]s?(x)'`) */
|
|
14
|
+
excludePatterns?: readonly string[];
|
|
15
15
|
|
|
16
|
-
/** File
|
|
17
|
-
|
|
16
|
+
/** File extensions of source files to export (default: ['.ts', '.tsx']) */
|
|
17
|
+
sourceExtensions?: readonly `.${string}`[];
|
|
18
18
|
|
|
19
|
-
/** File extension
|
|
19
|
+
/** File extension of index files to generate (default: '.ts') */
|
|
20
|
+
indexExtension?: `.${string}`;
|
|
21
|
+
|
|
22
|
+
/** File extension to use in export statements (default: '.js') */
|
|
20
23
|
exportExtension?: `.${string}`;
|
|
21
24
|
|
|
22
|
-
/**
|
|
23
|
-
|
|
25
|
+
/** Command to run for formatting generated files (default: 'npm run fmt') */
|
|
26
|
+
formatCommand?: string;
|
|
24
27
|
|
|
25
28
|
/** Whether to suppress output during execution (default: false) */
|
|
26
29
|
silent?: boolean;
|
|
27
30
|
}>;
|
|
28
31
|
|
|
32
|
+
type GenIndexConfigInternal = DeepReadonly<{
|
|
33
|
+
formatCommand: string | undefined;
|
|
34
|
+
targetDirectory: ISet<string>;
|
|
35
|
+
excludePatterns: ISet<string>;
|
|
36
|
+
sourceExtensions: ISet<`.${string}`>;
|
|
37
|
+
indexExtension: `.${string}`;
|
|
38
|
+
exportExtension: `.${string}`;
|
|
39
|
+
silent: boolean;
|
|
40
|
+
}>;
|
|
41
|
+
|
|
29
42
|
/**
|
|
30
|
-
* Generates index.
|
|
43
|
+
* Generates index.ts files recursively in `config.targetDirectory`.
|
|
31
44
|
* @param config - Configuration for index file generation
|
|
32
45
|
* @throws Error if any step fails.
|
|
33
46
|
*/
|
|
@@ -35,7 +48,7 @@ export const genIndex = async (config: GenIndexConfig): Promise<void> => {
|
|
|
35
48
|
echo('Starting index file generation...\n');
|
|
36
49
|
|
|
37
50
|
// Merge config with defaults
|
|
38
|
-
const filledConfig:
|
|
51
|
+
const filledConfig: GenIndexConfigInternal = fillConfig(config);
|
|
39
52
|
|
|
40
53
|
// Normalize target directories to array
|
|
41
54
|
const targetDirs =
|
|
@@ -61,14 +74,16 @@ export const genIndex = async (config: GenIndexConfig): Promise<void> => {
|
|
|
61
74
|
echo('✓ Index files generated\n');
|
|
62
75
|
|
|
63
76
|
// Step 3: Format generated files
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
77
|
+
if (filledConfig.formatCommand !== undefined) {
|
|
78
|
+
echo('3. Formatting generated files...');
|
|
79
|
+
const fmtResult = await $(filledConfig.formatCommand, {
|
|
80
|
+
silent: filledConfig.silent,
|
|
81
|
+
});
|
|
82
|
+
if (Result.isErr(fmtResult)) {
|
|
83
|
+
throw new Error(`Formatting failed: ${fmtResult.value.message}`);
|
|
84
|
+
}
|
|
85
|
+
echo('✓ Formatting completed\n');
|
|
70
86
|
}
|
|
71
|
-
echo('✓ Formatting completed\n');
|
|
72
87
|
|
|
73
88
|
echo('✅ Index file generation completed successfully!\n');
|
|
74
89
|
} catch (error) {
|
|
@@ -79,28 +94,43 @@ export const genIndex = async (config: GenIndexConfig): Promise<void> => {
|
|
|
79
94
|
|
|
80
95
|
/**
|
|
81
96
|
* Fills the configuration with default values.
|
|
97
|
+
* Default values:
|
|
98
|
+
* - sourceExtensions: ['.ts']
|
|
99
|
+
* - indexExtension: '.ts'
|
|
100
|
+
* - exportExtension: '.js'
|
|
101
|
+
* - excludePatterns: ['**\/*.{test,spec}.?(c|m)[jt]s?(x)']
|
|
102
|
+
* - silent: false
|
|
82
103
|
* @param config - The input configuration object.
|
|
83
104
|
* @returns The configuration object with all required properties filled with defaults.
|
|
84
105
|
*/
|
|
85
|
-
const fillConfig = (config: GenIndexConfig):
|
|
86
|
-
const
|
|
87
|
-
const exportExtension = config.exportExtension ?? '.
|
|
106
|
+
const fillConfig = (config: GenIndexConfig): GenIndexConfigInternal => {
|
|
107
|
+
const sourceExtensions = config.sourceExtensions ?? ['.ts'];
|
|
108
|
+
const exportExtension = config.exportExtension ?? '.js'; // For ESM imports, .mts resolves to .mjs
|
|
88
109
|
|
|
89
110
|
return {
|
|
90
111
|
formatCommand: config.formatCommand,
|
|
91
|
-
targetDirectory:
|
|
92
|
-
|
|
112
|
+
targetDirectory: ISet.create(
|
|
113
|
+
isString(config.targetDirectory)
|
|
114
|
+
? [config.targetDirectory]
|
|
115
|
+
: config.targetDirectory,
|
|
116
|
+
),
|
|
117
|
+
excludePatterns: ISet.create(
|
|
118
|
+
Arr.generate(function* () {
|
|
119
|
+
if (config.excludePatterns !== undefined) {
|
|
120
|
+
yield* config.excludePatterns;
|
|
121
|
+
}
|
|
122
|
+
yield '**/*.{test,spec}.?(c|m)[jt]s?(x)';
|
|
123
|
+
}),
|
|
124
|
+
),
|
|
125
|
+
sourceExtensions: ISet.create(sourceExtensions),
|
|
126
|
+
indexExtension: config.indexExtension ?? '.ts',
|
|
93
127
|
exportExtension,
|
|
94
|
-
excludePatterns: config.excludePatterns ?? [
|
|
95
|
-
`*.d${sourceExtension}`,
|
|
96
|
-
`*.test${sourceExtension}`,
|
|
97
|
-
],
|
|
98
128
|
silent: config.silent ?? false,
|
|
99
129
|
};
|
|
100
130
|
};
|
|
101
131
|
|
|
102
132
|
/**
|
|
103
|
-
* Generates an index.
|
|
133
|
+
* Generates an index.ts file for the given directory.
|
|
104
134
|
* Recursively calls itself for subdirectories.
|
|
105
135
|
* @param dirPath - The absolute path to the directory to process.
|
|
106
136
|
* @param config - The merged configuration object.
|
|
@@ -109,11 +139,7 @@ const fillConfig = (config: GenIndexConfig): DeepRequired<GenIndexConfig> => {
|
|
|
109
139
|
*/
|
|
110
140
|
const generateIndexFileForDir = async (
|
|
111
141
|
dirPath: string,
|
|
112
|
-
config:
|
|
113
|
-
sourceExtension: `.${string}`;
|
|
114
|
-
exportExtension: `.${string}`;
|
|
115
|
-
excludePatterns: string[];
|
|
116
|
-
}>,
|
|
142
|
+
config: GenIndexConfigInternal,
|
|
117
143
|
baseDir?: string,
|
|
118
144
|
): Promise<void> => {
|
|
119
145
|
try {
|
|
@@ -144,7 +170,7 @@ const generateIndexFileForDir = async (
|
|
|
144
170
|
config,
|
|
145
171
|
);
|
|
146
172
|
|
|
147
|
-
const indexPath = path.join(dirPath, `index${config.
|
|
173
|
+
const indexPath = path.join(dirPath, `index${config.indexExtension}`);
|
|
148
174
|
|
|
149
175
|
await fs.writeFile(indexPath, indexContent);
|
|
150
176
|
echo(`Generated: ${path.relative(process.cwd(), indexPath)}`);
|
|
@@ -157,26 +183,31 @@ const generateIndexFileForDir = async (
|
|
|
157
183
|
|
|
158
184
|
/**
|
|
159
185
|
* Determines if a file should be exported in the index file.
|
|
186
|
+
* A file is exported if:
|
|
187
|
+
* - It has one of the configured source extensions
|
|
188
|
+
* - It's not an index file itself
|
|
189
|
+
* - It doesn't match any exclusion patterns
|
|
160
190
|
* @param filePath - The relative path to the file from the target directory.
|
|
161
191
|
* @param config - The merged configuration object.
|
|
162
192
|
* @returns True if the file should be exported.
|
|
163
193
|
*/
|
|
164
194
|
const shouldExportFile = (
|
|
165
195
|
filePath: string,
|
|
166
|
-
config:
|
|
167
|
-
sourceExtension: `.${string}`;
|
|
168
|
-
excludePatterns: string[];
|
|
169
|
-
}>,
|
|
196
|
+
config: GenIndexConfigInternal,
|
|
170
197
|
): boolean => {
|
|
171
198
|
const fileName = path.basename(filePath);
|
|
172
199
|
|
|
200
|
+
const ext = path.extname(fileName);
|
|
201
|
+
|
|
173
202
|
// Must have the correct source extension
|
|
174
|
-
if (!
|
|
203
|
+
if (!config.sourceExtensions.has(ext)) {
|
|
175
204
|
return false;
|
|
176
205
|
}
|
|
177
206
|
|
|
178
207
|
// Don't export the index file itself
|
|
179
|
-
if (
|
|
208
|
+
if (
|
|
209
|
+
/^index\.[cm]?[jt]s[x]?$/u.test(fileName) // Matches index.ts, index.mts, index.js, index.tsx
|
|
210
|
+
) {
|
|
180
211
|
return false;
|
|
181
212
|
}
|
|
182
213
|
|
|
@@ -203,17 +234,14 @@ const shouldExportFile = (
|
|
|
203
234
|
const generateIndexContent = (
|
|
204
235
|
subDirectories: readonly string[],
|
|
205
236
|
filesToExport: readonly string[],
|
|
206
|
-
config:
|
|
207
|
-
sourceExtension: string;
|
|
208
|
-
exportExtension: `.${string}`;
|
|
209
|
-
}>,
|
|
237
|
+
config: GenIndexConfigInternal,
|
|
210
238
|
): string => {
|
|
211
239
|
const exportStatements = [
|
|
212
240
|
...subDirectories.map(
|
|
213
241
|
(subDir) => `export * from "./${subDir}/index${config.exportExtension}";`,
|
|
214
242
|
),
|
|
215
243
|
...filesToExport.map((file) => {
|
|
216
|
-
const fileNameWithoutExt = path.basename(file,
|
|
244
|
+
const fileNameWithoutExt = path.basename(file, path.extname(file));
|
|
217
245
|
|
|
218
246
|
return `export * from "./${fileNameWithoutExt}${config.exportExtension}";`;
|
|
219
247
|
}),
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
describe('index file regex', () => {
|
|
2
|
+
const reg = /^index\.[cm]?[jt]s[x]?$/u;
|
|
3
|
+
|
|
4
|
+
test.each([
|
|
5
|
+
['index.ts', true],
|
|
6
|
+
['index.js', true],
|
|
7
|
+
['index.mts', true],
|
|
8
|
+
['index.mjs', true],
|
|
9
|
+
['index.cts', true],
|
|
10
|
+
['index.cjs', true],
|
|
11
|
+
['index.tsx', true],
|
|
12
|
+
['index.jsx', true],
|
|
13
|
+
['not-index.ts', false],
|
|
14
|
+
['index.txt', false],
|
|
15
|
+
] as const)('reg.test($0) to be $1', (fileName, expected) => {
|
|
16
|
+
expect(reg.test(fileName)).toBe(expected);
|
|
17
|
+
});
|
|
18
|
+
});
|
package/src/index.mts
CHANGED
package/dist/globals.d.mjs
DELETED
package/dist/globals.d.mjs.map
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"globals.d.mjs","sources":[],"sourcesContent":[],"names":[],"mappings":""}
|
package/dist/globals.d.mts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
/// <reference types="ts-type-forge" />
|
package/src/globals.d.mts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
/// <reference types="ts-type-forge" />
|