{} || [] is not valid JavaScript

Viewed 923

Why is {} || [] not valid?

$ echo '[] || {}' | node # this works
$ echo '{} || []' | node # but this doesn't
[stdin]:1
{} || []
   ^^

SyntaxError: Unexpected token ||
    at createScript (vm.js:80:10)
    at Object.runInThisContext (vm.js:139:10)
    at Object.<anonymous> ([stdin]-wrapper:6:22)
    at Module._compile (module.js:652:30)
    at evalScript (bootstrap_node.js:466:27)
    at Socket.<anonymous> (bootstrap_node.js:237:15)
    at emitNone (events.js:111:20)
    at Socket.emit (events.js:208:7)
    at endReadableNT (_stream_readable.js:1064:12)
    at _combinedTickCallback (internal/process/next_tick.js:138:11)

$ echo '({}) || []' | node # unless you do this
1 Answers

When a statement starts with {, it's assumed by the parser to be the beginning of a block statement. In the case of {}, it's an empty block statement. So it's as if you had

{
  // no code here
}
|| []

and || cannot start a statement.

The one that does work, [] || {}, is unambiguous because a statement whose first token is [ can only be an expression statement.

Wrapping {} in ( ) means that the first token of the statement is (, not {. The ( token cannot start any form of statement other than an expression (though it does have a little ambiguity, since it can start an anonymous "fat arrow" function; that's still an expression and the parser just has to disambiguate that later).

Note: the implementation of various debugging environments like your browser console and the Node command-line "console" have an effect on this sort of syntax. In order to keep things simple, such tools take the code you type in and one way or another they "wrap" it so that it can be parsed and evaluated interactively, statement by statement as you type. Unfortunately that process can introduce anomalies, such that something you try in the console may work fine there but not when you try it in a real block of code.

Related