1

I have found a test case describing falsy unions spread types, which seems to be odd to me.

Why does TypeScript accept spread types from unions with Object and falsy types, whereas does not from unions with Object and truthy types?

https://github.com/microsoft/TypeScript/blob/master/tests/cases/conformance/types/spread/spreadOverwritesPropertyStrict.ts

declare const obj_a: Object | ""
declare const obj_b: Object | string

const x = { ...obj_a } // Not Error?
const y = { ...obj_b } // Spread types may only be created from object types.(2698)

Playground Link

uraway
  • 245
  • 1
  • 4
  • 8
  • Maybe because the [spread spec](https://github.com/tc39/proposal-object-rest-spread/blob/master/Spread.md) states `Null/Undefined Are Ignored`. The implementation in browsers seem to also ignore other falsy types. – sroes Feb 16 '21 at 15:04
  • @sroes [falsy is irrelevant for spreading into objects](https://stackoverflow.com/a/64612639/). `null` and `undefined` are treated as an early exist and just produce a new object. Anything else is converted to an object and the own properties are copied over. primitives like `0` or `""` don't differ at all from `1` or `"a"` in how they are treated. Numbers don't have own properties so nothing will be copied over. Strings *do* have the indexed characters, so spreading them into an object gives you that. Empty strings have no characters, so you still get an empty object in that case. – VLAZ Feb 17 '21 at 07:42
  • @sroes Point is, there is no distinction made for falsy in JavaScript. TypeScript seems to have unintuitive behaviour here. `Object | 0` is accepted as a spreadable target, `Object | 1` is not. The two should be identical. – VLAZ Feb 17 '21 at 07:44

0 Answers0