From 025430344d1e67ee3f9b17c6163dd0e3e763700c Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Mon, 22 Jul 2019 11:57:36 -0700 Subject: [PATCH] Fix object spread runtime semantics --- src/compiler/transformers/es2018.ts | 31 +++++++- src/testRunner/tsconfig.json | 1 + .../unittests/evaluation/objectRest.ts | 28 +++++++ ...iveInternalTypesProduceUniqueTypeParams.js | 2 +- .../excessPropertyCheckWithSpread.js | 2 +- .../reference/genericIsNeverEmptyObject.js | 2 +- .../objectLiteralFreshnessWithSpread.js | 2 +- .../reference/objectLiteralNormalization.js | 2 +- tests/baselines/reference/objectRestForOf.js | 2 +- tests/baselines/reference/objectSpread.js | 76 +++++++++---------- .../reference/objectSpreadComputedProperty.js | 2 +- .../reference/objectSpreadIndexSignature.js | 4 +- .../reference/objectSpreadNegative.js | 8 +- .../reference/objectSpreadNegativeParse.js | 2 +- .../reference/objectSpreadStrictNull.js | 20 ++--- ...preadWithinMethodWithinObjectWithSpread.js | 4 +- .../spreadContextualTypedBindingPattern.js | 2 +- .../baselines/reference/spreadIntersection.js | 2 +- .../baselines/reference/spreadNonPrimitive.js | 2 +- tests/baselines/reference/spreadUnion.js | 4 +- tests/baselines/reference/spreadUnion2.js | 8 +- tests/baselines/reference/spreadUnion3.js | 2 +- .../unionExcessPropsWithPartialMember.js | 2 +- tests/baselines/reference/unknownType1.js | 4 +- ...useBeforeDeclaration_propertyAssignment.js | 2 +- 25 files changed, 135 insertions(+), 81 deletions(-) create mode 100644 src/testRunner/unittests/evaluation/objectRest.ts diff --git a/src/compiler/transformers/es2018.ts b/src/compiler/transformers/es2018.ts index 89c43dcf599cf..50fb9f04d1abf 100644 --- a/src/compiler/transformers/es2018.ts +++ b/src/compiler/transformers/es2018.ts @@ -229,14 +229,39 @@ namespace ts { if (node.transformFlags & TransformFlags.ContainsObjectRestOrSpread) { // spread elements emit like so: // non-spread elements are chunked together into object literals, and then all are passed to __assign: - // { a, ...o, b } => __assign({a}, o, {b}); + // { a, ...o, b } => __assign(__assign({a}, o), {b}); // If the first element is a spread element, then the first argument to __assign is {}: - // { ...o, a, b, ...o2 } => __assign({}, o, {a, b}, o2) + // { ...o, a, b, ...o2 } => __assign(__assign(__assign({}, o), {a, b}), o2) + // + // We cannot call __assign with more than two elements, since any element could cause side effects. For + // example: + // var k = { a: 1, b: 2 }; + // var o = { a: 3, ...k, b: k.a++ }; + // // expected: { a: 1, b: 1 } + // If we translate the above to `__assign({ a: 3 }, k, { b: k.a++ })`, the `k.a++` will evaluate before + // `k` is spread and we end up with `{ a: 2, b: 1 }`. + // + // This also occurs for spread elements, not just property assignments: + // var k = { a: 1, get b() { l = { z: 9 }; return 2; } }; + // var l = { c: 3 }; + // var o = { ...k, ...l }; + // // expected: { a: 1, b: 2, z: 9 } + // If we translate the above to `__assign({}, k, l)`, the `l` will evaluate before `k` is spread and we + // end up with `{ a: 1, b: 2, c: 3 }` const objects = chunkObjectLiteralElements(node.properties); if (objects.length && objects[0].kind !== SyntaxKind.ObjectLiteralExpression) { objects.unshift(createObjectLiteral()); } - return createAssignHelper(context, objects); + let expression: Expression = objects[0]; + if (objects.length > 1) { + for (let i = 1; i < objects.length; i++) { + expression = createAssignHelper(context, [expression, objects[i]]); + } + return expression; + } + else { + return createAssignHelper(context, objects); + } } return visitEachChild(node, visitor, context); } diff --git a/src/testRunner/tsconfig.json b/src/testRunner/tsconfig.json index b2e7e3e78b947..9ea6c4c85cea2 100644 --- a/src/testRunner/tsconfig.json +++ b/src/testRunner/tsconfig.json @@ -74,6 +74,7 @@ "unittests/evaluation/asyncArrow.ts", "unittests/evaluation/asyncGenerator.ts", "unittests/evaluation/forAwaitOf.ts", + "unittests/evaluation/objectRest.ts", "unittests/services/cancellableLanguageServiceOperations.ts", "unittests/services/colorization.ts", "unittests/services/convertToAsyncFunction.ts", diff --git a/src/testRunner/unittests/evaluation/objectRest.ts b/src/testRunner/unittests/evaluation/objectRest.ts new file mode 100644 index 0000000000000..272ba51ffbeb5 --- /dev/null +++ b/src/testRunner/unittests/evaluation/objectRest.ts @@ -0,0 +1,28 @@ +describe("unittests:: evaluation:: objectRest", () => { + // https://github.com/microsoft/TypeScript/issues/31469 + it("side effects in property assignment", async () => { + const result = evaluator.evaluateTypeScript(` + const k = { a: 1, b: 2 }; + const o = { a: 3, ...k, b: k.a++ }; + export const output = o; + `); + assert.deepEqual(result.output, { a: 1, b: 1 }); + }); + it("side effects in during spread", async () => { + const result = evaluator.evaluateTypeScript(` + const k = { a: 1, get b() { l = { c: 9 }; return 2; } }; + let l = { c: 3 }; + const o = { ...k, ...l }; + export const output = o; + `); + assert.deepEqual(result.output, { a: 1, b: 2, c: 9 }); + }); + it("trailing literal-valued object-literal", async () => { + const result = evaluator.evaluateTypeScript(` + const k = { a: 1 } + const o = { ...k, ...{ b: 2 } }; + export const output = o; + `); + assert.deepEqual(result.output, { a: 1, b: 2 }); + }); +}); diff --git a/tests/baselines/reference/declarationsWithRecursiveInternalTypesProduceUniqueTypeParams.js b/tests/baselines/reference/declarationsWithRecursiveInternalTypesProduceUniqueTypeParams.js index 913e82292bf6a..b043fe275cc3a 100644 --- a/tests/baselines/reference/declarationsWithRecursiveInternalTypesProduceUniqueTypeParams.js +++ b/tests/baselines/reference/declarationsWithRecursiveInternalTypesProduceUniqueTypeParams.js @@ -73,7 +73,7 @@ exports.testRecFun = function (parent) { return { result: parent, deeper: function (child) { - return exports.testRecFun(__assign({}, parent, child)); + return exports.testRecFun(__assign(__assign({}, parent), child)); } }; }; diff --git a/tests/baselines/reference/excessPropertyCheckWithSpread.js b/tests/baselines/reference/excessPropertyCheckWithSpread.js index c08e4738965ac..1b105de791841 100644 --- a/tests/baselines/reference/excessPropertyCheckWithSpread.js +++ b/tests/baselines/reference/excessPropertyCheckWithSpread.js @@ -30,4 +30,4 @@ var __assign = (this && this.__assign) || function () { return __assign.apply(this, arguments); }; f(__assign({ a: 1 }, i)); -f(__assign({ a: 1 }, l, r)); +f(__assign(__assign({ a: 1 }, l), r)); diff --git a/tests/baselines/reference/genericIsNeverEmptyObject.js b/tests/baselines/reference/genericIsNeverEmptyObject.js index 692f34bfcc48c..ec489da75a9a6 100644 --- a/tests/baselines/reference/genericIsNeverEmptyObject.js +++ b/tests/baselines/reference/genericIsNeverEmptyObject.js @@ -37,7 +37,7 @@ var __rest = (this && this.__rest) || function (s, e) { }; function test(obj) { var a = obj.a, rest = __rest(obj, ["a"]); - return __assign({}, rest, { b: a }); + return __assign(__assign({}, rest), { b: a }); } var o1 = { a: 'hello', x: 42 }; var o2 = test(o1); diff --git a/tests/baselines/reference/objectLiteralFreshnessWithSpread.js b/tests/baselines/reference/objectLiteralFreshnessWithSpread.js index 73962db32abfb..ad87fd0557db1 100644 --- a/tests/baselines/reference/objectLiteralFreshnessWithSpread.js +++ b/tests/baselines/reference/objectLiteralFreshnessWithSpread.js @@ -16,4 +16,4 @@ var __assign = (this && this.__assign) || function () { return __assign.apply(this, arguments); }; var x = { b: 1, extra: 2 }; -var xx = __assign({ a: 1 }, x, { z: 3 }); // error for 'z', no error for 'extra' +var xx = __assign(__assign({ a: 1 }, x), { z: 3 }); // error for 'z', no error for 'extra' diff --git a/tests/baselines/reference/objectLiteralNormalization.js b/tests/baselines/reference/objectLiteralNormalization.js index 1a8aa8d4b043d..aa37bdc2c5ee7 100644 --- a/tests/baselines/reference/objectLiteralNormalization.js +++ b/tests/baselines/reference/objectLiteralNormalization.js @@ -80,7 +80,7 @@ a2 = { a: "def" }; a2 = {}; a2 = { a: "def", b: 20 }; // Error a2 = { a: 1 }; // Error -var b2 = __assign({}, b1, { z: 55 }); +var b2 = __assign(__assign({}, b1), { z: 55 }); var b3 = __assign({}, b2); var c1 = !true ? {} : opts; var c2 = !true ? opts : {}; diff --git a/tests/baselines/reference/objectRestForOf.js b/tests/baselines/reference/objectRestForOf.js index f946e42444cab..49ebf7c4c1726 100644 --- a/tests/baselines/reference/objectRestForOf.js +++ b/tests/baselines/reference/objectRestForOf.js @@ -37,7 +37,7 @@ for (let _b of array) { ({ x: xx } = _b, rrestOff = __rest(_b, ["x"])); [xx, rrestOff]; } -for (const norest of array.map(a => (Object.assign({}, a, { x: 'a string' })))) { +for (const norest of array.map(a => (Object.assign(Object.assign({}, a), { x: 'a string' })))) { [norest.x, norest.y]; // x is now a string. who knows why. } diff --git a/tests/baselines/reference/objectSpread.js b/tests/baselines/reference/objectSpread.js index b7d3e858c797b..1265cc889ff79 100644 --- a/tests/baselines/reference/objectSpread.js +++ b/tests/baselines/reference/objectSpread.js @@ -171,45 +171,45 @@ var __assign = (this && this.__assign) || function () { var o = { a: 1, b: 'no' }; var o2 = { b: 'yes', c: true }; var swap = { a: 'yes', b: -1 }; -var addAfter = __assign({}, o, { c: false }); +var addAfter = __assign(__assign({}, o), { c: false }); var addBefore = __assign({ c: false }, o); // Note: ignore still changes the order that properties are printed var ignore = __assign({ b: 'ignored' }, o); -var override = __assign({}, o, { b: 'override' }); -var nested = __assign({}, __assign({ a: 3 }, { b: false, c: 'overriden' }), { c: 'whatever' }); -var combined = __assign({}, o, o2); -var combinedBefore = __assign({ b: 'ok' }, o, o2); -var combinedMid = __assign({}, o, { b: 'ok' }, o2); -var combinedAfter = __assign({}, o, o2, { b: 'ok' }); -var combinedNested = __assign({}, __assign({ a: 4 }, { b: false, c: 'overriden' }), { d: 'actually new' }, { a: 5, d: 'maybe new' }); -var combinedNestedChangeType = __assign({}, __assign({ a: 1 }, { b: false, c: 'overriden' }), { c: -1 }); +var override = __assign(__assign({}, o), { b: 'override' }); +var nested = __assign(__assign({}, __assign({ a: 3 }, { b: false, c: 'overriden' })), { c: 'whatever' }); +var combined = __assign(__assign({}, o), o2); +var combinedBefore = __assign(__assign({ b: 'ok' }, o), o2); +var combinedMid = __assign(__assign(__assign({}, o), { b: 'ok' }), o2); +var combinedAfter = __assign(__assign(__assign({}, o), o2), { b: 'ok' }); +var combinedNested = __assign(__assign(__assign({}, __assign({ a: 4 }, { b: false, c: 'overriden' })), { d: 'actually new' }), { a: 5, d: 'maybe new' }); +var combinedNestedChangeType = __assign(__assign({}, __assign({ a: 1 }, { b: false, c: 'overriden' })), { c: -1 }); var propertyNested = { a: __assign({}, o) }; // accessors don't copy the descriptor // (which means that readonly getters become read/write properties) var op = { get a() { return 6; } }; -var getter = __assign({}, op, { c: 7 }); +var getter = __assign(__assign({}, op), { c: 7 }); getter.a = 12; // functions result in { } var spreadFunc = __assign({}, (function () { })); function from16326(header, authToken) { - return __assign({}, this.header, header, authToken && { authToken: authToken }); + return __assign(__assign(__assign({}, this.header), header), authToken && { authToken: authToken }); } // boolean && T results in Partial function conditionalSpreadBoolean(b) { var o = { x: 12, y: 13 }; - o = __assign({}, o, b && { x: 14 }); + o = __assign(__assign({}, o), b && { x: 14 }); var o2 = __assign({}, b && { x: 21 }); return o; } function conditionalSpreadNumber(nt) { var o = { x: 15, y: 16 }; - o = __assign({}, o, nt && { x: nt }); + o = __assign(__assign({}, o), nt && { x: nt }); var o2 = __assign({}, nt && { x: nt }); return o; } function conditionalSpreadString(st) { var o = { x: 'hi', y: 17 }; - o = __assign({}, o, st && { x: st }); + o = __assign(__assign({}, o), st && { x: st }); var o2 = __assign({}, st && { x: st }); return o; } @@ -227,31 +227,31 @@ var C = /** @class */ (function () { var c = new C(); var spreadC = __assign({}, c); // own methods are enumerable -var cplus = __assign({}, c, { plus: function () { return this.p + 1; } }); +var cplus = __assign(__assign({}, c), { plus: function () { return this.p + 1; } }); cplus.plus(); // new field's type conflicting with existing field is OK -var changeTypeAfter = __assign({}, o, { a: 'wrong type?' }); +var changeTypeAfter = __assign(__assign({}, o), { a: 'wrong type?' }); var changeTypeBefore = __assign({ a: 'wrong type?' }, o); -var changeTypeBoth = __assign({}, o, swap); +var changeTypeBoth = __assign(__assign({}, o), swap); // optional function container(definiteBoolean, definiteString, optionalString, optionalNumber) { var _a, _b, _c; - var optionalUnionStops = __assign({}, definiteBoolean, definiteString, optionalNumber); - var optionalUnionDuplicates = __assign({}, definiteBoolean, definiteString, optionalString, optionalNumber); - var allOptional = __assign({}, optionalString, optionalNumber); + var optionalUnionStops = __assign(__assign(__assign({}, definiteBoolean), definiteString), optionalNumber); + var optionalUnionDuplicates = __assign(__assign(__assign(__assign({}, definiteBoolean), definiteString), optionalString), optionalNumber); + var allOptional = __assign(__assign({}, optionalString), optionalNumber); // computed property - var computedFirst = __assign((_a = {}, _a['before everything'] = 12, _a), o, { b: 'yes' }); - var computedMiddle = __assign({}, o, (_b = {}, _b['in the middle'] = 13, _b.b = 'maybe?', _b), o2); - var computedAfter = __assign({}, o, (_c = { b: 'yeah' }, _c['at the end'] = 14, _c)); + var computedFirst = __assign(__assign((_a = {}, _a['before everything'] = 12, _a), o), { b: 'yes' }); + var computedMiddle = __assign(__assign(__assign({}, o), (_b = {}, _b['in the middle'] = 13, _b.b = 'maybe?', _b)), o2); + var computedAfter = __assign(__assign({}, o), (_c = { b: 'yeah' }, _c['at the end'] = 14, _c)); } // shortcut syntax var a = 12; -var shortCutted = __assign({}, o, { a: a }); +var shortCutted = __assign(__assign({}, o), { a: a }); // non primitive var spreadNonPrimitive = __assign({}, {}); // generic spreads function f(t, u) { - return __assign({}, t, u, { id: 'id' }); + return __assign(__assign(__assign({}, t), u), { id: 'id' }); } var exclusive = f({ a: 1, b: 'yes' }, { c: 'no', d: false }); var overlap = f({ a: 1 }, { a: 2, b: 'extra' }); @@ -259,20 +259,20 @@ var overlapConflict = f({ a: 1 }, { a: 'mismatch' }); var overwriteId = f({ a: 1, id: true }, { c: 1, d: 'no' }); function genericSpread(t, u, v, w, obj) { var x01 = __assign({}, t); - var x02 = __assign({}, t, t); - var x03 = __assign({}, t, u); - var x04 = __assign({}, u, t); + var x02 = __assign(__assign({}, t), t); + var x03 = __assign(__assign({}, t), u); + var x04 = __assign(__assign({}, u), t); var x05 = __assign({ a: 5, b: 'hi' }, t); - var x06 = __assign({}, t, { a: 5, b: 'hi' }); - var x07 = __assign({ a: 5, b: 'hi' }, t, { c: true }, obj); - var x09 = __assign({ a: 5 }, t, { b: 'hi', c: true }, obj); - var x10 = __assign({ a: 5 }, t, { b: 'hi' }, u, obj); + var x06 = __assign(__assign({}, t), { a: 5, b: 'hi' }); + var x07 = __assign(__assign(__assign({ a: 5, b: 'hi' }, t), { c: true }), obj); + var x09 = __assign(__assign(__assign({ a: 5 }, t), { b: 'hi', c: true }), obj); + var x10 = __assign(__assign(__assign(__assign({ a: 5 }, t), { b: 'hi' }), u), obj); var x11 = __assign({}, v); - var x12 = __assign({}, v, obj); + var x12 = __assign(__assign({}, v), obj); var x13 = __assign({}, w); - var x14 = __assign({}, w, obj); - var x15 = __assign({}, t, v); - var x16 = __assign({}, t, w); - var x17 = __assign({}, t, w, obj); - var x18 = __assign({}, t, v, w); + var x14 = __assign(__assign({}, w), obj); + var x15 = __assign(__assign({}, t), v); + var x16 = __assign(__assign({}, t), w); + var x17 = __assign(__assign(__assign({}, t), w), obj); + var x18 = __assign(__assign(__assign({}, t), v), w); } diff --git a/tests/baselines/reference/objectSpreadComputedProperty.js b/tests/baselines/reference/objectSpreadComputedProperty.js index b81b889b2cc8e..a28ceab111f8b 100644 --- a/tests/baselines/reference/objectSpreadComputedProperty.js +++ b/tests/baselines/reference/objectSpreadComputedProperty.js @@ -30,5 +30,5 @@ function f() { var a = null; var o1 = __assign({}, (_a = {}, _a[n] = n, _a)); var o2 = __assign({}, (_b = {}, _b[a] = n, _b)); - var o3 = __assign((_c = {}, _c[a] = n, _c), {}, (_d = {}, _d[n] = n, _d), {}, (_e = {}, _e[m] = m, _e)); + var o3 = __assign(__assign(__assign(__assign((_c = {}, _c[a] = n, _c), {}), (_d = {}, _d[n] = n, _d)), {}), (_e = {}, _e[m] = m, _e)); } diff --git a/tests/baselines/reference/objectSpreadIndexSignature.js b/tests/baselines/reference/objectSpreadIndexSignature.js index aef78611f38fe..8c461e39971d0 100644 --- a/tests/baselines/reference/objectSpreadIndexSignature.js +++ b/tests/baselines/reference/objectSpreadIndexSignature.js @@ -30,10 +30,10 @@ var __assign = (this && this.__assign) || function () { }; return __assign.apply(this, arguments); }; -var i = __assign({}, indexed1, { b: 11 }); +var i = __assign(__assign({}, indexed1), { b: 11 }); // only indexed has indexer, so i[101]: any i[101]; -var ii = __assign({}, indexed1, indexed2); +var ii = __assign(__assign({}, indexed1), indexed2); // both have indexer, so i[1001]: number | boolean ii[1001]; indexed3 = __assign({}, b ? indexed3 : undefined); diff --git a/tests/baselines/reference/objectSpreadNegative.js b/tests/baselines/reference/objectSpreadNegative.js index 23de5699ce6e8..6151f2d30b7c4 100644 --- a/tests/baselines/reference/objectSpreadNegative.js +++ b/tests/baselines/reference/objectSpreadNegative.js @@ -85,11 +85,11 @@ var PublicX = /** @class */ (function () { }()); var publicX; var privateOptionalX; -var o2 = __assign({}, publicX, privateOptionalX); +var o2 = __assign(__assign({}, publicX), privateOptionalX); var sn = o2.x; // error, x is private var optionalString; var optionalNumber; -var allOptional = __assign({}, optionalString, optionalNumber); +var allOptional = __assign(__assign({}, optionalString), optionalNumber); ; ; var spread = __assign({ b: true }, { s: "foo" }); @@ -97,8 +97,8 @@ spread = { s: "foo" }; // error, missing 'b' var b = { b: false }; spread = b; // error, missing 's' // literal repeats are not allowed, but spread repeats are fine -var duplicated = __assign({ b: 'bad' }, o, { b: 'bad' }, o2, { b: 'bad' }); -var duplicatedSpread = __assign({}, o, o); +var duplicated = __assign(__assign(__assign(__assign({ b: 'bad' }, o), { b: 'bad' }), o2), { b: 'bad' }); +var duplicatedSpread = __assign(__assign({}, o), o); // primitives are not allowed, except for falsy ones var spreadNum = __assign({}, 12); var spreadSum = __assign({}, 1 + 1); diff --git a/tests/baselines/reference/objectSpreadNegativeParse.js b/tests/baselines/reference/objectSpreadNegativeParse.js index 1eb384383fbc0..11809b96b92cf 100644 --- a/tests/baselines/reference/objectSpreadNegativeParse.js +++ b/tests/baselines/reference/objectSpreadNegativeParse.js @@ -21,4 +21,4 @@ var o7 = __assign({}, o ? : ); var o8 = __assign({}, * o); var o9 = __assign({}, matchMedia()), _a = void 0; ; -var o10 = __assign({}, get, { x: function () { return 12; } }); +var o10 = __assign(__assign({}, get), { x: function () { return 12; } }); diff --git a/tests/baselines/reference/objectSpreadStrictNull.js b/tests/baselines/reference/objectSpreadStrictNull.js index 737c1d3e038d7..f95c2582b26df 100644 --- a/tests/baselines/reference/objectSpreadStrictNull.js +++ b/tests/baselines/reference/objectSpreadStrictNull.js @@ -58,21 +58,21 @@ var __assign = (this && this.__assign) || function () { }; function f(definiteBoolean, definiteString, optionalString, optionalNumber, undefinedString, undefinedNumber) { // optional - var optionalUnionStops = __assign({}, definiteBoolean, definiteString, optionalNumber); - var optionalUnionDuplicates = __assign({}, definiteBoolean, definiteString, optionalString, optionalNumber); - var allOptional = __assign({}, optionalString, optionalNumber); + var optionalUnionStops = __assign(__assign(__assign({}, definiteBoolean), definiteString), optionalNumber); + var optionalUnionDuplicates = __assign(__assign(__assign(__assign({}, definiteBoolean), definiteString), optionalString), optionalNumber); + var allOptional = __assign(__assign({}, optionalString), optionalNumber); // undefined - var undefinedUnionStops = __assign({}, definiteBoolean, definiteString, undefinedNumber); - var undefinedUnionDuplicates = __assign({}, definiteBoolean, definiteString, undefinedString, undefinedNumber); - var allUndefined = __assign({}, undefinedString, undefinedNumber); - var undefinedWithOptionalContinues = __assign({}, definiteBoolean, undefinedString, optionalNumber); + var undefinedUnionStops = __assign(__assign(__assign({}, definiteBoolean), definiteString), undefinedNumber); + var undefinedUnionDuplicates = __assign(__assign(__assign(__assign({}, definiteBoolean), definiteString), undefinedString), undefinedNumber); + var allUndefined = __assign(__assign({}, undefinedString), undefinedNumber); + var undefinedWithOptionalContinues = __assign(__assign(__assign({}, definiteBoolean), undefinedString), optionalNumber); } var m = { title: "The Matrix", yearReleased: 1999 }; // should error here because title: undefined is not assignable to string -var x = __assign({}, m, { title: undefined }); +var x = __assign(__assign({}, m), { title: undefined }); function g(fields, partialFields, nearlyPartialFields) { // ok, undefined is stripped from optional properties when spread - fields = __assign({}, fields, partialFields); + fields = __assign(__assign({}, fields), partialFields); // error: not optional, undefined remains - fields = __assign({}, fields, nearlyPartialFields); + fields = __assign(__assign({}, fields), nearlyPartialFields); } diff --git a/tests/baselines/reference/objectSpreadWithinMethodWithinObjectWithSpread.js b/tests/baselines/reference/objectSpreadWithinMethodWithinObjectWithSpread.js index 89744f9f8e547..900dd89a820fa 100644 --- a/tests/baselines/reference/objectSpreadWithinMethodWithinObjectWithSpread.js +++ b/tests/baselines/reference/objectSpreadWithinMethodWithinObjectWithSpread.js @@ -24,6 +24,6 @@ var __assign = (this && this.__assign) || function () { return __assign.apply(this, arguments); }; var obj = {}; -var a = __assign({}, obj, { prop: function () { - return __assign({}, obj, { metadata: 213 }); +var a = __assign(__assign({}, obj), { prop: function () { + return __assign(__assign({}, obj), { metadata: 213 }); } }); diff --git a/tests/baselines/reference/spreadContextualTypedBindingPattern.js b/tests/baselines/reference/spreadContextualTypedBindingPattern.js index 7b2128e4a5337..c95cccedbf3c2 100644 --- a/tests/baselines/reference/spreadContextualTypedBindingPattern.js +++ b/tests/baselines/reference/spreadContextualTypedBindingPattern.js @@ -25,4 +25,4 @@ var __assign = (this && this.__assign) || function () { return __assign.apply(this, arguments); }; // [ts] Initializer provides no value for this binding element and the binding element has no default value. -var _a = __assign({}, bob, alice), naam = _a.naam, age = _a.age; +var _a = __assign(__assign({}, bob), alice), naam = _a.naam, age = _a.age; diff --git a/tests/baselines/reference/spreadIntersection.js b/tests/baselines/reference/spreadIntersection.js index 2defebc5ce1a8..fe746734d6d2b 100644 --- a/tests/baselines/reference/spreadIntersection.js +++ b/tests/baselines/reference/spreadIntersection.js @@ -23,4 +23,4 @@ var intersection; var o1; var o1 = __assign({}, intersection); var o2; -var o2 = __assign({}, intersection, { c: false }); +var o2 = __assign(__assign({}, intersection), { c: false }); diff --git a/tests/baselines/reference/spreadNonPrimitive.js b/tests/baselines/reference/spreadNonPrimitive.js index 81b23a584fa0b..50b2c1cdec87f 100644 --- a/tests/baselines/reference/spreadNonPrimitive.js +++ b/tests/baselines/reference/spreadNonPrimitive.js @@ -15,4 +15,4 @@ var __assign = (this && this.__assign) || function () { }; return __assign.apply(this, arguments); }; -var x = __assign({ a: 1 }, o, { b: 2 }); +var x = __assign(__assign({ a: 1 }, o), { b: 2 }); diff --git a/tests/baselines/reference/spreadUnion.js b/tests/baselines/reference/spreadUnion.js index 42ec336c67dda..03220cef0e851 100644 --- a/tests/baselines/reference/spreadUnion.js +++ b/tests/baselines/reference/spreadUnion.js @@ -26,6 +26,6 @@ var union; var o3; var o3 = __assign({}, union); var o4; -var o4 = __assign({}, union, { a: false }); +var o4 = __assign(__assign({}, union), { a: false }); var o5; -var o5 = __assign({}, union, union); +var o5 = __assign(__assign({}, union), union); diff --git a/tests/baselines/reference/spreadUnion2.js b/tests/baselines/reference/spreadUnion2.js index 2678ce707cf0f..b48209cfc0154 100644 --- a/tests/baselines/reference/spreadUnion2.js +++ b/tests/baselines/reference/spreadUnion2.js @@ -37,9 +37,9 @@ var o1 = __assign({}, undefinedUnion); var o2; var o2 = __assign({}, nullUnion); var o3; -var o3 = __assign({}, undefinedUnion, nullUnion); -var o3 = __assign({}, nullUnion, undefinedUnion); +var o3 = __assign(__assign({}, undefinedUnion), nullUnion); +var o3 = __assign(__assign({}, nullUnion), undefinedUnion); var o4; -var o4 = __assign({}, undefinedUnion, undefinedUnion); +var o4 = __assign(__assign({}, undefinedUnion), undefinedUnion); var o5; -var o5 = __assign({}, nullUnion, nullUnion); +var o5 = __assign(__assign({}, nullUnion), nullUnion); diff --git a/tests/baselines/reference/spreadUnion3.js b/tests/baselines/reference/spreadUnion3.js index 2175889db7074..dda735a2dc164 100644 --- a/tests/baselines/reference/spreadUnion3.js +++ b/tests/baselines/reference/spreadUnion3.js @@ -42,5 +42,5 @@ function g(t) { g(); g(undefined); g(null); -var x = __assign({}, nullAndUndefinedUnion, nullAndUndefinedUnion); +var x = __assign(__assign({}, nullAndUndefinedUnion), nullAndUndefinedUnion); var y = __assign({}, nullAndUndefinedUnion); diff --git a/tests/baselines/reference/unionExcessPropsWithPartialMember.js b/tests/baselines/reference/unionExcessPropsWithPartialMember.js index cefd480bba81a..f7e88d35a4129 100644 --- a/tests/baselines/reference/unionExcessPropsWithPartialMember.js +++ b/tests/baselines/reference/unionExcessPropsWithPartialMember.js @@ -28,4 +28,4 @@ var __assign = (this && this.__assign) || function () { }; return __assign.apply(this, arguments); }; -ab = __assign({}, a, { y: null }); // Should be allowed, since `y` is missing on `A` +ab = __assign(__assign({}, a), { y: null }); // Should be allowed, since `y` is missing on `A` diff --git a/tests/baselines/reference/unknownType1.js b/tests/baselines/reference/unknownType1.js index 688fbf8f93c01..8bd340de02060 100644 --- a/tests/baselines/reference/unknownType1.js +++ b/tests/baselines/reference/unknownType1.js @@ -279,8 +279,8 @@ function f25() { // Spread of unknown causes result to be unknown function f26(x, y, z) { var o1 = __assign({ a: 42 }, x); // { a: number } - var o2 = __assign({ a: 42 }, x, y); // unknown - var o3 = __assign({ a: 42 }, x, y, z); // any + var o2 = __assign(__assign({ a: 42 }, x), y); // unknown + var o3 = __assign(__assign(__assign({ a: 42 }, x), y), z); // any } // Functions with unknown return type don't need return expressions function f27() { diff --git a/tests/baselines/reference/useBeforeDeclaration_propertyAssignment.js b/tests/baselines/reference/useBeforeDeclaration_propertyAssignment.js index 47968d429ade5..4ee81065518e1 100644 --- a/tests/baselines/reference/useBeforeDeclaration_propertyAssignment.js +++ b/tests/baselines/reference/useBeforeDeclaration_propertyAssignment.js @@ -20,7 +20,7 @@ class D { //// [useBeforeDeclaration_propertyAssignment.js] export class C { constructor() { - this.a = Object.assign({ b: this.b }, this.c, { [this.b]: `${this.c}` }); + this.a = Object.assign(Object.assign({ b: this.b }, this.c), { [this.b]: `${this.c}` }); this.b = 0; this.c = { c: this.b }; }