From b12548bb4a92f854c000bd8329167880ee665c5a Mon Sep 17 00:00:00 2001 From: "Nicholas C. Zakas" Date: Thu, 16 Jul 2015 10:19:33 -0700 Subject: [PATCH] Fix: Allow AssignmentExpression in object spread (fixes #167) --- espree.js | 8 +- .../invalid-rest.config.js | 4 + .../invalid-rest.result.js | 6 + .../invalid-rest.src.js | 1 + .../property-spread.result.js | 407 ++++++++++++++++++ .../property-spread.src.js | 9 + 6 files changed, 434 insertions(+), 1 deletion(-) create mode 100644 tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.config.js create mode 100644 tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.result.js create mode 100644 tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.src.js create mode 100644 tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.result.js create mode 100644 tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.src.js diff --git a/espree.js b/espree.js index 18702761..970d79f4 100644 --- a/espree.js +++ b/espree.js @@ -2617,7 +2617,7 @@ function parseObjectProperty() { // object spread property if (allowSpread && match("...")) { lex(); - return markerApply(marker, astNodeFactory.createExperimentalSpreadProperty(parseVariableIdentifier())); + return markerApply(marker, astNodeFactory.createExperimentalSpreadProperty(parseAssignmentExpression())); } // only possibility in this branch is a shorthand generator @@ -3385,6 +3385,12 @@ function reinterpretAsAssignmentBindingPattern(expr) { property = expr.properties[i]; if (allowRest && property.type === astNodeTypes.ExperimentalSpreadProperty) { + + // only allow identifiers + if (property.argument.type !== astNodeTypes.Identifier) { + throwErrorTolerant({}, "Invalid object rest."); + } + property.type = astNodeTypes.ExperimentalRestProperty; return; } diff --git a/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.config.js b/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.config.js new file mode 100644 index 00000000..f407ad5a --- /dev/null +++ b/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.config.js @@ -0,0 +1,4 @@ +module.exports = { + destructuring: true, + experimentalObjectRestSpread: true +}; diff --git a/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.result.js b/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.result.js new file mode 100644 index 00000000..976aac95 --- /dev/null +++ b/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.result.js @@ -0,0 +1,6 @@ +module.exports = { + column: 25, + description: "Invalid object rest.", + index: 24, + lineNumber: 1 +}; diff --git a/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.src.js b/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.src.js new file mode 100644 index 00000000..a38d92cf --- /dev/null +++ b/tests/fixtures/ecma-features-mix/destructuring-and-experimentalObjectRestSpread/invalid-rest.src.js @@ -0,0 +1 @@ +var { x, y, ...foo.bar } = { x: 1, y: 2, a: 3, b: 4 }; diff --git a/tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.result.js b/tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.result.js new file mode 100644 index 00000000..c340939a --- /dev/null +++ b/tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.result.js @@ -0,0 +1,407 @@ +module.exports = { + "type": "Program", + "body": [ + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "foo", + "range": [ + 4, + 7 + ], + "loc": { + "start": { + "line": 1, + "column": 4 + }, + "end": { + "line": 1, + "column": 7 + } + } + }, + "init": null, + "range": [ + 4, + 7 + ], + "loc": { + "start": { + "line": 1, + "column": 4 + }, + "end": { + "line": 1, + "column": 7 + } + } + }, + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "get", + "range": [ + 13, + 16 + ], + "loc": { + "start": { + "line": 2, + "column": 4 + }, + "end": { + "line": 2, + "column": 7 + } + } + }, + "init": null, + "range": [ + 13, + 16 + ], + "loc": { + "start": { + "line": 2, + "column": 4 + }, + "end": { + "line": 2, + "column": 7 + } + } + }, + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "set", + "range": [ + 22, + 25 + ], + "loc": { + "start": { + "line": 3, + "column": 4 + }, + "end": { + "line": 3, + "column": 7 + } + } + }, + "init": null, + "range": [ + 22, + 25 + ], + "loc": { + "start": { + "line": 3, + "column": 4 + }, + "end": { + "line": 3, + "column": 7 + } + } + } + ], + "kind": "var", + "range": [ + 0, + 26 + ], + "loc": { + "start": { + "line": 1, + "column": 0 + }, + "end": { + "line": 3, + "column": 8 + } + } + }, + { + "type": "VariableDeclaration", + "declarations": [ + { + "type": "VariableDeclarator", + "id": { + "type": "Identifier", + "name": "x", + "range": [ + 32, + 33 + ], + "loc": { + "start": { + "line": 5, + "column": 4 + }, + "end": { + "line": 5, + "column": 5 + } + } + }, + "init": { + "type": "ObjectExpression", + "properties": [ + { + "type": "Property", + "key": { + "type": "Identifier", + "name": "foo", + "range": [ + 42, + 45 + ], + "loc": { + "start": { + "line": 6, + "column": 4 + }, + "end": { + "line": 6, + "column": 7 + } + } + }, + "value": { + "type": "Identifier", + "name": "foo", + "range": [ + 47, + 50 + ], + "loc": { + "start": { + "line": 6, + "column": 9 + }, + "end": { + "line": 6, + "column": 12 + } + } + }, + "kind": "init", + "method": false, + "shorthand": false, + "computed": false, + "range": [ + 42, + 50 + ], + "loc": { + "start": { + "line": 6, + "column": 4 + }, + "end": { + "line": 6, + "column": 12 + } + } + }, + { + "type": "Property", + "key": { + "type": "Identifier", + "name": "get", + "range": [ + 56, + 59 + ], + "loc": { + "start": { + "line": 7, + "column": 4 + }, + "end": { + "line": 7, + "column": 7 + } + } + }, + "value": { + "type": "Identifier", + "name": "get", + "range": [ + 61, + 64 + ], + "loc": { + "start": { + "line": 7, + "column": 9 + }, + "end": { + "line": 7, + "column": 12 + } + } + }, + "kind": "init", + "method": false, + "shorthand": false, + "computed": false, + "range": [ + 56, + 64 + ], + "loc": { + "start": { + "line": 7, + "column": 4 + }, + "end": { + "line": 7, + "column": 12 + } + } + }, + { + "type": "ExperimentalSpreadProperty", + "argument": { + "type": "MemberExpression", + "computed": false, + "object": { + "type": "Identifier", + "name": "set", + "range": [ + 73, + 76 + ], + "loc": { + "start": { + "line": 8, + "column": 7 + }, + "end": { + "line": 8, + "column": 10 + } + } + }, + "property": { + "type": "Identifier", + "name": "foo", + "range": [ + 77, + 80 + ], + "loc": { + "start": { + "line": 8, + "column": 11 + }, + "end": { + "line": 8, + "column": 14 + } + } + }, + "range": [ + 73, + 80 + ], + "loc": { + "start": { + "line": 8, + "column": 7 + }, + "end": { + "line": 8, + "column": 14 + } + } + }, + "range": [ + 70, + 80 + ], + "loc": { + "start": { + "line": 8, + "column": 4 + }, + "end": { + "line": 8, + "column": 14 + } + } + } + ], + "range": [ + 36, + 82 + ], + "loc": { + "start": { + "line": 5, + "column": 8 + }, + "end": { + "line": 9, + "column": 1 + } + } + }, + "range": [ + 32, + 82 + ], + "loc": { + "start": { + "line": 5, + "column": 4 + }, + "end": { + "line": 9, + "column": 1 + } + } + } + ], + "kind": "var", + "range": [ + 28, + 83 + ], + "loc": { + "start": { + "line": 5, + "column": 0 + }, + "end": { + "line": 9, + "column": 2 + } + } + } + ], + "sourceType": "script", + "range": [ + 0, + 83 + ], + "loc": { + "start": { + "line": 1, + "column": 0 + }, + "end": { + "line": 9, + "column": 2 + } + } +}; \ No newline at end of file diff --git a/tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.src.js b/tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.src.js new file mode 100644 index 00000000..1ef4ef44 --- /dev/null +++ b/tests/fixtures/ecma-features/experimentalObjectRestSpread/property-spread.src.js @@ -0,0 +1,9 @@ +var foo, + get, + set; + +var x = { + foo: foo, + get: get, + ...set.foo +};