218 lines
9.1 KiB
JavaScript
218 lines
9.1 KiB
JavaScript
"use strict";
|
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
exports.createSwcOptions = exports.targetMapping = exports.create = void 0;
|
|
const ts_internals_1 = require("../ts-internals");
|
|
function create(createOptions) {
|
|
const { swc, service: { config, projectLocalResolveHelper }, transpilerConfigLocalResolveHelper, nodeModuleEmitKind, } = createOptions;
|
|
// Load swc compiler
|
|
let swcInstance;
|
|
// Used later in diagnostics; merely needs to be human-readable.
|
|
let swcDepName = 'swc';
|
|
if (typeof swc === 'string') {
|
|
swcDepName = swc;
|
|
swcInstance = require(transpilerConfigLocalResolveHelper(swc, true));
|
|
}
|
|
else if (swc == null) {
|
|
let swcResolved;
|
|
try {
|
|
swcDepName = '@swc/core';
|
|
swcResolved = transpilerConfigLocalResolveHelper(swcDepName, true);
|
|
}
|
|
catch (e) {
|
|
try {
|
|
swcDepName = '@swc/wasm';
|
|
swcResolved = transpilerConfigLocalResolveHelper(swcDepName, true);
|
|
}
|
|
catch (e) {
|
|
throw new Error('swc compiler requires either @swc/core or @swc/wasm to be installed as a dependency. See https://typestrong.org/ts-node/docs/transpilers');
|
|
}
|
|
}
|
|
swcInstance = require(swcResolved);
|
|
}
|
|
else {
|
|
swcInstance = swc;
|
|
}
|
|
// Prepare SWC options derived from typescript compiler options
|
|
const { nonTsxOptions, tsxOptions } = createSwcOptions(config.options, nodeModuleEmitKind, swcInstance, swcDepName);
|
|
const transpile = (input, transpileOptions) => {
|
|
const { fileName } = transpileOptions;
|
|
const swcOptions = fileName.endsWith('.tsx') || fileName.endsWith('.jsx') ? tsxOptions : nonTsxOptions;
|
|
const { code, map } = swcInstance.transformSync(input, {
|
|
...swcOptions,
|
|
filename: fileName,
|
|
});
|
|
return { outputText: code, sourceMapText: map };
|
|
};
|
|
return {
|
|
transpile,
|
|
};
|
|
}
|
|
exports.create = create;
|
|
/** @internal */
|
|
exports.targetMapping = new Map();
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES3 */ 0, 'es3');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES5 */ 1, 'es5');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2015 */ 2, 'es2015');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2016 */ 3, 'es2016');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2017 */ 4, 'es2017');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2018 */ 5, 'es2018');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2019 */ 6, 'es2019');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2020 */ 7, 'es2020');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2021 */ 8, 'es2021');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ES2022 */ 9, 'es2022');
|
|
exports.targetMapping.set(/* ts.ScriptTarget.ESNext */ 99, 'esnext');
|
|
/**
|
|
* @internal
|
|
* We use this list to downgrade to a prior target when we probe swc to detect if it supports a particular target
|
|
*/
|
|
const swcTargets = [
|
|
'es3',
|
|
'es5',
|
|
'es2015',
|
|
'es2016',
|
|
'es2017',
|
|
'es2018',
|
|
'es2019',
|
|
'es2020',
|
|
'es2021',
|
|
'es2022',
|
|
'esnext',
|
|
];
|
|
const ModuleKind = {
|
|
None: 0,
|
|
CommonJS: 1,
|
|
AMD: 2,
|
|
UMD: 3,
|
|
System: 4,
|
|
ES2015: 5,
|
|
ES2020: 6,
|
|
ESNext: 99,
|
|
Node16: 100,
|
|
NodeNext: 199,
|
|
};
|
|
const JsxEmit = {
|
|
ReactJSX: /* ts.JsxEmit.ReactJSX */ 4,
|
|
ReactJSXDev: /* ts.JsxEmit.ReactJSXDev */ 5,
|
|
};
|
|
/**
|
|
* Prepare SWC options derived from typescript compiler options.
|
|
* @internal exported for testing
|
|
*/
|
|
function createSwcOptions(compilerOptions, nodeModuleEmitKind, swcInstance, swcDepName) {
|
|
var _a;
|
|
const { esModuleInterop, sourceMap, importHelpers, experimentalDecorators, emitDecoratorMetadata, target, module, jsx, jsxFactory, jsxFragmentFactory, strict, alwaysStrict, noImplicitUseStrict, jsxImportSource, } = compilerOptions;
|
|
let swcTarget = (_a = exports.targetMapping.get(target)) !== null && _a !== void 0 ? _a : 'es3';
|
|
// Downgrade to lower target if swc does not support the selected target.
|
|
// Perhaps project has an older version of swc.
|
|
// TODO cache the results of this; slightly faster
|
|
let swcTargetIndex = swcTargets.indexOf(swcTarget);
|
|
for (; swcTargetIndex >= 0; swcTargetIndex--) {
|
|
try {
|
|
swcInstance.transformSync('', {
|
|
jsc: { target: swcTargets[swcTargetIndex] },
|
|
});
|
|
break;
|
|
}
|
|
catch (e) { }
|
|
}
|
|
swcTarget = swcTargets[swcTargetIndex];
|
|
const keepClassNames = target >= /* ts.ScriptTarget.ES2016 */ 3;
|
|
const isNodeModuleKind = module === ModuleKind.Node16 || module === ModuleKind.NodeNext;
|
|
// swc only supports these 4x module options [MUST_UPDATE_FOR_NEW_MODULEKIND]
|
|
const moduleType = module === ModuleKind.CommonJS
|
|
? 'commonjs'
|
|
: module === ModuleKind.AMD
|
|
? 'amd'
|
|
: module === ModuleKind.UMD
|
|
? 'umd'
|
|
: isNodeModuleKind && nodeModuleEmitKind === 'nodecjs'
|
|
? 'commonjs'
|
|
: isNodeModuleKind && nodeModuleEmitKind === 'nodeesm'
|
|
? 'es6'
|
|
: 'es6';
|
|
// In swc:
|
|
// strictMode means `"use strict"` is *always* emitted for non-ES module, *never* for ES module where it is assumed it can be omitted.
|
|
// (this assumption is invalid, but that's the way swc behaves)
|
|
// tsc is a bit more complex:
|
|
// alwaysStrict will force emitting it always unless `import`/`export` syntax is emitted which implies it per the JS spec.
|
|
// if not alwaysStrict, will emit implicitly whenever module target is non-ES *and* transformed module syntax is emitted.
|
|
// For node, best option is to assume that all scripts are modules (commonjs or esm) and thus should get tsc's implicit strict behavior.
|
|
// Always set strictMode, *unless* alwaysStrict is disabled and noImplicitUseStrict is enabled
|
|
const strictMode =
|
|
// if `alwaysStrict` is disabled, remembering that `strict` defaults `alwaysStrict` to true
|
|
(alwaysStrict === false || (alwaysStrict !== true && strict !== true)) &&
|
|
// if noImplicitUseStrict is enabled
|
|
noImplicitUseStrict === true
|
|
? false
|
|
: true;
|
|
const jsxRuntime = jsx === JsxEmit.ReactJSX || jsx === JsxEmit.ReactJSXDev ? 'automatic' : undefined;
|
|
const jsxDevelopment = jsx === JsxEmit.ReactJSXDev ? true : undefined;
|
|
const useDefineForClassFields = (0, ts_internals_1.getUseDefineForClassFields)(compilerOptions);
|
|
const nonTsxOptions = createVariant(false);
|
|
const tsxOptions = createVariant(true);
|
|
return { nonTsxOptions, tsxOptions };
|
|
function createVariant(isTsx) {
|
|
const swcOptions = {
|
|
sourceMaps: sourceMap,
|
|
// isModule: true,
|
|
module: moduleType
|
|
? {
|
|
type: moduleType,
|
|
...(moduleType === 'amd' || moduleType === 'commonjs' || moduleType === 'umd'
|
|
? {
|
|
noInterop: !esModuleInterop,
|
|
strictMode,
|
|
// For NodeNext and Node12, emit as CJS but do not transform dynamic imports
|
|
ignoreDynamic: nodeModuleEmitKind === 'nodecjs',
|
|
}
|
|
: {}),
|
|
}
|
|
: undefined,
|
|
swcrc: false,
|
|
jsc: {
|
|
externalHelpers: importHelpers,
|
|
parser: {
|
|
syntax: 'typescript',
|
|
tsx: isTsx,
|
|
decorators: experimentalDecorators,
|
|
dynamicImport: true,
|
|
importAssertions: true,
|
|
},
|
|
target: swcTarget,
|
|
transform: {
|
|
decoratorMetadata: emitDecoratorMetadata,
|
|
legacyDecorator: true,
|
|
react: {
|
|
throwIfNamespace: false,
|
|
development: jsxDevelopment,
|
|
useBuiltins: false,
|
|
pragma: jsxFactory,
|
|
pragmaFrag: jsxFragmentFactory,
|
|
runtime: jsxRuntime,
|
|
importSource: jsxImportSource,
|
|
},
|
|
useDefineForClassFields,
|
|
},
|
|
keepClassNames,
|
|
experimental: {
|
|
keepImportAttributes: true,
|
|
emitAssertForImportAttributes: true,
|
|
},
|
|
},
|
|
};
|
|
// Throw a helpful error if swc version is old, for example, if it rejects `ignoreDynamic`
|
|
try {
|
|
swcInstance.transformSync('', swcOptions);
|
|
}
|
|
catch (e) {
|
|
throw new Error(`${swcDepName} threw an error when attempting to validate swc compiler options.\n` +
|
|
'You may be using an old version of swc which does not support the options used by ts-node.\n' +
|
|
'Try upgrading to the latest version of swc.\n' +
|
|
'Error message from swc:\n' +
|
|
(e === null || e === void 0 ? void 0 : e.message));
|
|
}
|
|
return swcOptions;
|
|
}
|
|
}
|
|
exports.createSwcOptions = createSwcOptions;
|
|
//# sourceMappingURL=swc.js.map
|