-
-
Notifications
You must be signed in to change notification settings - Fork 1.4k
Description
Describe the bug
When handling code that has already been transformed by tsc with a generated source map swc will generate an incorrect source map that points to the incorrect locations in the original file.
Input code
src/typescript.ts
interface MyObject {
[key: string]: any;
}
let foo = 'foo';
let boo = 'boo';
let bar = 'bar';
let baz = 'baz';
foo += bar;
eval("function hi(name) { return `Hi ${name}` } hi('world!')");
const key: string = 'key';
const obj: MyObject = Object.create(null)
const dynamic = 'somedynamickey';
switch (key) {
case obj[dynamic]:
case dynamic:
case 'literal':
}
const abc = boo + baz;
const def = boo == baz;
const ghi = boo === baz;
const jkl = boo != baz;
const mno = boo !== baz;
const word = 'world';
const str = `hello ${word}`;tsconfig.json
{
"extends": "@tsconfig/node16/tsconfig.json",
"compilerOptions": {
"sourceMap": true,
"outDir": "./dist",
"rootDir": "./src",
},
"include": [
"src/**/*.ts"
],
}
dist/typescript.js
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
let foo = 'foo';
let boo = 'boo';
let bar = 'bar';
let baz = 'baz';
foo += bar;
eval("function hi(name) { return `Hi ${name}` } hi('world!')");
const key = 'key';
const obj = Object.create(null);
const dynamic = 'somedynamickey';
switch (key) {
case obj[dynamic]:
case dynamic:
case 'literal':
}
const abc = boo + baz;
const def = boo == baz;
const ghi = boo === baz;
const jkl = boo != baz;
const mno = boo !== baz;
const word = 'world';
const str = `hello ${word}`;
//# sourceMappingURL=typescript.js.mapdist/typescript.js.map
{"version":3,"file":"typescript.js","sourceRoot":"","sources":["../src/typescript.ts"],"names":[],"mappings":";;AAIA,IAAI,GAAG,GAAG,KAAK,CAAC;AAChB,IAAI,GAAG,GAAG,KAAK,CAAC;AAChB,IAAI,GAAG,GAAG,KAAK,CAAC;AAChB,IAAI,GAAG,GAAG,KAAK,CAAC;AAEhB,GAAG,IAAI,GAAG,CAAC;AAEX,IAAI,CAAC,wDAAwD,CAAC,CAAC;AAE/D,MAAM,GAAG,GAAW,KAAK,CAAC;AAC1B,MAAM,GAAG,GAAa,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAA;AACzC,MAAM,OAAO,GAAG,gBAAgB,CAAC;AAEjC,QAAQ,GAAG,EAAE,CAAC;IACZ,KAAK,GAAG,CAAC,OAAO,CAAC,CAAC;IAClB,KAAK,OAAO,CAAC;IACb,KAAK,SAAS,CAAC;AACjB,CAAC;AAED,MAAM,GAAG,GAAG,GAAG,GAAG,GAAG,CAAC;AACtB,MAAM,GAAG,GAAG,GAAG,IAAI,GAAG,CAAC;AACvB,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,CAAC;AACxB,MAAM,GAAG,GAAG,GAAG,IAAI,GAAG,CAAC;AACvB,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,CAAC;AAExB,MAAM,IAAI,GAAG,OAAO,CAAC;AACrB,MAAM,GAAG,GAAG,SAAS,IAAI,EAAE,CAAC"}Config
{
"env": {
"targets": {
"node": "20",
},
},
"jsc": { "minify": { "compress": { "defaults": false } } },
"minify": true,
"sourceMaps": true
}Link to the code that reproduces this issue
https://gist.github.com/tough-griff/e300d5d8020d59b8d89ad94cf56175c3
SWC Info output
Operating System:
Platform: darwin
Arch: arm64
Machine Type: arm64
Version: Darwin Kernel Version 24.5.0: Tue Apr 22 19:54:49 PDT 2025; root:xnu-11417.121.6~2/RELEASE_ARM64_T6000
CPU: (10 cores)
Models: Apple M1 Max
Binaries:
Node: 20.19.0
npm: 10.8.2
Yarn: N/A
pnpm: N/A
Relevant Packages:
@swc/core: 1.11.24
@swc/helpers: N/A
@swc/types: 0.1.21
typescript: 5.8.3
SWC Config:
output: N/A
.swcrc path: N/A
Next.js info:
output: N/A
Expected behavior
Actual behavior
While the source code is not visible, you can still see the error: the generated source map does not seem to handle the newlines in the typescript source correctly and puts the first span from a newline on the previous code line:
This leads to further errors when implementing a transform plugin that replaces operators with functions. The source map for the generated code points to the incorrect line previous line.
Version
@swc/core: 1.11.24