I'd like to exclude a single property from the type. How can I do that?
For example I have
interface XYZ {
x: number;
y: number;
z: number;
}
And I want to exclude property z
to get
type XY = { x: number, y: number };
This question is related to
typescript
As of Typescript 3.5, the Omit helper will be included: TypeScript 3.5 RC - The Omit Helper Type
You can use it directly, and you should remove your own definition of the Omit helper when updating.
type T1 = Omit<XYZ, "z"> // { x: number; y: number; }
type T2 = Omit<XYZ, "y" | "z"> // { x: number; }
type Keys_StringExcluded<T> =
{ [K in keyof T]: T[K] extends string ? never : K }[keyof T]
type XYZ = { x: number; y: string; z: number; }
type T3a = Pick<XYZ, Keys_StringExcluded<XYZ>> // { x: number; z: number; }
Shorter version with TS 4.1 key remapping / as
clause in mapped types (PR):
type T3b = { [K in keyof XYZ as XYZ[K] extends string ? never : K]: XYZ[K] }
// { x: number; z: number; }
string
patterntype OmitGet<T> = {[K in keyof T as K extends `get${infer _}` ? never : K]: T[K]}
type XYZ2 = { getA: number; b: string; getC: boolean; }
type T4 = OmitGet<XYZ2> // { b: string; }
Note: Above template literal types are supported with TS 4.1.
Note 2: You can also write get${string}
instead of get${infer _}
here.
Pick
, Omit
and other utility types
How to Pick and rename certain keys using Typescript? (rename instead of exclude)
In Typescript 3.5+:
interface TypographyProps {
variant: string
fontSize: number
}
type TypographyPropsMinusVariant = Omit<TypographyProps, "variant">
I do like that:
interface XYZ {
x: number;
y: number;
z: number;
}
const a:XYZ = {x:1, y:2, z:3};
const { x, y, ...last } = a;
const { z, ...firstTwo} = a;
console.log(firstTwo, last);
If you prefer to use a library, use ts-essentials.
import { Omit } from "ts-essentials";
type ComplexObject = {
simple: number;
nested: {
a: string;
array: [{ bar: number }];
};
};
type SimplifiedComplexObject = Omit<ComplexObject, "nested">;
// Result:
// {
// simple: number
// }
// if you want to Omit multiple properties just use union type:
type SimplifiedComplexObject = Omit<ComplexObject, "nested" | "simple">;
// Result:
// { } (empty type)
PS: You will find lots of other useful stuff there ;)
I've found solution with declaring some variables and using spread operator to infer type:
interface XYZ {
x: number;
y: number;
z: number;
}
declare var { z, ...xy }: XYZ;
type XY = typeof xy; // { x: number; y: number; }
It works, but I would be glad to see a better solution.
With typescript 2.8, you can use the new built-in Exclude
type. The 2.8 release notes actually mention this in the section "Predefined conditional types":
Note: The Exclude type is a proper implementation of the Diff type suggested here. [...] We did not include the Omit type because it is trivially written as
Pick<T, Exclude<keyof T, K>>
.
Applying this to your example, type XY could be defined as:
type XY = Pick<XYZ, Exclude<keyof XYZ, "z">>
Source: Stackoverflow.com