Skip to content

Instantly share code, notes, and snippets.

@Drag13
Last active November 18, 2021 06:44
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Drag13/055068f6ae45670428db2a21cc7b1544 to your computer and use it in GitHub Desktop.
Save Drag13/055068f6ae45670428db2a21cc7b1544 to your computer and use it in GitHub Desktop.
TypeScript Advanced Types and Trics
// At least one property
type AtLeastOne<T, Keys extends keyof T = keyof T> = Pick<T, Exclude<keyof T, Keys>> & {
[K in Keys]-?: Required<Pick<T, K>>
}[Keys]
type PerformanceBudget = AtLeastOne<{ fcp: number, lcp: number }>
// Typed Key
type ContractMap<TContract> = {
[key in keyof TContract]: (value: TContract[key]) => TContract[key]
};
const contractMap: ContractMap<{ data: string, value: number }> = {
data: (_) => '4',
value: (x) => x
}
// Deep Partial (here credits goes to StackOverflow)
type DeepPartial<T> = {
[P in keyof T]?: T[P] extends Array<infer U>
? Array<DeepPartial<U>>
: T[P] extends ReadonlyArray<infer U>
? ReadonlyArray<DeepPartial<U>>
: DeepPartial<T[P]>;
};
// exclude dynamic properties from object
function exclude<T, K extends keyof T>(obj: T, keys: K[]): Pick<T, Exclude<keyof T, K>> {
return Object.keys(obj)
.filter((key) => !keys.includes(key as K))
.reduce((acc, key) => {
acc[key as Exclude<keyof T, K>] = obj[key as Exclude<keyof T, K>];
return acc;
}, {} as Omit<T, K>);
}
// take only common props
type C = Pick<A | B, keyof A & keyof B>; // { Y: number; }
const fields = ['a', 'b'] as const; //Trick #1
type PickFromArray<T> = {
[key in (typeof fields)[number]]: T //Trick #2
}
const x: PickFromArray<string> = {
'a': 'sttr',
'b': 'zzz'
}
export const defined = <T>(x: T | undefined): x is T => x != null;
const v = [1,2, null].filter(defined);
declare interface Array<T> {
foo(): string;
}
Array.prototype.foo = function(): string {
return "bar";
}
const factory = () => class MyClass { }
class MClass extends (factory()){}
https://stackoverflow.com/questions/69089549/typescript-template-literal-type-how-to-infer-numeric-type
type MAXIMUM_ALLOWED_BOUNDARY = 495
type Mapped<
N extends number,
Result extends Array<unknown> = [],
> =
(Result['length'] extends N
? Result
: Mapped<N, [...Result, Result['length']]>
)
// 0 , 1, 2 ... 494
type NumberRange = Mapped<MAXIMUM_ALLOWED_BOUNDARY>[number]
const x: NumberRange = 3;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment