UNPKG

1.88 kBTypeScriptView Raw
1import type {NonRecursiveType, IsUnion} from './internal';
2import type {IsNever} from './is-never';
3import type {Simplify} from './simplify';
4import type {UnknownArray} from './unknown-array';
5
6/**
7Create a type with shared fields from a union of object types.
8
9Use-cases:
10- You want a safe object type where each key exists in the union object.
11- You want to focus on the common fields of the union type and don't want to have to care about the other fields.
12
13@example
14```
15import type {SharedUnionFields} from 'type-fest';
16
17type Cat = {
18 name: string;
19 type: 'cat';
20 catType: string;
21};
22
23type Dog = {
24 name: string;
25 type: 'dog';
26 dogType: string;
27};
28
29function displayPetInfo(petInfo: Cat | Dog) {
30 // typeof petInfo =>
31 // {
32 // name: string;
33 // type: 'cat';
34 // catType: string; // Needn't care about this field, because it's not a common pet info field.
35 // } | {
36 // name: string;
37 // type: 'dog';
38 // dogType: string; // Needn't care about this field, because it's not a common pet info field.
39 // }
40
41 // petInfo type is complex and have some needless fields
42
43 console.log('name: ', petInfo.name);
44 console.log('type: ', petInfo.type);
45}
46
47function displayPetInfo(petInfo: SharedUnionFields<Cat | Dog>) {
48 // typeof petInfo =>
49 // {
50 // name: string;
51 // type: 'cat' | 'dog';
52 // }
53
54 // petInfo type is simple and clear
55
56 console.log('name: ', petInfo.name);
57 console.log('type: ', petInfo.type);
58}
59```
60
61@see SharedUnionFieldsDeep
62
63@category Object
64@category Union
65*/
66export type SharedUnionFields<Union> =
67Extract<Union, NonRecursiveType | ReadonlyMap<unknown, unknown> | ReadonlySet<unknown> | UnknownArray> extends infer SkippedMembers
68 ? Exclude<Union, SkippedMembers> extends infer RelevantMembers
69 ?
70 | SkippedMembers
71 | (IsNever<RelevantMembers> extends true
72 ? never
73 : Simplify<Pick<RelevantMembers, keyof RelevantMembers>>)
74 : never
75 : never;