Node: Weird issues when passing object literals to eval() or vm.runInNewContext()

Created on 25 Mar 2018  Â·  2Comments  Â·  Source: nodejs/node

  • Version: v9.8.0
  • Platform: archlinux 4.14.15-1-ARCH SMP PREEMPT x86_64 GNU/Linux
  • Subsystem: vm, eval

Passing an object literal to eval or vm.runInNewContext (and presumably other vm.run* functions) has weird issues.
When passing an object with one key, the returned value is the value of that key.
Passing an object with two keys throws a SyntaxError even though the passed code is syntactically correct.
Examples:

const output = eval('{ foo: "bar" }');
output === 'bar'; // true

```js
const output = eval('{ foo: "bar", baz: "qux" }');
// Throws a SyntaxError:
// { foo: "bar", baz: "qux" }
// ^
// SyntaxError: Unexpected token :


The same issue occurs with `vm.runInNewContext`:
```js
const vm = require('vm');
const output = vm.runInNewContext('{ foo: "bar" }');
output === 'bar'; // true

vm.runInNewContext('{ foo: "bar", baz: "qux" }');
// Throws a SyntaxError:
// { foo: "bar", baz: "qux" }
//                 ^
// SyntaxError: Unexpected token :

I suspect it to be a parsing error with object literals in this form. For example, this works fine:

const output = eval('const myObj = { foo: "bar" }; myObj;');
output instanceof Object && output.foo === 'bar'; // true
question

Most helpful comment

Ohh.. I didn't really think about that. Very clear explanation, thank you.

All 2 comments

This is, unfortunately, “working as expected” – it’s part of the JS spec, and not something that Node could change on its own.

{foo: 'bar'}, when parsed as a JS script, is not parsed as an object; it’s parsed as a block, like you’d usually have in the body of an if (…) { … } statement, and the foo: bit is parsed as a label. The only “real” code that remains is 'bar', which is why that is returned as the completion value in that case.

Fwiw, what Node does in its own REPL in these cases is to first try to wrap everything in (…) and check whether that gives a syntax error; that should be a pretty reliable way to get the actual object that you want to get.

Ohh.. I didn't really think about that. Very clear explanation, thank you.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

mcollina picture mcollina  Â·  3Comments

filipesilvaa picture filipesilvaa  Â·  3Comments

stevenvachon picture stevenvachon  Â·  3Comments

loretoparisi picture loretoparisi  Â·  3Comments

Icemic picture Icemic  Â·  3Comments