mirror of
https://github.com/swc-project/swc.git
synced 2024-10-05 12:49:21 +03:00
fix(es): Fix bugs (#1728)
swc_ecma_transforms_compat: - `block_scoping`: Ensure that #1462 is fixed. (#1462) - `regenerator`: Inject variables at proper level. (#1718) swc_ecam_transforms_typescript: - `strip`: Handle class expressions in arrow expressions correctly. (#1729)
This commit is contained in:
parent
d20c1d3089
commit
a518c83485
@ -6,7 +6,7 @@ edition = "2018"
|
||||
license = "Apache-2.0/MIT"
|
||||
name = "swc_ecma_transforms_compat"
|
||||
repository = "https://github.com/swc-project/swc.git"
|
||||
version = "0.17.4"
|
||||
version = "0.17.5"
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
|
||||
[dependencies]
|
||||
|
@ -998,846 +998,3 @@ impl Visit for FunctionFinder {
|
||||
self.found = true
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::block_scoping;
|
||||
use crate::{es2015, es2015::for_of::for_of, es2017::async_to_generator};
|
||||
use swc_common::{chain, Mark};
|
||||
use swc_ecma_parser::Syntax;
|
||||
use swc_ecma_transforms_testing::{test, test_exec, Tester};
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_loop,
|
||||
"for (const key in obj) {
|
||||
const bar = obj[key];
|
||||
|
||||
let qux;
|
||||
let fog;
|
||||
|
||||
if (Array.isArray(bar)) {
|
||||
qux = bar[0];
|
||||
fog = bar[1];
|
||||
} else {
|
||||
qux = bar;
|
||||
}
|
||||
|
||||
baz(key, qux, fog);
|
||||
}",
|
||||
"for (var key in obj) {
|
||||
var bar = obj[key];
|
||||
|
||||
var qux = void 0;
|
||||
var fog = void 0;
|
||||
|
||||
if (Array.isArray(bar)) {
|
||||
qux = bar[0];
|
||||
fog = bar[1];
|
||||
} else {
|
||||
qux = bar;
|
||||
}
|
||||
|
||||
baz(key, qux, fog);
|
||||
}"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_let_loop,
|
||||
"let functions = [];
|
||||
for (let i = 0; i < 10; i++) {
|
||||
functions.push(function() {
|
||||
console.log(i);
|
||||
});
|
||||
}
|
||||
functions[0]();
|
||||
functions[7]();",
|
||||
"
|
||||
var _loop = function(i) {
|
||||
functions.push(function() {
|
||||
console.log(i);
|
||||
});
|
||||
};
|
||||
var functions = [];
|
||||
for(var i = 0; i < 10; i++)_loop(i);
|
||||
functions[0]();
|
||||
functions[7]();
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_let_loop_exec,
|
||||
"let functions = [];
|
||||
for (let i = 0; i < 10; i++) {
|
||||
functions.push(function() {
|
||||
return i;
|
||||
});
|
||||
}
|
||||
expect(functions[0]()).toBe(0);
|
||||
expect(functions[7]()).toBe(7);
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_let_of_exec,
|
||||
"let functions = [];
|
||||
for (let i of [1, 3, 5, 7, 9]) {
|
||||
functions.push(function() {
|
||||
return i;
|
||||
});
|
||||
}
|
||||
expect(functions[0]()).toBe(1);
|
||||
expect(functions[1]()).toBe(3);
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| chain!(for_of(Default::default()), block_scoping()),
|
||||
issue_609_1,
|
||||
"let functions = [];
|
||||
for (let i of [1, 3, 5, 7, 9]) {
|
||||
functions.push(function() {
|
||||
return i;
|
||||
});
|
||||
}
|
||||
expect(functions[0]()).toBe(1);
|
||||
expect(functions[1]()).toBe(3);
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_662,
|
||||
"function foo(parts) {
|
||||
let match = null;
|
||||
|
||||
for (let i = 1; i >= 0; i--) {
|
||||
for (let j = 0; j >= 0; j--) {
|
||||
match = parts[i][j];
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return match;
|
||||
}
|
||||
|
||||
foo();",
|
||||
"function foo(parts) {
|
||||
var match = null;
|
||||
|
||||
for (var i = 1; i >= 0; i--) {
|
||||
for (var j = 0; j >= 0; j--) {
|
||||
match = parts[i][j];
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return match;
|
||||
}
|
||||
|
||||
foo();"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_686,
|
||||
"module.exports = function(values) {
|
||||
var vars = [];
|
||||
var elem = null, name, val;
|
||||
for (var i = 0; i < this.elements.length; i++) {
|
||||
elem = this.elements[i];
|
||||
name = elem.name;
|
||||
if (!name) continue;
|
||||
val = values[name];
|
||||
if (val == null) val = '';
|
||||
switch (elem.type) {
|
||||
case 'submit':
|
||||
break;
|
||||
case 'radio':
|
||||
case 'checkbox':
|
||||
elem.checked = val.some(function(str) {
|
||||
return str.toString() == elem.value;
|
||||
});
|
||||
break;
|
||||
case 'select-multiple':
|
||||
elem.fill(val);
|
||||
break;
|
||||
case 'textarea':
|
||||
elem.innerText = val;
|
||||
break;
|
||||
case 'hidden':
|
||||
break;
|
||||
default:
|
||||
if (elem.fill) {
|
||||
elem.fill(val);
|
||||
} else {
|
||||
elem.value = val;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
return vars;
|
||||
};",
|
||||
"
|
||||
module.exports = function(values) {
|
||||
var _this = this, _loop = function(i) {
|
||||
elem = _this.elements[i];
|
||||
name = elem.name;
|
||||
if (!name) return 'continue';
|
||||
val = values[name];
|
||||
if (val == null) val = '';
|
||||
switch(elem.type){
|
||||
case 'submit':
|
||||
break;
|
||||
case 'radio':
|
||||
case 'checkbox':
|
||||
elem.checked = val.some(function(str) {
|
||||
return str.toString() == elem.value;
|
||||
});
|
||||
break;
|
||||
case 'select-multiple':
|
||||
elem.fill(val);
|
||||
break;
|
||||
case 'textarea':
|
||||
elem.innerText = val;
|
||||
break;
|
||||
case 'hidden':
|
||||
break;
|
||||
default:
|
||||
if (elem.fill) {
|
||||
elem.fill(val);
|
||||
} else {
|
||||
elem.value = val;
|
||||
}
|
||||
break;
|
||||
}
|
||||
};
|
||||
var vars = [];
|
||||
var elem = null, name, val;
|
||||
for(var i = 0; i < this.elements.length; i++){
|
||||
var _ret = _loop(i);
|
||||
if (_ret === 'continue') continue;
|
||||
}
|
||||
return vars;
|
||||
};
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_723_1,
|
||||
"function foo() {
|
||||
const lod = { 0: { mig: 'bana' }};
|
||||
|
||||
for (let i = 0; i < 1; i++) {
|
||||
const { mig } = lod[i];
|
||||
|
||||
return false;
|
||||
|
||||
(zap) => zap === mig;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
expect(foo()).toBe(false);
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_723_2,
|
||||
"function foo() {
|
||||
const lod = { 0: { mig: 'bana' }};
|
||||
|
||||
for (let i = 0; i < 1; i++) {
|
||||
const { mig } = lod[i];
|
||||
|
||||
return false;
|
||||
|
||||
(zap) => zap === mig;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
expect(foo()).toBe(false);
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1022_1,
|
||||
"
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i++, [2].every(x => x != i))
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var _loop = function(i1) {
|
||||
console.log(i1++, [
|
||||
2
|
||||
].every(function(x) {
|
||||
return x != i1;
|
||||
}));
|
||||
i = i1, void 0;
|
||||
};
|
||||
for(var i = 0; i < 5; i++)_loop(i);
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1022_2,
|
||||
"
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i++, [2].every(x => x != i))
|
||||
if (i % 2 === 0) continue
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var _loop = function(i1) {
|
||||
console.log(i1++, [
|
||||
2
|
||||
].every(function(x) {
|
||||
return x != i1;
|
||||
}));
|
||||
if (i1 % 2 === 0) return i = i1, "continue";
|
||||
i = i1, void 0;
|
||||
};
|
||||
for(var i = 0; i < 5; i++){
|
||||
var _ret = _loop(i);
|
||||
if (_ret === "continue") continue;
|
||||
}
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1022_3,
|
||||
"
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i++, [2].every(x => x != i))
|
||||
if (i % 2 === 0) break
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var _loop = function(i1) {
|
||||
console.log(i1++, [
|
||||
2
|
||||
].every(function(x) {
|
||||
return x != i1;
|
||||
}));
|
||||
if (i1 % 2 === 0) return i = i1, "break";
|
||||
i = i1, void 0;
|
||||
};
|
||||
for(var i = 0; i < 5; i++){
|
||||
var _ret = _loop(i);
|
||||
if (_ret === "break") break;
|
||||
}
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1021_1,
|
||||
"
|
||||
class C {
|
||||
m() {
|
||||
for (let x = 0; x < 10; x++) console.log(this, y => y != x)
|
||||
}
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var C = function() {
|
||||
"use strict";
|
||||
function C() {
|
||||
_classCallCheck(this, C);
|
||||
}
|
||||
_createClass(C, [
|
||||
{
|
||||
key: "m",
|
||||
value: function m() {
|
||||
var _this = this, _loop = function(x) {
|
||||
console.log(_this, function(y) {
|
||||
return y != x;
|
||||
});
|
||||
};
|
||||
for(var x = 0; x < 10; x++)_loop(x);
|
||||
}
|
||||
}
|
||||
]);
|
||||
return C;
|
||||
}();
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1036_1,
|
||||
"
|
||||
async function foo() {
|
||||
await Promise.all([[1], [2], [3]].map(
|
||||
async ([a]) => Promise.resolve().then(() => a * 2))
|
||||
)
|
||||
}
|
||||
",
|
||||
"
|
||||
async function foo() {
|
||||
await Promise.all([
|
||||
[
|
||||
1
|
||||
],
|
||||
[
|
||||
2
|
||||
],
|
||||
[
|
||||
3
|
||||
]
|
||||
].map(async function(param) {
|
||||
var _param = _slicedToArray(param, 1), a = _param[0];
|
||||
return Promise.resolve().then(function() {
|
||||
return a * 2;
|
||||
});
|
||||
}));
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
chain!(
|
||||
async_to_generator(),
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
)
|
||||
},
|
||||
issue_1036_2,
|
||||
"
|
||||
async function foo() {
|
||||
await Promise.all([[1], [2], [3]].map(
|
||||
async ([a]) => Promise.resolve().then(() => a * 2))
|
||||
)
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var regeneratorRuntime = require("regenerator-runtime");
|
||||
var _marked = regeneratorRuntime.mark(_foo);
|
||||
function _foo() {
|
||||
_foo = _asyncToGenerator(regeneratorRuntime.mark(function _callee() {
|
||||
return regeneratorRuntime.wrap(function _callee$(_ctx) {
|
||||
while(1)switch(_ctx.prev = _ctx.next){
|
||||
case 0:
|
||||
_ctx.next = 2;
|
||||
return Promise.all([
|
||||
[
|
||||
1
|
||||
],
|
||||
[
|
||||
2
|
||||
],
|
||||
[
|
||||
3
|
||||
]
|
||||
].map(_asyncToGenerator(regeneratorRuntime.mark(function _callee1(param) {
|
||||
var _param = _slicedToArray(param, 1), a = _param[0];
|
||||
return regeneratorRuntime.wrap(function _callee$1(_ctx1) {
|
||||
while(1)switch(_ctx1.prev = _ctx1.next){
|
||||
case 0:
|
||||
return _ctx1.abrupt("return", Promise.resolve().then(function() {
|
||||
return a * 2;
|
||||
}));
|
||||
case 1:
|
||||
case "end":
|
||||
return _ctx1.stop();
|
||||
}
|
||||
}, _callee1);
|
||||
}))));
|
||||
case 2:
|
||||
case "end":
|
||||
return _ctx.stop();
|
||||
}
|
||||
}, _callee);
|
||||
}));
|
||||
return _foo.apply(this, arguments);
|
||||
}
|
||||
function foo() {
|
||||
return _foo.apply(this, arguments);
|
||||
}
|
||||
|
||||
"#
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
chain!(
|
||||
async_to_generator(),
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
)
|
||||
},
|
||||
issue_1036_3,
|
||||
"
|
||||
const x = async function() {
|
||||
return await Promise.all([[1], [2], [3]].map(
|
||||
async ([a]) => Promise.resolve().then(() => a * 2))
|
||||
)
|
||||
};
|
||||
return x().then(x => {
|
||||
expect(x).toEqual([2, 4, 6])
|
||||
})
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_1231_1,
|
||||
"
|
||||
function combineOverlappingMatches(matches) {
|
||||
let hasOverlaps = false
|
||||
|
||||
for (let i = matches.length - 1; i >= 0; i--) {
|
||||
let currentMatch = matches[i]
|
||||
let overlap = matches.find(match => {
|
||||
return match !== currentMatch && match.itemsType === currentMatch.itemsType
|
||||
})
|
||||
|
||||
if (overlap) {
|
||||
hasOverlaps = true
|
||||
matches.splice(i, 1)
|
||||
}
|
||||
}
|
||||
|
||||
if (hasOverlaps) {
|
||||
combineOverlappingMatches(matches)
|
||||
}
|
||||
}
|
||||
|
||||
combineOverlappingMatches([1])
|
||||
",
|
||||
"
|
||||
function combineOverlappingMatches(matches) {
|
||||
var hasOverlaps = false;
|
||||
for(var i = matches.length - 1; i >= 0; i--){
|
||||
var currentMatch = matches[i];
|
||||
var overlap = matches.find((match)=>{
|
||||
return match !== currentMatch && match.itemsType === currentMatch.itemsType;
|
||||
});
|
||||
if (overlap) {
|
||||
hasOverlaps = true;
|
||||
matches.splice(i, 1);
|
||||
}
|
||||
}
|
||||
if (hasOverlaps) {
|
||||
combineOverlappingMatches(matches);
|
||||
}
|
||||
}
|
||||
combineOverlappingMatches([
|
||||
1
|
||||
]);
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_1415_1,
|
||||
"
|
||||
export function test(items) {
|
||||
const infoMap = new WeakMap();
|
||||
for (let i = 0; i < items.length; i += 1) {
|
||||
const item = items[i];
|
||||
let info;
|
||||
switch (item.type) {
|
||||
case 'branch1':
|
||||
info = item.method1();
|
||||
break;
|
||||
case 'branch2':
|
||||
info = item.method2();
|
||||
break;
|
||||
case 'branch3':
|
||||
info = item.method3(
|
||||
Object.fromEntries(
|
||||
item.subItems.map((t) => [item.alias ?? t.name, getInfo(t)])
|
||||
)
|
||||
);
|
||||
break;
|
||||
default:
|
||||
throw new Error('boom');
|
||||
}
|
||||
infoMap.set(item, info); // important
|
||||
}
|
||||
|
||||
function getInfo(item) {
|
||||
if (!infoMap.has(item)) {
|
||||
throw new Error('no info yet');
|
||||
}
|
||||
return infoMap.get(item);
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
export function test(items) {
|
||||
var infoMap = new WeakMap();
|
||||
for(var i = 0; i < items.length; i += 1){
|
||||
var item = items[i];
|
||||
var info = void 0;
|
||||
switch(item.type){
|
||||
case 'branch1':
|
||||
info = item.method1();
|
||||
break;
|
||||
case 'branch2':
|
||||
info = item.method2();
|
||||
break;
|
||||
case 'branch3':
|
||||
info = item.method3(Object.fromEntries(item.subItems.map((t)=>[
|
||||
item.alias ?? t.name,
|
||||
getInfo(t)
|
||||
]
|
||||
)));
|
||||
break;
|
||||
default:
|
||||
throw new Error('boom');
|
||||
}
|
||||
infoMap.set(item, info);
|
||||
}
|
||||
function getInfo(item) {
|
||||
if (!infoMap.has(item)) {
|
||||
throw new Error('no info yet');
|
||||
}
|
||||
return infoMap.get(item);
|
||||
}
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_loop,
|
||||
"
|
||||
function test() {
|
||||
for (var i = 0; i < arguments.length; i++) {
|
||||
var arg = arguments[i];
|
||||
console.log((() => arg)());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test() {
|
||||
var _arguments = arguments, _loop = function(i) {
|
||||
var arg = _arguments[i];
|
||||
console.log(function() {
|
||||
return arg;
|
||||
}());
|
||||
};
|
||||
for(var i = 0; i < arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_loop_member,
|
||||
"
|
||||
function test(a) {
|
||||
for (var i = 0; i < a.arguments.length; i++) {
|
||||
var arg = a.arguments[i];
|
||||
console.log((() => arg)());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test(a) {
|
||||
var _loop = function(i) {
|
||||
var arg = a.arguments[i];
|
||||
console.log(function() {
|
||||
return arg;
|
||||
}());
|
||||
};
|
||||
for(var i = 0; i < a.arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_arrow,
|
||||
"
|
||||
function test() {
|
||||
for (var i = 0; i < arguments.length; i++) {
|
||||
console.log((() => arguments[i])());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test() {
|
||||
var _this = this, _arguments = arguments, _loop = function(i) {
|
||||
console.log((function(_arguments1) {
|
||||
return _arguments1[i];
|
||||
}).bind(_this, _arguments)());
|
||||
};
|
||||
for(var i = 0; i < arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_function,
|
||||
"
|
||||
function test() {
|
||||
for (var i = 0; i < arguments.length; i++) {
|
||||
console.log((function () { return arguments[i] })());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test() {
|
||||
var _loop = function(i) {
|
||||
console.log(function() {
|
||||
return arguments[i];
|
||||
}());
|
||||
};
|
||||
for(var i = 0; i < arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
}
|
||||
|
@ -60,6 +60,11 @@ impl Hoister {
|
||||
impl Fold for Hoister {
|
||||
noop_fold_type!();
|
||||
|
||||
/// Noop
|
||||
fn fold_function(&mut self, n: Function) -> Function {
|
||||
n
|
||||
}
|
||||
|
||||
fn fold_expr(&mut self, e: Expr) -> Expr {
|
||||
let e = e.fold_children_with(self);
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
use self::{case::CaseHandler, hoist::hoist};
|
||||
use std::mem::replace;
|
||||
use std::mem::take;
|
||||
use swc_atoms::js_word;
|
||||
use swc_common::{Mark, Spanned, DUMMY_SP};
|
||||
use swc_ecma_ast::*;
|
||||
@ -78,7 +78,7 @@ impl Regenerator {
|
||||
span: DUMMY_SP,
|
||||
kind: VarDeclKind::Var,
|
||||
declare: false,
|
||||
decls: replace(&mut self.top_level_vars, Default::default()),
|
||||
decls: take(&mut self.top_level_vars),
|
||||
}))),
|
||||
);
|
||||
}
|
||||
@ -411,7 +411,7 @@ impl Regenerator {
|
||||
buf.push(Stmt::Decl(Decl::Var(VarDecl {
|
||||
span: DUMMY_SP,
|
||||
kind: VarDeclKind::Var,
|
||||
decls: replace(&mut self.outer_fn_vars, Default::default()),
|
||||
decls: take(&mut self.outer_fn_vars),
|
||||
declare: false,
|
||||
})));
|
||||
}
|
||||
|
885
ecmascript/transforms/compat/tests/es2015_block_scoping.rs
Normal file
885
ecmascript/transforms/compat/tests/es2015_block_scoping.rs
Normal file
@ -0,0 +1,885 @@
|
||||
use swc_common::{chain, Mark};
|
||||
use swc_ecma_parser::Syntax;
|
||||
use swc_ecma_transforms_compat::es2015::block_scoping;
|
||||
use swc_ecma_transforms_compat::{es2015, es2015::for_of::for_of, es2017::async_to_generator};
|
||||
use swc_ecma_transforms_testing::{test, test_exec, Tester};
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_loop,
|
||||
"for (const key in obj) {
|
||||
const bar = obj[key];
|
||||
|
||||
let qux;
|
||||
let fog;
|
||||
|
||||
if (Array.isArray(bar)) {
|
||||
qux = bar[0];
|
||||
fog = bar[1];
|
||||
} else {
|
||||
qux = bar;
|
||||
}
|
||||
|
||||
baz(key, qux, fog);
|
||||
}",
|
||||
"for (var key in obj) {
|
||||
var bar = obj[key];
|
||||
|
||||
var qux = void 0;
|
||||
var fog = void 0;
|
||||
|
||||
if (Array.isArray(bar)) {
|
||||
qux = bar[0];
|
||||
fog = bar[1];
|
||||
} else {
|
||||
qux = bar;
|
||||
}
|
||||
|
||||
baz(key, qux, fog);
|
||||
}"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_let_loop,
|
||||
"let functions = [];
|
||||
for (let i = 0; i < 10; i++) {
|
||||
functions.push(function() {
|
||||
console.log(i);
|
||||
});
|
||||
}
|
||||
functions[0]();
|
||||
functions[7]();",
|
||||
"
|
||||
var _loop = function(i) {
|
||||
functions.push(function() {
|
||||
console.log(i);
|
||||
});
|
||||
};
|
||||
var functions = [];
|
||||
for(var i = 0; i < 10; i++)_loop(i);
|
||||
functions[0]();
|
||||
functions[7]();
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_let_loop_exec,
|
||||
"let functions = [];
|
||||
for (let i = 0; i < 10; i++) {
|
||||
functions.push(function() {
|
||||
return i;
|
||||
});
|
||||
}
|
||||
expect(functions[0]()).toBe(0);
|
||||
expect(functions[7]()).toBe(7);
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
for_let_of_exec,
|
||||
"let functions = [];
|
||||
for (let i of [1, 3, 5, 7, 9]) {
|
||||
functions.push(function() {
|
||||
return i;
|
||||
});
|
||||
}
|
||||
expect(functions[0]()).toBe(1);
|
||||
expect(functions[1]()).toBe(3);
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| chain!(for_of(Default::default()), block_scoping()),
|
||||
issue_609_1,
|
||||
"let functions = [];
|
||||
for (let i of [1, 3, 5, 7, 9]) {
|
||||
functions.push(function() {
|
||||
return i;
|
||||
});
|
||||
}
|
||||
expect(functions[0]()).toBe(1);
|
||||
expect(functions[1]()).toBe(3);
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_662,
|
||||
"function foo(parts) {
|
||||
let match = null;
|
||||
|
||||
for (let i = 1; i >= 0; i--) {
|
||||
for (let j = 0; j >= 0; j--) {
|
||||
match = parts[i][j];
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return match;
|
||||
}
|
||||
|
||||
foo();",
|
||||
"function foo(parts) {
|
||||
var match = null;
|
||||
|
||||
for (var i = 1; i >= 0; i--) {
|
||||
for (var j = 0; j >= 0; j--) {
|
||||
match = parts[i][j];
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (match) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return match;
|
||||
}
|
||||
|
||||
foo();"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_686,
|
||||
"module.exports = function(values) {
|
||||
var vars = [];
|
||||
var elem = null, name, val;
|
||||
for (var i = 0; i < this.elements.length; i++) {
|
||||
elem = this.elements[i];
|
||||
name = elem.name;
|
||||
if (!name) continue;
|
||||
val = values[name];
|
||||
if (val == null) val = '';
|
||||
switch (elem.type) {
|
||||
case 'submit':
|
||||
break;
|
||||
case 'radio':
|
||||
case 'checkbox':
|
||||
elem.checked = val.some(function(str) {
|
||||
return str.toString() == elem.value;
|
||||
});
|
||||
break;
|
||||
case 'select-multiple':
|
||||
elem.fill(val);
|
||||
break;
|
||||
case 'textarea':
|
||||
elem.innerText = val;
|
||||
break;
|
||||
case 'hidden':
|
||||
break;
|
||||
default:
|
||||
if (elem.fill) {
|
||||
elem.fill(val);
|
||||
} else {
|
||||
elem.value = val;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
return vars;
|
||||
};",
|
||||
"
|
||||
module.exports = function(values) {
|
||||
var _this = this, _loop = function(i) {
|
||||
elem = _this.elements[i];
|
||||
name = elem.name;
|
||||
if (!name) return 'continue';
|
||||
val = values[name];
|
||||
if (val == null) val = '';
|
||||
switch(elem.type){
|
||||
case 'submit':
|
||||
break;
|
||||
case 'radio':
|
||||
case 'checkbox':
|
||||
elem.checked = val.some(function(str) {
|
||||
return str.toString() == elem.value;
|
||||
});
|
||||
break;
|
||||
case 'select-multiple':
|
||||
elem.fill(val);
|
||||
break;
|
||||
case 'textarea':
|
||||
elem.innerText = val;
|
||||
break;
|
||||
case 'hidden':
|
||||
break;
|
||||
default:
|
||||
if (elem.fill) {
|
||||
elem.fill(val);
|
||||
} else {
|
||||
elem.value = val;
|
||||
}
|
||||
break;
|
||||
}
|
||||
};
|
||||
var vars = [];
|
||||
var elem = null, name, val;
|
||||
for(var i = 0; i < this.elements.length; i++){
|
||||
var _ret = _loop(i);
|
||||
if (_ret === 'continue') continue;
|
||||
}
|
||||
return vars;
|
||||
};
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_723_1,
|
||||
"function foo() {
|
||||
const lod = { 0: { mig: 'bana' }};
|
||||
|
||||
for (let i = 0; i < 1; i++) {
|
||||
const { mig } = lod[i];
|
||||
|
||||
return false;
|
||||
|
||||
(zap) => zap === mig;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
expect(foo()).toBe(false);
|
||||
"
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_723_2,
|
||||
"function foo() {
|
||||
const lod = { 0: { mig: 'bana' }};
|
||||
|
||||
for (let i = 0; i < 1; i++) {
|
||||
const { mig } = lod[i];
|
||||
|
||||
return false;
|
||||
|
||||
(zap) => zap === mig;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
expect(foo()).toBe(false);
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1022_1,
|
||||
"
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i++, [2].every(x => x != i))
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var _loop = function(i1) {
|
||||
console.log(i1++, [
|
||||
2
|
||||
].every(function(x) {
|
||||
return x != i1;
|
||||
}));
|
||||
i = i1, void 0;
|
||||
};
|
||||
for(var i = 0; i < 5; i++)_loop(i);
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1022_2,
|
||||
"
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i++, [2].every(x => x != i))
|
||||
if (i % 2 === 0) continue
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var _loop = function(i1) {
|
||||
console.log(i1++, [
|
||||
2
|
||||
].every(function(x) {
|
||||
return x != i1;
|
||||
}));
|
||||
if (i1 % 2 === 0) return i = i1, "continue";
|
||||
i = i1, void 0;
|
||||
};
|
||||
for(var i = 0; i < 5; i++){
|
||||
var _ret = _loop(i);
|
||||
if (_ret === "continue") continue;
|
||||
}
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1022_3,
|
||||
"
|
||||
for (let i = 0; i < 5; i++) {
|
||||
console.log(i++, [2].every(x => x != i))
|
||||
if (i % 2 === 0) break
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var _loop = function(i1) {
|
||||
console.log(i1++, [
|
||||
2
|
||||
].every(function(x) {
|
||||
return x != i1;
|
||||
}));
|
||||
if (i1 % 2 === 0) return i = i1, "break";
|
||||
i = i1, void 0;
|
||||
};
|
||||
for(var i = 0; i < 5; i++){
|
||||
var _ret = _loop(i);
|
||||
if (_ret === "break") break;
|
||||
}
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1021_1,
|
||||
"
|
||||
class C {
|
||||
m() {
|
||||
for (let x = 0; x < 10; x++) console.log(this, y => y != x)
|
||||
}
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var C = function() {
|
||||
"use strict";
|
||||
function C() {
|
||||
_classCallCheck(this, C);
|
||||
}
|
||||
_createClass(C, [
|
||||
{
|
||||
key: "m",
|
||||
value: function m() {
|
||||
var _this = this, _loop = function(x) {
|
||||
console.log(_this, function(y) {
|
||||
return y != x;
|
||||
});
|
||||
};
|
||||
for(var x = 0; x < 10; x++)_loop(x);
|
||||
}
|
||||
}
|
||||
]);
|
||||
return C;
|
||||
}();
|
||||
"#
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
issue_1036_1,
|
||||
"
|
||||
async function foo() {
|
||||
await Promise.all([[1], [2], [3]].map(
|
||||
async ([a]) => Promise.resolve().then(() => a * 2))
|
||||
)
|
||||
}
|
||||
",
|
||||
"
|
||||
async function foo() {
|
||||
await Promise.all([
|
||||
[
|
||||
1
|
||||
],
|
||||
[
|
||||
2
|
||||
],
|
||||
[
|
||||
3
|
||||
]
|
||||
].map(async function(param) {
|
||||
var _param = _slicedToArray(param, 1), a = _param[0];
|
||||
return Promise.resolve().then(function() {
|
||||
return a * 2;
|
||||
});
|
||||
}));
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
chain!(
|
||||
async_to_generator(),
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
)
|
||||
},
|
||||
issue_1036_2,
|
||||
"
|
||||
async function foo() {
|
||||
await Promise.all([[1], [2], [3]].map(
|
||||
async ([a]) => Promise.resolve().then(() => a * 2))
|
||||
)
|
||||
}
|
||||
",
|
||||
r#"
|
||||
var regeneratorRuntime = require("regenerator-runtime");
|
||||
var _marked = regeneratorRuntime.mark(_foo);
|
||||
function _foo() {
|
||||
_foo = _asyncToGenerator(regeneratorRuntime.mark(function _callee() {
|
||||
return regeneratorRuntime.wrap(function _callee$(_ctx) {
|
||||
while(1)switch(_ctx.prev = _ctx.next){
|
||||
case 0:
|
||||
_ctx.next = 2;
|
||||
return Promise.all([
|
||||
[
|
||||
1
|
||||
],
|
||||
[
|
||||
2
|
||||
],
|
||||
[
|
||||
3
|
||||
]
|
||||
].map(_asyncToGenerator(regeneratorRuntime.mark(function _callee1(param) {
|
||||
var _param = _slicedToArray(param, 1), a = _param[0];
|
||||
return regeneratorRuntime.wrap(function _callee$1(_ctx1) {
|
||||
while(1)switch(_ctx1.prev = _ctx1.next){
|
||||
case 0:
|
||||
return _ctx1.abrupt("return", Promise.resolve().then(function() {
|
||||
return a * 2;
|
||||
}));
|
||||
case 1:
|
||||
case "end":
|
||||
return _ctx1.stop();
|
||||
}
|
||||
}, _callee1);
|
||||
}))));
|
||||
case 2:
|
||||
case "end":
|
||||
return _ctx.stop();
|
||||
}
|
||||
}, _callee);
|
||||
}));
|
||||
return _foo.apply(this, arguments);
|
||||
}
|
||||
function foo() {
|
||||
return _foo.apply(this, arguments);
|
||||
}
|
||||
|
||||
"#
|
||||
);
|
||||
|
||||
test_exec!(
|
||||
Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
chain!(
|
||||
async_to_generator(),
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
)
|
||||
},
|
||||
issue_1036_3,
|
||||
"
|
||||
const x = async function() {
|
||||
return await Promise.all([[1], [2], [3]].map(
|
||||
async ([a]) => Promise.resolve().then(() => a * 2))
|
||||
)
|
||||
};
|
||||
return x().then(x => {
|
||||
expect(x).toEqual([2, 4, 6])
|
||||
})
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_1231_1,
|
||||
"
|
||||
function combineOverlappingMatches(matches) {
|
||||
let hasOverlaps = false
|
||||
|
||||
for (let i = matches.length - 1; i >= 0; i--) {
|
||||
let currentMatch = matches[i]
|
||||
let overlap = matches.find(match => {
|
||||
return match !== currentMatch && match.itemsType === currentMatch.itemsType
|
||||
})
|
||||
|
||||
if (overlap) {
|
||||
hasOverlaps = true
|
||||
matches.splice(i, 1)
|
||||
}
|
||||
}
|
||||
|
||||
if (hasOverlaps) {
|
||||
combineOverlappingMatches(matches)
|
||||
}
|
||||
}
|
||||
|
||||
combineOverlappingMatches([1])
|
||||
",
|
||||
"
|
||||
function combineOverlappingMatches(matches) {
|
||||
var hasOverlaps = false;
|
||||
for(var i = matches.length - 1; i >= 0; i--){
|
||||
var currentMatch = matches[i];
|
||||
var overlap = matches.find((match)=>{
|
||||
return match !== currentMatch && match.itemsType === currentMatch.itemsType;
|
||||
});
|
||||
if (overlap) {
|
||||
hasOverlaps = true;
|
||||
matches.splice(i, 1);
|
||||
}
|
||||
}
|
||||
if (hasOverlaps) {
|
||||
combineOverlappingMatches(matches);
|
||||
}
|
||||
}
|
||||
combineOverlappingMatches([
|
||||
1
|
||||
]);
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_1415_1,
|
||||
"
|
||||
export function test(items) {
|
||||
const infoMap = new WeakMap();
|
||||
for (let i = 0; i < items.length; i += 1) {
|
||||
const item = items[i];
|
||||
let info;
|
||||
switch (item.type) {
|
||||
case 'branch1':
|
||||
info = item.method1();
|
||||
break;
|
||||
case 'branch2':
|
||||
info = item.method2();
|
||||
break;
|
||||
case 'branch3':
|
||||
info = item.method3(
|
||||
Object.fromEntries(
|
||||
item.subItems.map((t) => [item.alias ?? t.name, getInfo(t)])
|
||||
)
|
||||
);
|
||||
break;
|
||||
default:
|
||||
throw new Error('boom');
|
||||
}
|
||||
infoMap.set(item, info); // important
|
||||
}
|
||||
|
||||
function getInfo(item) {
|
||||
if (!infoMap.has(item)) {
|
||||
throw new Error('no info yet');
|
||||
}
|
||||
return infoMap.get(item);
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
export function test(items) {
|
||||
var infoMap = new WeakMap();
|
||||
for(var i = 0; i < items.length; i += 1){
|
||||
var item = items[i];
|
||||
var info = void 0;
|
||||
switch(item.type){
|
||||
case 'branch1':
|
||||
info = item.method1();
|
||||
break;
|
||||
case 'branch2':
|
||||
info = item.method2();
|
||||
break;
|
||||
case 'branch3':
|
||||
info = item.method3(Object.fromEntries(item.subItems.map((t)=>[
|
||||
item.alias ?? t.name,
|
||||
getInfo(t)
|
||||
]
|
||||
)));
|
||||
break;
|
||||
default:
|
||||
throw new Error('boom');
|
||||
}
|
||||
infoMap.set(item, info);
|
||||
}
|
||||
function getInfo(item) {
|
||||
if (!infoMap.has(item)) {
|
||||
throw new Error('no info yet');
|
||||
}
|
||||
return infoMap.get(item);
|
||||
}
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_loop,
|
||||
"
|
||||
function test() {
|
||||
for (var i = 0; i < arguments.length; i++) {
|
||||
var arg = arguments[i];
|
||||
console.log((() => arg)());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test() {
|
||||
var _arguments = arguments, _loop = function(i) {
|
||||
var arg = _arguments[i];
|
||||
console.log(function() {
|
||||
return arg;
|
||||
}());
|
||||
};
|
||||
for(var i = 0; i < arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_loop_member,
|
||||
"
|
||||
function test(a) {
|
||||
for (var i = 0; i < a.arguments.length; i++) {
|
||||
var arg = a.arguments[i];
|
||||
console.log((() => arg)());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test(a) {
|
||||
var _loop = function(i) {
|
||||
var arg = a.arguments[i];
|
||||
console.log(function() {
|
||||
return arg;
|
||||
}());
|
||||
};
|
||||
for(var i = 0; i < a.arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_arrow,
|
||||
"
|
||||
function test() {
|
||||
for (var i = 0; i < arguments.length; i++) {
|
||||
console.log((() => arguments[i])());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test() {
|
||||
var _this = this, _arguments = arguments, _loop = function(i) {
|
||||
console.log((function(_arguments1) {
|
||||
return _arguments1[i];
|
||||
}).bind(_this, _arguments)());
|
||||
};
|
||||
for(var i = 0; i < arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|Tester { comments, .. }| {
|
||||
let mark = Mark::fresh(Mark::root());
|
||||
es2015::es2015(
|
||||
mark,
|
||||
Some(comments.clone()),
|
||||
es2015::Config {
|
||||
..Default::default()
|
||||
},
|
||||
)
|
||||
},
|
||||
arguments_function,
|
||||
"
|
||||
function test() {
|
||||
for (var i = 0; i < arguments.length; i++) {
|
||||
console.log((function () { return arguments[i] })());
|
||||
}
|
||||
}
|
||||
",
|
||||
"
|
||||
function test() {
|
||||
var _loop = function(i) {
|
||||
console.log(function() {
|
||||
return arguments[i];
|
||||
}());
|
||||
};
|
||||
for(var i = 0; i < arguments.length; i++)_loop(i);
|
||||
}
|
||||
"
|
||||
);
|
||||
|
||||
test!(
|
||||
::swc_ecma_parser::Syntax::default(),
|
||||
|_| block_scoping(),
|
||||
issue_1462_1,
|
||||
"
|
||||
export default function _objectSpread(target) {
|
||||
for (var i = 1; i < arguments.length; i++) {
|
||||
var source = arguments[i] != null ? arguments[i] : {};
|
||||
var ownKeys = Object.keys(source);
|
||||
|
||||
if (typeof Object.getOwnPropertySymbols === 'function') {
|
||||
ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) {
|
||||
return Object.getOwnPropertyDescriptor(source, sym).enumerable;
|
||||
}));
|
||||
}
|
||||
|
||||
ownKeys.forEach(function (key) {
|
||||
defineProperty(target, key, source[key]);
|
||||
});
|
||||
}
|
||||
|
||||
return target;
|
||||
}
|
||||
",
|
||||
"
|
||||
export default function _objectSpread(target) {
|
||||
var _arguments = arguments, _loop = function(i) {
|
||||
var source = _arguments[i] != null ? _arguments[i] : {
|
||||
};
|
||||
var ownKeys = Object.keys(source);
|
||||
if (typeof Object.getOwnPropertySymbols === 'function') {
|
||||
ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function(sym) \
|
||||
{
|
||||
return Object.getOwnPropertyDescriptor(source, sym).enumerable;
|
||||
}));
|
||||
}
|
||||
ownKeys.forEach(function(key) {
|
||||
defineProperty(target, key, source[key]);
|
||||
});
|
||||
};
|
||||
for(var i = 1; i < arguments.length; i++)_loop(i);
|
||||
return target;
|
||||
}
|
||||
"
|
||||
);
|
@ -6,7 +6,7 @@ edition = "2018"
|
||||
license = "Apache-2.0/MIT"
|
||||
name = "swc_ecma_transforms_typescript"
|
||||
repository = "https://github.com/swc-project/swc.git"
|
||||
version = "0.19.1"
|
||||
version = "0.19.2"
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
|
||||
[dependencies]
|
||||
|
@ -1271,9 +1271,11 @@ impl VisitMut for Strip {
|
||||
fn visit_mut_block_stmt_or_expr(&mut self, n: &mut BlockStmtOrExpr) {
|
||||
match n {
|
||||
BlockStmtOrExpr::Expr(expr) if expr.is_class() => {
|
||||
let span = expr.span();
|
||||
|
||||
let ClassExpr { ident, class } = expr.take().class().unwrap();
|
||||
let ident = ident.unwrap_or_else(|| private_ident!("_class"));
|
||||
let (decl, extra_exprs) = self.fold_class_as_decl(ident, class);
|
||||
let (decl, extra_exprs) = self.fold_class_as_decl(ident.clone(), class);
|
||||
let mut stmts = vec![];
|
||||
stmts.push(Stmt::Decl(decl));
|
||||
stmts.extend(
|
||||
@ -1282,6 +1284,10 @@ impl VisitMut for Strip {
|
||||
.map(|e| e.into_stmt())
|
||||
.collect::<Vec<_>>(),
|
||||
);
|
||||
stmts.push(Stmt::Return(ReturnStmt {
|
||||
span,
|
||||
arg: Some(Box::new(Expr::Ident(ident))),
|
||||
}));
|
||||
*n = BlockStmtOrExpr::BlockStmt(BlockStmt {
|
||||
span: n.span(),
|
||||
stmts,
|
||||
|
@ -59,4 +59,5 @@ export var fn = function() {
|
||||
return _class;
|
||||
}(MyClass);
|
||||
_class.x = 5;
|
||||
return _class;
|
||||
};
|
||||
|
@ -58,4 +58,5 @@ export var fn = function() {
|
||||
}
|
||||
return _class;
|
||||
}(MyClass);
|
||||
return _class;
|
||||
};
|
||||
|
@ -63,4 +63,5 @@ var withTeamsForUser = function(_WrappedComponent) {
|
||||
return _class;
|
||||
}(Component);
|
||||
_class.displayName = "x";
|
||||
return _class;
|
||||
};
|
||||
|
@ -55,4 +55,5 @@ var withTeamsForUser = function() {
|
||||
return _class;
|
||||
}(Component);
|
||||
_class.displayName = "x";
|
||||
return _class;
|
||||
};
|
||||
|
@ -58,4 +58,5 @@ export var fn = function() {
|
||||
}
|
||||
return _class;
|
||||
}(MyClass);
|
||||
return _class;
|
||||
};
|
||||
|
7
tests/fixture/issue-1718/case1/input/.swcrc
Normal file
7
tests/fixture/issue-1718/case1/input/.swcrc
Normal file
@ -0,0 +1,7 @@
|
||||
{
|
||||
"jsc": {
|
||||
"parser": {
|
||||
"syntax": "typescript"
|
||||
}
|
||||
}
|
||||
}
|
13
tests/fixture/issue-1718/case1/input/index.ts
Normal file
13
tests/fixture/issue-1718/case1/input/index.ts
Normal file
@ -0,0 +1,13 @@
|
||||
async function scanUser(groups: { users: number[] }[]) {
|
||||
await Promise.all(groups.map(async ({ users }) => {
|
||||
for (const user of users) {
|
||||
console.log('user', user)
|
||||
await new Promise(resolve => setTimeout(resolve, 30))
|
||||
}
|
||||
}))
|
||||
}
|
||||
|
||||
scanUser([
|
||||
{ users: [1, 2, 3, 4, 5] },
|
||||
{ users: [11, 12, 13, 14, 15] },
|
||||
])
|
136
tests/fixture/issue-1718/case1/output/index.ts
Normal file
136
tests/fixture/issue-1718/case1/output/index.ts
Normal file
@ -0,0 +1,136 @@
|
||||
function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) {
|
||||
try {
|
||||
var info = gen[key](arg);
|
||||
var value = info.value;
|
||||
} catch (error) {
|
||||
reject(error);
|
||||
return;
|
||||
}
|
||||
if (info.done) {
|
||||
resolve(value);
|
||||
} else {
|
||||
Promise.resolve(value).then(_next, _throw);
|
||||
}
|
||||
}
|
||||
function _asyncToGenerator(fn) {
|
||||
return function() {
|
||||
var self = this, args = arguments;
|
||||
return new Promise(function(resolve, reject) {
|
||||
var gen = fn.apply(self, args);
|
||||
function _next(value) {
|
||||
asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value);
|
||||
}
|
||||
function _throw(err) {
|
||||
asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err);
|
||||
}
|
||||
_next(undefined);
|
||||
});
|
||||
};
|
||||
}
|
||||
var regeneratorRuntime = require("regenerator-runtime");
|
||||
var _marked = regeneratorRuntime.mark(_scanUser);
|
||||
function _scanUser() {
|
||||
_scanUser = _asyncToGenerator(regeneratorRuntime.mark(function _callee(groups) {
|
||||
return regeneratorRuntime.wrap(function _callee$(_ctx) {
|
||||
while(1)switch(_ctx.prev = _ctx.next){
|
||||
case 0:
|
||||
_ctx.next = 2;
|
||||
return Promise.all(groups.map(_asyncToGenerator(regeneratorRuntime.mark(function _callee1(param) {
|
||||
var users = param.users;
|
||||
var _iteratorNormalCompletion, _didIteratorError, _iteratorError, _iterator, _step, user;
|
||||
return regeneratorRuntime.wrap(function _callee$1(_ctx1) {
|
||||
while(1)switch(_ctx1.prev = _ctx1.next){
|
||||
case 0:
|
||||
_iteratorNormalCompletion = true, _didIteratorError = false, _iteratorError = undefined;
|
||||
_ctx1.prev = 1;
|
||||
_iterator = users[Symbol.iterator]();
|
||||
case 3:
|
||||
if (_iteratorNormalCompletion = (_step = _iterator.next()).done) {
|
||||
_ctx1.next = 11;
|
||||
break;
|
||||
}
|
||||
user = _step.value;
|
||||
console.log('user', user);
|
||||
_ctx1.next = 8;
|
||||
return new Promise(function(resolve) {
|
||||
return setTimeout(resolve, 30);
|
||||
});
|
||||
case 8:
|
||||
_iteratorNormalCompletion = true;
|
||||
_ctx1.next = 3;
|
||||
break;
|
||||
case 11:
|
||||
_ctx1.next = 17;
|
||||
break;
|
||||
case 13:
|
||||
_ctx1.prev = 13;
|
||||
_ctx1.t0 = _ctx1["catch"](1);
|
||||
_didIteratorError = true;
|
||||
_iteratorError = _ctx1.t0;
|
||||
case 17:
|
||||
_ctx1.prev = 17;
|
||||
_ctx1.prev = 18;
|
||||
if (!_iteratorNormalCompletion && _iterator.return != null) {
|
||||
_iterator.return();
|
||||
}
|
||||
case 20:
|
||||
_ctx1.prev = 20;
|
||||
if (!_didIteratorError) {
|
||||
_ctx1.next = 23;
|
||||
break;
|
||||
}
|
||||
throw _iteratorError;
|
||||
case 23:
|
||||
return _ctx1.finish(20);
|
||||
case 24:
|
||||
return _ctx1.finish(17);
|
||||
case 25:
|
||||
case "end":
|
||||
return _ctx1.stop();
|
||||
}
|
||||
}, _callee1, null, [
|
||||
[
|
||||
18,
|
||||
,
|
||||
20,
|
||||
24
|
||||
],
|
||||
[
|
||||
1,
|
||||
13,
|
||||
17,
|
||||
25
|
||||
]
|
||||
]);
|
||||
}))));
|
||||
case 2:
|
||||
case "end":
|
||||
return _ctx.stop();
|
||||
}
|
||||
}, _callee);
|
||||
}));
|
||||
return _scanUser.apply(this, arguments);
|
||||
}
|
||||
function scanUser(groups) {
|
||||
return _scanUser.apply(this, arguments);
|
||||
}
|
||||
scanUser([
|
||||
{
|
||||
users: [
|
||||
1,
|
||||
2,
|
||||
3,
|
||||
4,
|
||||
5
|
||||
]
|
||||
},
|
||||
{
|
||||
users: [
|
||||
11,
|
||||
12,
|
||||
13,
|
||||
14,
|
||||
15
|
||||
]
|
||||
},
|
||||
]);
|
8
tests/fixture/issue-1718/case2/input/.swcrc
Normal file
8
tests/fixture/issue-1718/case2/input/.swcrc
Normal file
@ -0,0 +1,8 @@
|
||||
{
|
||||
"jsc": {
|
||||
"parser": {
|
||||
"syntax": "typescript"
|
||||
},
|
||||
"target": "es2016"
|
||||
}
|
||||
}
|
13
tests/fixture/issue-1718/case2/input/index.ts
Normal file
13
tests/fixture/issue-1718/case2/input/index.ts
Normal file
@ -0,0 +1,13 @@
|
||||
async function scanUser(groups: { users: number[] }[]) {
|
||||
await Promise.all(groups.map(async ({ users }) => {
|
||||
for (const user of users) {
|
||||
console.log('user', user)
|
||||
await new Promise(resolve => setTimeout(resolve, 30))
|
||||
}
|
||||
}))
|
||||
}
|
||||
|
||||
scanUser([
|
||||
{ users: [1, 2, 3, 4, 5] },
|
||||
{ users: [11, 12, 13, 14, 15] },
|
||||
])
|
64
tests/fixture/issue-1718/case2/output/index.ts
Normal file
64
tests/fixture/issue-1718/case2/output/index.ts
Normal file
@ -0,0 +1,64 @@
|
||||
function asyncGeneratorStep(gen, resolve, reject, _next, _throw, key, arg) {
|
||||
try {
|
||||
var info = gen[key](arg);
|
||||
var value = info.value;
|
||||
} catch (error) {
|
||||
reject(error);
|
||||
return;
|
||||
}
|
||||
if (info.done) {
|
||||
resolve(value);
|
||||
} else {
|
||||
Promise.resolve(value).then(_next, _throw);
|
||||
}
|
||||
}
|
||||
function _asyncToGenerator(fn) {
|
||||
return function() {
|
||||
var self = this, args = arguments;
|
||||
return new Promise(function(resolve, reject) {
|
||||
var gen = fn.apply(self, args);
|
||||
function _next(value) {
|
||||
asyncGeneratorStep(gen, resolve, reject, _next, _throw, "next", value);
|
||||
}
|
||||
function _throw(err) {
|
||||
asyncGeneratorStep(gen, resolve, reject, _next, _throw, "throw", err);
|
||||
}
|
||||
_next(undefined);
|
||||
});
|
||||
};
|
||||
}
|
||||
function _scanUser() {
|
||||
_scanUser = _asyncToGenerator(function*(groups) {
|
||||
yield Promise.all(groups.map(_asyncToGenerator(function*({ users }) {
|
||||
for (const user of users){
|
||||
console.log('user', user);
|
||||
yield new Promise((resolve)=>setTimeout(resolve, 30)
|
||||
);
|
||||
}
|
||||
})));
|
||||
});
|
||||
return _scanUser.apply(this, arguments);
|
||||
}
|
||||
function scanUser(groups) {
|
||||
return _scanUser.apply(this, arguments);
|
||||
}
|
||||
scanUser([
|
||||
{
|
||||
users: [
|
||||
1,
|
||||
2,
|
||||
3,
|
||||
4,
|
||||
5
|
||||
]
|
||||
},
|
||||
{
|
||||
users: [
|
||||
11,
|
||||
12,
|
||||
13,
|
||||
14,
|
||||
15
|
||||
]
|
||||
},
|
||||
]);
|
14
tests/fixture/issue-1729/case1/input/index.ts
Normal file
14
tests/fixture/issue-1729/case1/input/index.ts
Normal file
@ -0,0 +1,14 @@
|
||||
function createConstructor(callback) {
|
||||
let klass
|
||||
return (...args) => {
|
||||
if (klass === undefined) {
|
||||
klass = callback()
|
||||
}
|
||||
return new klass(...args)
|
||||
}
|
||||
}
|
||||
|
||||
const constructor = createConstructor(() => class {
|
||||
})
|
||||
|
||||
console.log(constructor())
|
78
tests/fixture/issue-1729/case1/output/index.ts
Normal file
78
tests/fixture/issue-1729/case1/output/index.ts
Normal file
@ -0,0 +1,78 @@
|
||||
function _arrayWithoutHoles(arr) {
|
||||
if (Array.isArray(arr)) {
|
||||
for(var i = 0, arr2 = new Array(arr.length); i < arr.length; i++){
|
||||
arr2[i] = arr[i];
|
||||
}
|
||||
return arr2;
|
||||
}
|
||||
}
|
||||
function _classCallCheck(instance, Constructor) {
|
||||
if (!(instance instanceof Constructor)) {
|
||||
throw new TypeError("Cannot call a class as a function");
|
||||
}
|
||||
}
|
||||
function isNativeReflectConstruct() {
|
||||
if (typeof Reflect === "undefined" || !Reflect.construct) return false;
|
||||
if (Reflect.construct.sham) return false;
|
||||
if (typeof Proxy === "function") return true;
|
||||
try {
|
||||
Date.prototype.toString.call(Reflect.construct(Date, [], function() {
|
||||
}));
|
||||
return true;
|
||||
} catch (e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
function _construct(Parent, args, Class) {
|
||||
if (isNativeReflectConstruct()) {
|
||||
_construct = Reflect.construct;
|
||||
} else {
|
||||
_construct = function _construct(Parent, args, Class) {
|
||||
var a = [
|
||||
null
|
||||
];
|
||||
a.push.apply(a, args);
|
||||
var Constructor = Function.bind.apply(Parent, a);
|
||||
var instance = new Constructor();
|
||||
if (Class) _setPrototypeOf(instance, Class.prototype);
|
||||
return instance;
|
||||
};
|
||||
}
|
||||
return _construct.apply(null, arguments);
|
||||
}
|
||||
function _iterableToArray(iter) {
|
||||
if (Symbol.iterator in Object(iter) || Object.prototype.toString.call(iter) === "[object Arguments]") return Array.from(iter);
|
||||
}
|
||||
function _nonIterableSpread() {
|
||||
throw new TypeError("Invalid attempt to spread non-iterable instance");
|
||||
}
|
||||
function _setPrototypeOf(o, p) {
|
||||
_setPrototypeOf = Object.setPrototypeOf || function _setPrototypeOf(o, p) {
|
||||
o.__proto__ = p;
|
||||
return o;
|
||||
};
|
||||
return _setPrototypeOf(o, p);
|
||||
}
|
||||
function _toConsumableArray(arr) {
|
||||
return _arrayWithoutHoles(arr) || _iterableToArray(arr) || _nonIterableSpread();
|
||||
}
|
||||
function createConstructor(callback) {
|
||||
var klass;
|
||||
return function() {
|
||||
for(var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++){
|
||||
args[_key] = arguments[_key];
|
||||
}
|
||||
if (klass === undefined) {
|
||||
klass = callback();
|
||||
}
|
||||
return _construct(klass, _toConsumableArray(args));
|
||||
};
|
||||
}
|
||||
var constructor = createConstructor(function() {
|
||||
var _class = function _class() {
|
||||
"use strict";
|
||||
_classCallCheck(this, _class);
|
||||
};
|
||||
return _class;
|
||||
});
|
||||
console.log(constructor());
|
5
tests/fixture/issue-1729/case2/input/.swcrc
Normal file
5
tests/fixture/issue-1729/case2/input/.swcrc
Normal file
@ -0,0 +1,5 @@
|
||||
{
|
||||
"jsc": {
|
||||
"target": "es2016"
|
||||
}
|
||||
}
|
14
tests/fixture/issue-1729/case2/input/index.ts
Normal file
14
tests/fixture/issue-1729/case2/input/index.ts
Normal file
@ -0,0 +1,14 @@
|
||||
function createConstructor(callback) {
|
||||
let klass
|
||||
return (...args) => {
|
||||
if (klass === undefined) {
|
||||
klass = callback()
|
||||
}
|
||||
return new klass(...args)
|
||||
}
|
||||
}
|
||||
|
||||
const constructor = createConstructor(() => class {
|
||||
})
|
||||
|
||||
console.log(constructor())
|
13
tests/fixture/issue-1729/case2/output/index.ts
Normal file
13
tests/fixture/issue-1729/case2/output/index.ts
Normal file
@ -0,0 +1,13 @@
|
||||
function createConstructor(callback) {
|
||||
let klass;
|
||||
return (...args)=>{
|
||||
if (klass === undefined) {
|
||||
klass = callback();
|
||||
}
|
||||
return new klass(...args);
|
||||
};
|
||||
}
|
||||
const constructor = createConstructor(()=>class {
|
||||
}
|
||||
);
|
||||
console.log(constructor());
|
5
tests/fixture/issue-1729/case3/input/.swcrc
Normal file
5
tests/fixture/issue-1729/case3/input/.swcrc
Normal file
@ -0,0 +1,5 @@
|
||||
{
|
||||
"jsc": {
|
||||
"target": "es2020"
|
||||
}
|
||||
}
|
14
tests/fixture/issue-1729/case3/input/index.ts
Normal file
14
tests/fixture/issue-1729/case3/input/index.ts
Normal file
@ -0,0 +1,14 @@
|
||||
function createConstructor(callback) {
|
||||
let klass
|
||||
return (...args) => {
|
||||
if (klass === undefined) {
|
||||
klass = callback()
|
||||
}
|
||||
return new klass(...args)
|
||||
}
|
||||
}
|
||||
|
||||
const constructor = createConstructor(() => class {
|
||||
})
|
||||
|
||||
console.log(constructor())
|
13
tests/fixture/issue-1729/case3/output/index.ts
Normal file
13
tests/fixture/issue-1729/case3/output/index.ts
Normal file
@ -0,0 +1,13 @@
|
||||
function createConstructor(callback) {
|
||||
let klass;
|
||||
return (...args)=>{
|
||||
if (klass === undefined) {
|
||||
klass = callback();
|
||||
}
|
||||
return new klass(...args);
|
||||
};
|
||||
}
|
||||
const constructor = createConstructor(()=>class {
|
||||
}
|
||||
);
|
||||
console.log(constructor());
|
8
tests/fixture/issue-1729/case4/input/.swcrc
Normal file
8
tests/fixture/issue-1729/case4/input/.swcrc
Normal file
@ -0,0 +1,8 @@
|
||||
{
|
||||
"jsc": {
|
||||
"parser": {
|
||||
"syntax": "typescript"
|
||||
},
|
||||
"target": "es2020"
|
||||
}
|
||||
}
|
14
tests/fixture/issue-1729/case4/input/index.ts
Normal file
14
tests/fixture/issue-1729/case4/input/index.ts
Normal file
@ -0,0 +1,14 @@
|
||||
function createConstructor(callback) {
|
||||
let klass
|
||||
return (...args) => {
|
||||
if (klass === undefined) {
|
||||
klass = callback()
|
||||
}
|
||||
return new klass(...args)
|
||||
}
|
||||
}
|
||||
|
||||
const constructor = createConstructor(() => class {
|
||||
})
|
||||
|
||||
console.log(constructor())
|
15
tests/fixture/issue-1729/case4/output/index.ts
Normal file
15
tests/fixture/issue-1729/case4/output/index.ts
Normal file
@ -0,0 +1,15 @@
|
||||
function createConstructor(callback) {
|
||||
let klass;
|
||||
return (...args)=>{
|
||||
if (klass === undefined) {
|
||||
klass = callback();
|
||||
}
|
||||
return new klass(...args);
|
||||
};
|
||||
}
|
||||
const constructor = createConstructor(()=>{
|
||||
class _class {
|
||||
}
|
||||
return _class;
|
||||
});
|
||||
console.log(constructor());
|
Loading…
Reference in New Issue
Block a user