Skip to content

Commit 781db84

Browse files
authored
fix array destructuring prefix operator side effects (#1405) (#1708)
* fix array destructuring not preserving evaluation order with side effects (#1405) * add more test cases for array destructuring side effects
1 parent c3b3a8b commit 781db84

2 files changed

Lines changed: 29 additions & 2 deletions

File tree

src/transformation/visitors/variable-declaration.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ import { createCallableTable, isFunctionTypeWithProperties } from "./function";
1212
import { transformIdentifier } from "./identifier";
1313
import { isMultiReturnCall } from "./language-extensions/multi";
1414
import { transformPropertyName } from "./literal";
15-
import { moveToPrecedingTemp } from "./expression-list";
15+
import { moveToPrecedingTemp, transformExpressionList } from "./expression-list";
1616

1717
export function transformArrayBindingElement(
1818
context: TransformationContext,
@@ -205,7 +205,7 @@ export function transformBindingVariableDeclaration(
205205
// Don't unpack array literals
206206
const values =
207207
initializer.elements.length > 0
208-
? initializer.elements.map(e => context.transformExpression(e))
208+
? transformExpressionList(context, initializer.elements)
209209
: lua.createNilLiteral();
210210
statements.push(...createLocalOrExportedOrGlobalDeclaration(context, vars, values, initializer));
211211
} else {

test/unit/destructuring.spec.ts

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -226,6 +226,33 @@ describe("array destructuring optimization", () => {
226226
.expectToMatchJsResult();
227227
});
228228

229+
test("array literal with side effects in elements", () => {
230+
util.testFunction`
231+
const arr = [1, 2];
232+
let i = 0;
233+
let [v1, v2] = [arr[i], arr[++i]];
234+
return { v1, v2 };
235+
`.expectToMatchJsResult();
236+
});
237+
238+
test("array literal with many side effects in elements", () => {
239+
util.testFunction`
240+
const arr = [10, 20, 30, 40];
241+
let i = 0;
242+
let [v1, v2, v3, v4] = [arr[i++], arr[i++], arr[i++], arr[i++]];
243+
return { v1, v2, v3, v4 };
244+
`.expectToMatchJsResult();
245+
});
246+
247+
test("array literal with mixed pure and impure elements", () => {
248+
util.testFunction`
249+
const arr = [10, 20, 30];
250+
let i = 0;
251+
let [v1, v2, v3] = [1, arr[++i], 2];
252+
return { v1, v2, v3, i };
253+
`.expectToMatchJsResult();
254+
});
255+
229256
test("array union", () => {
230257
util.testFunction`
231258
const array: [string] | [] = ["bar"];

0 commit comments

Comments
 (0)