Dennie de Lange
Dennie de Lange

Reputation: 2934

ES6 object destructuring with a default value assignment

Consider the following code:

const log = ({a,b=a}) => console.log(a,b);
log({a:'a'})

The variable b is assigned the value a. This does work when transpiling it to es5, but I am not entirely sure if this is valid es6 syntax.

Am I allowed to do this kind of default value assignment in a destructured object?

Upvotes: 0

Views: 112

Answers (2)

Bergi
Bergi

Reputation: 664297

Am I allowed to do this kind of default value assignment in a destructured object?

Yes. The destructuring expression is evaluated from left to right, and you can use variables that are already initialised from properties in the default initialiser expressions of later properties.

Remember that it desugars to

const log = (o) => {
  var a = o.a;
  var b = o.b !== undefined ? o.b : a;
//                                  ^ a is usable here
  console.log(a,b);
};

Upvotes: 0

Karen Grigoryan
Karen Grigoryan

Reputation: 5422

const log = ({a,b=a}) => console.log(a,b);
log('a')

is syntactically valid but semantically invalid, since you are trying to destructure a string primitive, which gets boxed into a temporary String object wrapper, and tries to get both a and b properties, which are always undefined since the wrapper object is temporary and only created for the sake of the operation triggering the boxing itself.

Thus you have undefined, undefined when you call it.

The destructuring operation with defaults could be semantically valid in your case with a call like this:

const log = ({a,b=a}) => console.log(a,b);
log({a: 'a'}) // a,a

UPD:

But beware that order of supplying default value matters, so this won't work

const log = ({a=b,b}) => console.log(a,b);
log({a: 'a'}) // error

because destructuring happens after argument object initialization and is evaluated from left to right, thus b is not yet destructured and known by the time we destructure a to try to reference it in case a is undefined.

Upvotes: 1

Related Questions