import type { IsEqual } from "./is-equal"; | |
/** | |
Filter out keys from an object. | |
Returns `never` if `Exclude` is strictly equal to `Key`. | |
Returns `never` if `Key` extends `Exclude`. | |
Returns `Key` otherwise. | |
@example | |
``` | |
type Filtered = Filter<'foo', 'foo'>; | |
//=> never | |
``` | |
@example | |
``` | |
type Filtered = Filter<'bar', string>; | |
//=> never | |
``` | |
@example | |
``` | |
type Filtered = Filter<'bar', 'foo'>; | |
//=> 'bar' | |
``` | |
@see {Except} | |
*/ | |
type Filter<KeyType, ExcludeType> = IsEqual<KeyType, ExcludeType> extends true | |
? never | |
: KeyType extends ExcludeType | |
? never | |
: KeyType; | |
/** | |
Create a type from an object type without certain keys. | |
We recommend setting the `requireExactProps` option to `true`. | |
This type is a stricter version of [`Omit`](https://www.typescriptlang.org/docs/handbook/release-notes/typescript-3-5.html#the-omit-helper-type). The `Omit` type does not restrict the omitted keys to be keys present on the given type, while `Except` does. The benefits of a stricter type are avoiding typos and allowing the compiler to pick up on rename refactors automatically. | |
This type was proposed to the TypeScript team, which declined it, saying they prefer that libraries implement stricter versions of the built-in types ([microsoft/TypeScript#30825](https://github.com/microsoft/TypeScript/issues/30825#issuecomment-523668235)). | |
@example | |
``` | |
import type {Except} from 'type-fest'; | |
type Foo = { | |
a: number; | |
b: string; | |
}; | |
type FooWithoutA = Except<Foo, 'a'>; | |
//=> {b: string} | |
const fooWithoutA: FooWithoutA = {a: 1, b: '2'}; | |
//=> errors: 'a' does not exist in type '{ b: string; }' | |
type FooWithoutB = Except<Foo, 'b', {requireExactProps: true}>; | |
//=> {a: number} & Partial<Record<"b", never>> | |
const fooWithoutB: FooWithoutB = {a: 1, b: '2'}; | |
//=> errors at 'b': Type 'string' is not assignable to type 'undefined'. | |
``` | |
@category Object | |
*/ | |
export type Except<ObjectType, KeysType extends keyof ObjectType> = { | |
[KeyType in keyof ObjectType as Filter<KeyType, KeysType>]: ObjectType[KeyType]; | |
}; | |