Search code examples
typescriptunion-typesconditional-types

Conditional data types on union data types


Assume that you have the following types:

type Foo = {
    prop1: 'foo',
    prop2: null
}

type Bar = {
    prop1: 'bar',
    prop2: number
}

type FooOrBar = Foo | Bar

Is it possible to rewrite the above code using conditional types?

I have tried the following:

type FooOrBar = {
    prop1: 'foo' | 'bar'
    prop2: FooOrBar['prop1'] extends 'foo' ? null : number
}

But when trying to declare a var like so:

const sample1: FooOrBar = {
    prop1: 'foo',
    prop2: null
}

I receive the following error:

Type 'null' is not assignable to type 'number'.

It seems that FooOrBar['prop1'] extends 'foo' is always false which shouldn't be since FooOrBar['prop1'] is a union type of 'foo' | 'bar'

What am I doing wrong?


Solution

  • You could do that, but you'd still need to provide the type argument explicitly.

    type FooOrBar<T extends 'foo' | 'bar'> = {
      prop1: T;
      prop2: T extends 'foo' ? null : number;
    }
    
    const test: FooOrBar<'foo'> = {
      prop1: 'foo',
      prop2: null,
    }