I have a Type<T>
which is supposed to have a field additionalField
with a type of T[]
.
I need to make this field optional, depending on if there's a generic being passed.
So I introduce a ConditionalType<T = void>
, in which if I don't pass a generic - then there's no additionalField
.
So I have an enum MyEnum
and in ConditionalType<MyEnum>
I expect additionalField
to be of type MyEnum[]
. Instead, additionalField
has a type of MyEnum.TEST_1[] | MyEnum.TEST_2[]
.
Here's the full code:
type ConditionalType<T = void> = {
someField: string;
} & (T extends void ? {} : {
additionalField: T[];
})
type Type<T> = {
someField: string;
additionalField: T[];
}
enum MyEnum {
TEST_1 = "test_1",
TEST_2 = "test_2"
}
const a: ConditionalType<MyEnum>;
a.additionalField
// (property) additionalField: MyEnum.TEST_1[] | MyEnum.TEST_2[]
// Need to make it MyEnum[] somehow
const b: Type<MyEnum>;
b.additionalField;
// (property) additionalField: MyEnum[]
// Works as expected
Could someone please tell me, how can I make additionalField
to be of type MyEnum[]
instead of MyEnum.TEST_1[] | MyEnum.TEST_2[]
in ConditionalType<MyEnum>
? In the original Type<T>
it works as expected and additionalField
has the type of MyEnum[]
in Type<MyEnum>
;
And if this is supposed to work this way, why is this happening with ConditionalType<T = void>
?
Here's a link to the playground
CodePudding user response:
You accidentally triggered distribution by writing T extends void
. The union in T
is distributed over the conditional leading to the union MyEnum.TEST_1[] | MyEnum.TEST_2[]
instead of (MyEnum.TEST_1[] | MyEnum.TEST_2)[]
.
Avoid distribution by wrapping T
and void
inside tuples.
type ConditionalType<T = void> = {
someField: string;
} & ([T] extends [void] ? {} : {
additionalField: T[];
})