Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use 'Omit' instead of 'Pick<Exclude<...>>' for object rest #31134

Merged
merged 5 commits into from Apr 30, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
20 changes: 7 additions & 13 deletions src/compiler/checker.ts
Expand Up @@ -536,8 +536,7 @@ namespace ts {
let deferredGlobalTemplateStringsArrayType: ObjectType;
let deferredGlobalImportMetaType: ObjectType;
let deferredGlobalExtractSymbol: Symbol;
let deferredGlobalExcludeSymbol: Symbol;
let deferredGlobalPickSymbol: Symbol;
let deferredGlobalOmitSymbol: Symbol;
let deferredGlobalBigIntType: ObjectType;

const allPotentiallyUnusedIdentifiers = createMap<PotentiallyUnusedIdentifier[]>(); // key is file name
Expand Down Expand Up @@ -4939,13 +4938,12 @@ namespace ts {
if (omitKeyType.flags & TypeFlags.Never) {
return source;
}
const pickTypeAlias = getGlobalPickSymbol();
const excludeTypeAlias = getGlobalExcludeSymbol();
if (!pickTypeAlias || !excludeTypeAlias) {

const omitTypeAlias = getGlobalOmitSymbol();
if (!omitTypeAlias) {
return errorType;
}
const pickKeys = getTypeAliasInstantiation(excludeTypeAlias, [getIndexType(source), omitKeyType]);
return getTypeAliasInstantiation(pickTypeAlias, [source, pickKeys]);
return getTypeAliasInstantiation(omitTypeAlias, [source, omitKeyType]);
}
const members = createSymbolTable();
for (const prop of getPropertiesOfType(source)) {
Expand Down Expand Up @@ -9274,12 +9272,8 @@ namespace ts {
return deferredGlobalExtractSymbol || (deferredGlobalExtractSymbol = getGlobalSymbol("Extract" as __String, SymbolFlags.TypeAlias, Diagnostics.Cannot_find_global_type_0)!); // TODO: GH#18217
}

function getGlobalExcludeSymbol(): Symbol {
return deferredGlobalExcludeSymbol || (deferredGlobalExcludeSymbol = getGlobalSymbol("Exclude" as __String, SymbolFlags.TypeAlias, Diagnostics.Cannot_find_global_type_0)!); // TODO: GH#18217
}

function getGlobalPickSymbol(): Symbol {
return deferredGlobalPickSymbol || (deferredGlobalPickSymbol = getGlobalSymbol("Pick" as __String, SymbolFlags.TypeAlias, Diagnostics.Cannot_find_global_type_0)!); // TODO: GH#18217
function getGlobalOmitSymbol(): Symbol {
return deferredGlobalOmitSymbol || (deferredGlobalOmitSymbol = getGlobalSymbol("Omit" as __String, SymbolFlags.TypeAlias, Diagnostics.Cannot_find_global_type_0)!); // TODO: GH#18217
}

function getGlobalBigIntType(reportErrors: boolean) {
Expand Down
12 changes: 6 additions & 6 deletions tests/baselines/reference/genericIsNeverEmptyObject.types
Expand Up @@ -2,18 +2,18 @@
// Repro from #29067

function test<T extends { a: string }>(obj: T) {
>test : <T extends { a: string; }>(obj: T) => Pick<T, Exclude<keyof T, "a">> & { b: string; }
>test : <T extends { a: string; }>(obj: T) => Omit<T, "a"> & { b: string; }
>a : string
>obj : T

let { a, ...rest } = obj;
>a : string
>rest : Pick<T, Exclude<keyof T, "a">>
>rest : Omit<T, "a">
>obj : T

return { ...rest, b: a };
>{ ...rest, b: a } : Pick<T, Exclude<keyof T, "a">> & { b: string; }
>rest : Pick<T, Exclude<keyof T, "a">>
>{ ...rest, b: a } : Omit<T, "a"> & { b: string; }
>rest : Omit<T, "a">
>b : string
>a : string
}
Expand All @@ -30,7 +30,7 @@ let o2: { b: string, x: number } = test(o1);
>o2 : { b: string; x: number; }
>b : string
>x : number
>test(o1) : Pick<{ a: string; x: number; }, "x"> & { b: string; }
>test : <T extends { a: string; }>(obj: T) => Pick<T, Exclude<keyof T, "a">> & { b: string; }
>test(o1) : Omit<{ a: string; x: number; }, "a"> & { b: string; }
>test : <T extends { a: string; }>(obj: T) => Omit<T, "a"> & { b: string; }
>o1 : { a: string; x: number; }

16 changes: 8 additions & 8 deletions tests/baselines/reference/genericObjectRest.types
Expand Up @@ -16,32 +16,32 @@ function f1<T extends { a: string, b: number }>(obj: T) {
let { a: a1, ...r1 } = obj;
>a : any
>a1 : string
>r1 : Pick<T, Exclude<keyof T, "a">>
>r1 : Omit<T, "a">
>obj : T

let { a: a2, b: b2, ...r2 } = obj;
>a : any
>a2 : string
>b : any
>b2 : number
>r2 : Pick<T, Exclude<keyof T, "a" | "b">>
>r2 : Omit<T, "a" | "b">
>obj : T

let { 'a': a3, ...r3 } = obj;
>a3 : string
>r3 : Pick<T, Exclude<keyof T, "a">>
>r3 : Omit<T, "a">
>obj : T

let { ['a']: a4, ...r4 } = obj;
>'a' : "a"
>a4 : string
>r4 : Pick<T, Exclude<keyof T, "a">>
>r4 : Omit<T, "a">
>obj : T

let { [a]: a5, ...r5 } = obj;
>a : "a"
>a5 : string
>r5 : Pick<T, Exclude<keyof T, "a">>
>r5 : Omit<T, "a">
>obj : T
}

Expand All @@ -68,7 +68,7 @@ function f2<T extends { [sa]: string, [sb]: number }>(obj: T) {
>a1 : string
>sb : unique symbol
>b1 : number
>r1 : Pick<T, Exclude<keyof T, unique symbol | unique symbol>>
>r1 : Omit<T, unique symbol | unique symbol>
>obj : T
}

Expand All @@ -83,7 +83,7 @@ function f3<T, K1 extends keyof T, K2 extends keyof T>(obj: T, k1: K1, k2: K2) {
>a1 : T[K1]
>k2 : K2
>a2 : T[K2]
>r1 : Pick<T, Exclude<keyof T, K1 | K2>>
>r1 : Omit<T, K1 | K2>
>obj : T
}

Expand All @@ -104,7 +104,7 @@ function f4<K1 extends keyof Item, K2 extends keyof Item>(obj: Item, k1: K1, k2:
>a1 : Item[K1]
>k2 : K2
>a2 : Item[K2]
>r1 : Pick<Item, Exclude<"a", K1 | K2> | Exclude<"b", K1 | K2> | Exclude<"c", K1 | K2>>
>r1 : Omit<Item, K1 | K2>
>obj : Item
}

6 changes: 3 additions & 3 deletions tests/baselines/reference/literalTypeWidening.types
Expand Up @@ -443,14 +443,14 @@ function test<T extends { a: string, b: string }>(obj: T): T {

let { a, ...rest } = obj;
>a : string
>rest : Pick<T, Exclude<keyof T, "a">>
>rest : Omit<T, "a">
>obj : T

return { a: 'hello', ...rest } as T;
>{ a: 'hello', ...rest } as T : T
>{ a: 'hello', ...rest } : { a: string; } & Pick<T, Exclude<keyof T, "a">>
>{ a: 'hello', ...rest } : { a: string; } & Omit<T, "a">
>a : string
>'hello' : "hello"
>rest : Pick<T, Exclude<keyof T, "a">>
>rest : Omit<T, "a">
}

4 changes: 2 additions & 2 deletions tests/baselines/reference/mappedTypeConstraints.symbols
Expand Up @@ -132,9 +132,9 @@ const modifier = <T extends TargetProps>(targetProps: T) => {
>targetProps : Symbol(targetProps, Decl(mappedTypeConstraints.ts, 30, 41))

rest.foo;
>rest.foo : Symbol(foo, Decl(mappedTypeConstraints.ts, 25, 20))
>rest.foo : Symbol(foo)
>rest : Symbol(rest, Decl(mappedTypeConstraints.ts, 31, 13))
>foo : Symbol(foo, Decl(mappedTypeConstraints.ts, 25, 20))
>foo : Symbol(foo)

};

4 changes: 2 additions & 2 deletions tests/baselines/reference/mappedTypeConstraints.types
Expand Up @@ -98,12 +98,12 @@ const modifier = <T extends TargetProps>(targetProps: T) => {

let {bar, ...rest} = targetProps;
>bar : string
>rest : Pick<T, Exclude<keyof T, "bar">>
>rest : Omit<T, "bar">
>targetProps : T

rest.foo;
>rest.foo : T["foo"]
>rest : Pick<T, Exclude<keyof T, "bar">>
>rest : Omit<T, "bar">
>foo : T["foo"]

};
Expand Down
6 changes: 3 additions & 3 deletions tests/baselines/reference/objectRestNegative.types
Expand Up @@ -36,18 +36,18 @@ function stillMustBeLast({ ...mustBeLast, a }: { a: number, b: string }): void {
>b : string
}
function generic<T extends { x, y }>(t: T) {
>generic : <T extends { x: any; y: any; }>(t: T) => Pick<T, Exclude<keyof T, "x">>
>generic : <T extends { x: any; y: any; }>(t: T) => Omit<T, "x">
>x : any
>y : any
>t : T

let { x, ...rest } = t;
>x : any
>rest : Pick<T, Exclude<keyof T, "x">>
>rest : Omit<T, "x">
>t : T

return rest;
>rest : Pick<T, Exclude<keyof T, "x">>
>rest : Omit<T, "x">
}

let rest: { b: string }
Expand Down