tsnite 0.0.5 → 0.0.6
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/cli.js +32 -132
- package/dist/loader.js +73 -0
- package/package.json +15 -18
- package/dist/builders/swc.js +0 -43
- package/dist/common/constants.js +0 -6
- package/dist/utils/gradient.js +0 -36
- package/dist/utils/tsconfig-loader.js +0 -13
package/dist/cli.js
CHANGED
|
@@ -1,13 +1,11 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import { program } from 'commander';
|
|
3
3
|
import { join } from 'node:path';
|
|
4
|
-
import { readdir, stat, rm, mkdir, cp, symlink } from 'node:fs/promises';
|
|
5
4
|
import { fork } from 'node:child_process';
|
|
6
5
|
import { watch } from 'chokidar';
|
|
7
|
-
import {
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
import { gradient } from './utils/gradient.js';
|
|
6
|
+
import { createRequire } from 'node:module';
|
|
7
|
+
const require = createRequire(import.meta.dirname);
|
|
8
|
+
const { name, description, version } = require(join(import.meta.dirname, '..', 'package.json'));
|
|
11
9
|
program
|
|
12
10
|
.name(name)
|
|
13
11
|
.description(description)
|
|
@@ -18,137 +16,39 @@ program
|
|
|
18
16
|
.argument('<string>', 'Entrypoint file')
|
|
19
17
|
.argument('[args...]', 'Specify the Node.js command and any additional arguments')
|
|
20
18
|
.showSuggestionAfterError();
|
|
21
|
-
const events = new EventEmitter();
|
|
22
|
-
const pids = new Set();
|
|
23
|
-
let starts = 0;
|
|
24
|
-
export async function* discover(path) {
|
|
25
|
-
const entries = await readdir(path);
|
|
26
|
-
const ignores = /^(?:node_modules|dist|coverage|tests|\..+|.*\.(?:spec|test)\.ts)$/;
|
|
27
|
-
for (const entry of entries) {
|
|
28
|
-
if (ignores.test(entry))
|
|
29
|
-
continue;
|
|
30
|
-
const stats = await stat(join(path, entry));
|
|
31
|
-
if (stats.isDirectory()) {
|
|
32
|
-
yield* discover(join(path, entry));
|
|
33
|
-
continue;
|
|
34
|
-
}
|
|
35
|
-
yield join(path, entry);
|
|
36
|
-
}
|
|
37
|
-
}
|
|
38
19
|
async function handler() {
|
|
39
20
|
const options = program.opts();
|
|
40
21
|
const [entry, nodeArgs] = program.processedArgs;
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
pids.add(pid);
|
|
70
|
-
process.stdout.write(`\x1b[1m${gradient(['#5e23e6', '#f88bc7'])(`➤ Compiled successfully in ${(ends - starts).toFixed(2)}ms`)}\x1b[0m\n`);
|
|
71
|
-
}
|
|
72
|
-
catch (err) {
|
|
73
|
-
process.stdout.write(`\x1b${gradient(['#cf4444', '#9b1e1e'])(`❌ Failed to compile!\n`)}\x1b[0m\n${err}`);
|
|
74
|
-
}
|
|
75
|
-
if (options.watch) {
|
|
76
|
-
const watcher = watch(join(process.cwd(), options.sourceRoot), {
|
|
77
|
-
atomic: true,
|
|
78
|
-
ignoreInitial: true,
|
|
79
|
-
ignored: [/.+\.(?:test|spec)\.ts$/i]
|
|
80
|
-
});
|
|
81
|
-
watcher.on('change', async function (path) {
|
|
82
|
-
process.stdout.write('\x1Bc');
|
|
83
|
-
starts = performance.now();
|
|
84
|
-
try {
|
|
85
|
-
if (!path.endsWith('.ts') && options.includeAssets) {
|
|
86
|
-
await cp(path, join(outDir, path.replace(join(process.cwd(), options.sourceRoot, '/'), '')), { force: true, recursive: true });
|
|
87
|
-
return;
|
|
88
|
-
}
|
|
89
|
-
await compile(path, options.sourceRoot);
|
|
90
|
-
events.emit('ready');
|
|
91
|
-
}
|
|
92
|
-
catch (err) {
|
|
93
|
-
process.stdout.write(`\x1b${gradient(['#cf4444', '#9b1e1e'])(`❌ Failed to compile!\n`)}\x1b[0m\n${err}`);
|
|
94
|
-
}
|
|
95
|
-
});
|
|
96
|
-
watcher.on('add', async function (path) {
|
|
97
|
-
process.stdout.write('\x1Bc');
|
|
98
|
-
starts = performance.now();
|
|
99
|
-
try {
|
|
100
|
-
if (!path.endsWith('.ts') && options.includeAssets) {
|
|
101
|
-
await cp(path, join(outDir, path.replace(join(process.cwd(), options.sourceRoot, '/'), '')), { force: true, recursive: true });
|
|
102
|
-
return;
|
|
103
|
-
}
|
|
104
|
-
await compile(path, options.sourceRoot);
|
|
105
|
-
events.emit('ready');
|
|
106
|
-
}
|
|
107
|
-
catch (err) {
|
|
108
|
-
process.stdout.write(`\x1b${gradient(['#cf4444', '#9b1e1e'])(`❌ Failed to compile!\n`)}\x1b[0m\n${err}`);
|
|
109
|
-
}
|
|
110
|
-
});
|
|
111
|
-
watcher.on('unlink', async function (path) {
|
|
112
|
-
process.stdout.write('\x1Bc');
|
|
113
|
-
starts = performance.now();
|
|
114
|
-
try {
|
|
115
|
-
await rm(join(outDir, path.replace(join(process.cwd(), options.sourceRoot, '/'), '')), {
|
|
116
|
-
force: true,
|
|
117
|
-
recursive: true
|
|
118
|
-
});
|
|
119
|
-
events.emit('ready');
|
|
120
|
-
}
|
|
121
|
-
catch (err) {
|
|
122
|
-
console.error(err);
|
|
123
|
-
}
|
|
124
|
-
});
|
|
125
|
-
events.on('ready', async function () {
|
|
126
|
-
try {
|
|
127
|
-
for (const pid of pids.values()) {
|
|
128
|
-
try {
|
|
129
|
-
process.kill(pid);
|
|
130
|
-
pids.delete(pid);
|
|
131
|
-
}
|
|
132
|
-
catch {
|
|
133
|
-
pids.delete(pid);
|
|
134
|
-
}
|
|
135
|
-
}
|
|
136
|
-
const ends = performance.now();
|
|
137
|
-
const entrypoint = entry
|
|
138
|
-
.replace(join(options.sourceRoot, '/'), '')
|
|
139
|
-
.replace(/(.+).ts$/, '$1.js');
|
|
140
|
-
const { pid } = fork(join(outDir, entrypoint), {
|
|
141
|
-
execArgv: ['--enable-source-maps', ...nodeArgs],
|
|
142
|
-
stdio: 'inherit'
|
|
143
|
-
});
|
|
144
|
-
pids.add(pid);
|
|
145
|
-
process.stdout.write(`\x1b[1m${gradient(['#5e23e6', '#f88bc7'])(`› Compiled successfully in ${(ends - starts).toFixed(2)}ms`)}\x1b[0m\n`);
|
|
146
|
-
}
|
|
147
|
-
catch (err) {
|
|
148
|
-
console.error(err);
|
|
149
|
-
}
|
|
22
|
+
fork(join(process.cwd(), entry), {
|
|
23
|
+
stdio: 'inherit',
|
|
24
|
+
execArgv: [
|
|
25
|
+
'--enable-source-maps',
|
|
26
|
+
'--no-experimental-strip-types',
|
|
27
|
+
'--import',
|
|
28
|
+
`data:text/javascript,import { register } from "node:module"; import { pathToFileURL } from "node:url"; register("./dist/loader.js", pathToFileURL("./"));`,
|
|
29
|
+
...nodeArgs
|
|
30
|
+
]
|
|
31
|
+
});
|
|
32
|
+
if (!options.watch)
|
|
33
|
+
return;
|
|
34
|
+
const watcher = watch('.', {
|
|
35
|
+
atomic: true,
|
|
36
|
+
ignoreInitial: true,
|
|
37
|
+
ignored: [/.+\.(?:test|spec)\.ts$/i]
|
|
38
|
+
});
|
|
39
|
+
watcher.on('change', async function () {
|
|
40
|
+
process.stdout.write('\x1Bc');
|
|
41
|
+
fork(join(process.cwd(), entry), {
|
|
42
|
+
stdio: 'inherit',
|
|
43
|
+
execArgv: [
|
|
44
|
+
'--enable-source-maps',
|
|
45
|
+
'--no-experimental-strip-types',
|
|
46
|
+
'--import',
|
|
47
|
+
`data:text/javascript,import { register } from "node:module"; import { pathToFileURL } from "node:url"; register("./dist/loader.js", pathToFileURL("./"));`,
|
|
48
|
+
...nodeArgs
|
|
49
|
+
]
|
|
150
50
|
});
|
|
151
|
-
}
|
|
51
|
+
});
|
|
152
52
|
}
|
|
153
53
|
program.action(handler);
|
|
154
54
|
program.parse(process.argv);
|
package/dist/loader.js
ADDED
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
import { transformFile } from '@swc/core';
|
|
2
|
+
import { fileURLToPath, pathToFileURL } from 'node:url';
|
|
3
|
+
import { existsSync } from 'node:fs';
|
|
4
|
+
import path from 'node:path';
|
|
5
|
+
export async function resolve(specifier, ctx, next) {
|
|
6
|
+
if (!specifier.startsWith('.') && !specifier.startsWith('/')) {
|
|
7
|
+
return next(specifier, ctx);
|
|
8
|
+
}
|
|
9
|
+
const parentPath = fileURLToPath(ctx.parentURL);
|
|
10
|
+
const parentDir = path.dirname(parentPath);
|
|
11
|
+
const basePath = path.resolve(parentDir, specifier);
|
|
12
|
+
const tryFiles = [
|
|
13
|
+
basePath,
|
|
14
|
+
basePath + '.ts',
|
|
15
|
+
basePath + '.tsx',
|
|
16
|
+
basePath + '.js',
|
|
17
|
+
basePath + '.mjs',
|
|
18
|
+
path.join(basePath, 'index.ts'),
|
|
19
|
+
path.join(basePath, 'index.tsx'),
|
|
20
|
+
path.join(basePath, 'index.js'),
|
|
21
|
+
path.join(basePath, 'index.mjs')
|
|
22
|
+
];
|
|
23
|
+
for (const file of tryFiles) {
|
|
24
|
+
if (existsSync(file)) {
|
|
25
|
+
return {
|
|
26
|
+
url: pathToFileURL(file).href,
|
|
27
|
+
format: 'module',
|
|
28
|
+
shortCircuit: true
|
|
29
|
+
};
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
export async function load(url, ctx, next) {
|
|
34
|
+
if (!url.startsWith('file://') || !url.endsWith('.ts')) {
|
|
35
|
+
return next(url, ctx);
|
|
36
|
+
}
|
|
37
|
+
const filename = fileURLToPath(url);
|
|
38
|
+
const { code } = await transformFile(filename, {
|
|
39
|
+
filename,
|
|
40
|
+
jsc: {
|
|
41
|
+
baseUrl: import.meta.dirname,
|
|
42
|
+
parser: {
|
|
43
|
+
syntax: 'typescript',
|
|
44
|
+
tsx: false,
|
|
45
|
+
decorators: true
|
|
46
|
+
},
|
|
47
|
+
target: 'es2022',
|
|
48
|
+
keepClassNames: true,
|
|
49
|
+
experimental: {
|
|
50
|
+
emitAssertForImportAttributes: true
|
|
51
|
+
},
|
|
52
|
+
transform: {
|
|
53
|
+
decoratorMetadata: true,
|
|
54
|
+
legacyDecorator: true,
|
|
55
|
+
react: {
|
|
56
|
+
runtime: 'automatic',
|
|
57
|
+
development: true
|
|
58
|
+
}
|
|
59
|
+
},
|
|
60
|
+
paths: {
|
|
61
|
+
'#/*': ['./src/*']
|
|
62
|
+
}
|
|
63
|
+
},
|
|
64
|
+
module: {
|
|
65
|
+
type: 'es6',
|
|
66
|
+
strict: true,
|
|
67
|
+
outFileExtension: 'ts',
|
|
68
|
+
resolveFully: true
|
|
69
|
+
},
|
|
70
|
+
sourceMaps: 'inline'
|
|
71
|
+
});
|
|
72
|
+
return { format: 'module', source: code, shortCircuit: true };
|
|
73
|
+
}
|
package/package.json
CHANGED
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
"nodejs",
|
|
9
9
|
"typescript"
|
|
10
10
|
],
|
|
11
|
-
"version": "0.0.
|
|
11
|
+
"version": "0.0.6",
|
|
12
12
|
"type": "module",
|
|
13
13
|
"bin": {
|
|
14
14
|
"tsnite": "dist/cli.js"
|
|
@@ -26,39 +26,36 @@
|
|
|
26
26
|
"prepare": "husky"
|
|
27
27
|
},
|
|
28
28
|
"dependencies": {
|
|
29
|
-
"@swc/core": "^1.
|
|
29
|
+
"@swc/core": "^1.14.0",
|
|
30
30
|
"chokidar": "^4.0.3",
|
|
31
|
-
"commander": "^14.0.
|
|
31
|
+
"commander": "^14.0.2",
|
|
32
32
|
"json5": "^2.2.3"
|
|
33
33
|
},
|
|
34
34
|
"devDependencies": {
|
|
35
|
-
"@commitlint/cli": "^
|
|
36
|
-
"@commitlint/config-conventional": "^
|
|
37
|
-
"@eslint/js": "^9.
|
|
38
|
-
"@jest/globals": "^30.
|
|
35
|
+
"@commitlint/cli": "^20.1.0",
|
|
36
|
+
"@commitlint/config-conventional": "^20.0.0",
|
|
37
|
+
"@eslint/js": "^9.38.0",
|
|
38
|
+
"@jest/globals": "^30.2.0",
|
|
39
39
|
"@swc/jest": "^0.2.39",
|
|
40
|
-
"eslint": "^9.
|
|
40
|
+
"eslint": "^9.38.0",
|
|
41
41
|
"eslint-plugin-jest": "^29.0.1",
|
|
42
42
|
"eslint-plugin-prettier": "^5.5.4",
|
|
43
|
-
"globals": "^16.
|
|
43
|
+
"globals": "^16.4.0",
|
|
44
44
|
"husky": "^9.1.7",
|
|
45
|
-
"jest": "^30.
|
|
46
|
-
"jest-environment-node": "^30.
|
|
45
|
+
"jest": "^30.2.0",
|
|
46
|
+
"jest-environment-node": "^30.2.0",
|
|
47
47
|
"jest-mock-extended": "^4.0.0",
|
|
48
|
-
"lint-staged": "^16.
|
|
48
|
+
"lint-staged": "^16.2.6",
|
|
49
49
|
"prettier": "^3.6.2",
|
|
50
|
-
"rimraf": "^6.0
|
|
50
|
+
"rimraf": "^6.1.0",
|
|
51
51
|
"tsc-alias": "^1.8.16",
|
|
52
|
-
"typescript": "^5.9.
|
|
53
|
-
"typescript-eslint": "^8.
|
|
52
|
+
"typescript": "^5.9.3",
|
|
53
|
+
"typescript-eslint": "^8.46.2"
|
|
54
54
|
},
|
|
55
55
|
"author": {
|
|
56
56
|
"name": "Luciano Alves",
|
|
57
57
|
"url": "https://github.com/luas10c"
|
|
58
58
|
},
|
|
59
|
-
"engines": {
|
|
60
|
-
"node": "^20.9.0 || ^22.11.0"
|
|
61
|
-
},
|
|
62
59
|
"homepage": "https://github.com/luas10c/tsnite",
|
|
63
60
|
"repository": {
|
|
64
61
|
"type": "github",
|
package/dist/builders/swc.js
DELETED
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
import { transformFile } from '@swc/core';
|
|
2
|
-
import { mkdir, writeFile } from 'node:fs/promises';
|
|
3
|
-
import { join, parse } from 'node:path';
|
|
4
|
-
import { loadTsConfigPaths } from '../utils/tsconfig-loader.js';
|
|
5
|
-
import { outDir } from '../common/constants.js';
|
|
6
|
-
const paths = await loadTsConfigPaths();
|
|
7
|
-
export async function compile(filename, sourceRoot) {
|
|
8
|
-
const { code, map } = await transformFile(filename, {
|
|
9
|
-
jsc: {
|
|
10
|
-
baseUrl: join(process.cwd(), '.'),
|
|
11
|
-
parser: {
|
|
12
|
-
syntax: 'typescript',
|
|
13
|
-
decorators: true
|
|
14
|
-
},
|
|
15
|
-
target: 'es2022',
|
|
16
|
-
keepClassNames: true,
|
|
17
|
-
transform: {
|
|
18
|
-
treatConstEnumAsEnum: true,
|
|
19
|
-
decoratorMetadata: true,
|
|
20
|
-
legacyDecorator: true
|
|
21
|
-
},
|
|
22
|
-
experimental: {
|
|
23
|
-
keepImportAssertions: true
|
|
24
|
-
},
|
|
25
|
-
paths
|
|
26
|
-
},
|
|
27
|
-
module: {
|
|
28
|
-
type: 'es6',
|
|
29
|
-
strict: true,
|
|
30
|
-
outFileExtension: 'js',
|
|
31
|
-
resolveFully: true
|
|
32
|
-
},
|
|
33
|
-
sourceMaps: true
|
|
34
|
-
});
|
|
35
|
-
const { dir, name } = parse(filename
|
|
36
|
-
.replace(join(process.cwd(), '/'), '')
|
|
37
|
-
.replace(join(sourceRoot, '/'), ''));
|
|
38
|
-
await mkdir(join(outDir, dir), { recursive: true });
|
|
39
|
-
await writeFile(join(outDir, dir, `${name}.js`), `${code}\n//# sourceMappingURL=${join(outDir, dir, `${name}.js.map`)}`);
|
|
40
|
-
if (map) {
|
|
41
|
-
await writeFile(join(outDir, dir, `${name}.js.map`), map);
|
|
42
|
-
}
|
|
43
|
-
}
|
package/dist/common/constants.js
DELETED
|
@@ -1,6 +0,0 @@
|
|
|
1
|
-
import { createRequire } from 'node:module';
|
|
2
|
-
import { tmpdir } from 'node:os';
|
|
3
|
-
import { join } from 'node:path';
|
|
4
|
-
const require = createRequire(import.meta.dirname);
|
|
5
|
-
export const { name, description, version } = require(join(import.meta.dirname, '..', '..', 'package.json'));
|
|
6
|
-
export const outDir = join(tmpdir(), name);
|
package/dist/utils/gradient.js
DELETED
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
function hexToRgb(hex) {
|
|
2
|
-
hex = hex.replace(/^#/, '');
|
|
3
|
-
if (hex.length === 3) {
|
|
4
|
-
hex = hex
|
|
5
|
-
.split('')
|
|
6
|
-
.map((c) => c + c)
|
|
7
|
-
.join('');
|
|
8
|
-
}
|
|
9
|
-
const num = parseInt(hex, 16);
|
|
10
|
-
return [num >> 16, (num >> 8) & 255, num & 255];
|
|
11
|
-
}
|
|
12
|
-
function rgbToAnsi([r, g, b]) {
|
|
13
|
-
return `\x1b[38;2;${r};${g};${b}m`;
|
|
14
|
-
}
|
|
15
|
-
export function gradient(colors) {
|
|
16
|
-
return function (text) {
|
|
17
|
-
if (colors.length < 2) {
|
|
18
|
-
throw new Error('gradient needs at least 2 colors');
|
|
19
|
-
}
|
|
20
|
-
const segments = colors.length - 1;
|
|
21
|
-
const length = text.length;
|
|
22
|
-
let result = '';
|
|
23
|
-
for (let i = 0; i < length; i++) {
|
|
24
|
-
const pos = (i / (length - 1)) * segments;
|
|
25
|
-
const segIndex = Math.min(Math.floor(pos), segments - 1);
|
|
26
|
-
const t = pos - segIndex;
|
|
27
|
-
const start = hexToRgb(colors[segIndex]);
|
|
28
|
-
const end = hexToRgb(colors[segIndex + 1]);
|
|
29
|
-
const r = Math.round(start[0] + (end[0] - start[0]) * t);
|
|
30
|
-
const g = Math.round(start[1] + (end[1] - start[1]) * t);
|
|
31
|
-
const b = Math.round(start[2] + (end[2] - start[2]) * t);
|
|
32
|
-
result += rgbToAnsi([r, g, b]) + text[i];
|
|
33
|
-
}
|
|
34
|
-
return result + '\x1b[0m';
|
|
35
|
-
};
|
|
36
|
-
}
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import { join } from 'node:path';
|
|
2
|
-
import { readFile } from 'node:fs/promises';
|
|
3
|
-
import json5 from 'json5';
|
|
4
|
-
export async function loadTsConfigPaths() {
|
|
5
|
-
try {
|
|
6
|
-
const data = await readFile(join(process.cwd(), 'tsconfig.json'), 'utf-8');
|
|
7
|
-
const { compilerOptions: { paths } } = json5.parse(data);
|
|
8
|
-
return paths;
|
|
9
|
-
}
|
|
10
|
-
catch {
|
|
11
|
-
return {};
|
|
12
|
-
}
|
|
13
|
-
}
|