1 | <div align="center">
|
2 | <br>
|
3 | <br>
|
4 | <img src="media/logo.svg" alt="type-fest" height="300">
|
5 | <br>
|
6 | <br>
|
7 | <b>A collection of essential TypeScript types</b>
|
8 | <br>
|
9 | <br>
|
10 | <br>
|
11 | <br>
|
12 | <hr>
|
13 | <div align="center">
|
14 | <p>
|
15 | <p>
|
16 | <sup>
|
17 | <a href="https://github.com/sponsors/sindresorhus">Sindre Sorhus' open source work is supported by the community</a>
|
18 | </sup>
|
19 | </p>
|
20 | <sup>Special thanks to:</sup>
|
21 | <br>
|
22 | <br>
|
23 | <a href="https://standardresume.co/tech">
|
24 | <img src="https://sindresorhus.com/assets/thanks/standard-resume-logo.svg" width="180"/>
|
25 | </a>
|
26 | <br>
|
27 | <br>
|
28 | <br>
|
29 | <a href="https://workos.com/?utm_campaign=github_repo&utm_medium=referral&utm_content=type-fest&utm_source=github">
|
30 | <div>
|
31 | <img src="https://sindresorhus.com/assets/thanks/workos-logo-white-bg.svg" width="220" alt="WorkOS">
|
32 | </div>
|
33 | <b>Your app, enterprise-ready.</b>
|
34 | <div>
|
35 | <sub>Start selling to enterprise customers with just a few lines of code.</sub>
|
36 | <br>
|
37 | <sup>Add Single Sign-On (and more) in minutes instead of months.</sup>
|
38 | </div>
|
39 | </a>
|
40 | <br>
|
41 | <br>
|
42 | <br>
|
43 | <a href="https://transloadit.com?utm_source=sindresorhus&utm_medium=referral&utm_campaign=sponsorship&utm_content=type-fest">
|
44 | <picture>
|
45 | <source width="350" media="(prefers-color-scheme: dark)" srcset="https://sindresorhus.com/assets/thanks/transloadit-logo-dark.svg">
|
46 | <source width="350" media="(prefers-color-scheme: light)" srcset="https://sindresorhus.com/assets/thanks/transloadit-logo.svg">
|
47 | <img width="350" src="https://sindresorhus.com/assets/thanks/transloadit-logo.svg" alt="Transloadit logo">
|
48 | </picture>
|
49 | </a>
|
50 | <br>
|
51 | <br>
|
52 | <br>
|
53 | <a href="https://logto.io/?ref=sindre">
|
54 | <div>
|
55 | <picture>
|
56 | <source width="200" media="(prefers-color-scheme: dark)" srcset="https://sindresorhus.com/assets/thanks/logto-logo-dark.svg?x">
|
57 | <source width="200" media="(prefers-color-scheme: light)" srcset="https://sindresorhus.com/assets/thanks/logto-logo-light.svg?x">
|
58 | <img width="200" src="https://sindresorhus.com/assets/thanks/logto-logo-light.svg?x" alt="Logto logo">
|
59 | </picture>
|
60 | </div>
|
61 | <b>The better identity infrastructure for developers</b>
|
62 | <div>
|
63 | <sup>Logto is an open-source Auth0 alternative designed for every app.</sup>
|
64 | </div>
|
65 | </a>
|
66 | <br>
|
67 | <br>
|
68 | </p>
|
69 | </div>
|
70 | <br>
|
71 | <hr>
|
72 | </div>
|
73 | <br>
|
74 | <br>
|
75 |
|
76 | [](https://giphy.com/gifs/illustration-rainbow-unicorn-26AHG5KGFxSkUWw1i)
|
77 | [](https://www.npmjs.com/package/type-fest?activeTab=dependents)
|
78 | [](https://www.npmjs.com/package/type-fest)
|
79 |
|
80 | Many of the types here should have been built-in. You can help by suggesting some of them to the [TypeScript project](https://github.com/Microsoft/TypeScript/blob/main/CONTRIBUTING.md).
|
81 |
|
82 | Either add this package as a dependency or copy-paste the needed types. No credit required. 👌
|
83 |
|
84 | PR welcome for additional commonly needed types and docs improvements. Read the [contributing guidelines](.github/contributing.md) first.
|
85 |
|
86 | **Help wanted with reviewing [proposals](https://github.com/sindresorhus/type-fest/issues) and [pull requests](https://github.com/sindresorhus/type-fest/pulls).**
|
87 |
|
88 | ## Install
|
89 |
|
90 | ```sh
|
91 | npm install type-fest
|
92 | ```
|
93 |
|
94 | *Requires TypeScript >=5.1*
|
95 |
|
96 | *Works best with [`{strict: true}`](https://www.typescriptlang.org/tsconfig#strict) in your tsconfig.*
|
97 |
|
98 | ## Usage
|
99 |
|
100 | ```ts
|
101 | import type {Except} from 'type-fest';
|
102 |
|
103 | type Foo = {
|
104 | unicorn: string;
|
105 | rainbow: boolean;
|
106 | };
|
107 |
|
108 | type FooWithoutRainbow = Except<Foo, 'rainbow'>;
|
109 | //=> {unicorn: string}
|
110 | ```
|
111 |
|
112 | ## API
|
113 |
|
114 | Click the type names for complete docs.
|
115 |
|
116 | ### Basic
|
117 |
|
118 | - [`Primitive`](source/primitive.d.ts) - Matches any [primitive value](https://developer.mozilla.org/en-US/docs/Glossary/Primitive).
|
119 | - [`Class`](source/basic.d.ts) - Matches a [`class`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes).
|
120 | - [`Constructor`](source/basic.d.ts) - Matches a [`class` constructor](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes).
|
121 | - [`AbstractClass`](source/basic.d.ts) - Matches an [`abstract class`](https://www.typescriptlang.org/docs/handbook/classes.html#abstract-classes).
|
122 | - [`AbstractConstructor`](source/basic.d.ts) - Matches an [`abstract class`](https://www.typescriptlang.org/docs/handbook/release-notes/typescript-4-2.html#abstract-construct-signatures) constructor.
|
123 | - [`TypedArray`](source/typed-array.d.ts) - Matches any [typed array](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypedArray), like `Uint8Array` or `Float64Array`.
|
124 | - [`ObservableLike`](source/observable-like.d.ts) - Matches a value that is like an [Observable](https://github.com/tc39/proposal-observable).
|
125 |
|
126 | ### Utilities
|
127 |
|
128 | - [`EmptyObject`](source/empty-object.d.ts) - Represents a strictly empty plain object, the `{}` value.
|
129 | - [`NonEmptyObject`](source/non-empty-object.d.ts) - Represents an object with at least 1 non-optional key.
|
130 | - [`UnknownRecord`](source/unknown-record.d.ts) - Represents an object with `unknown` value. You probably want this instead of `{}`.
|
131 | - [`UnknownArray`](source/unknown-array.d.ts) - Represents an array with `unknown` value.
|
132 | - [`Except`](source/except.d.ts) - Create a type from an object type without certain keys. This is a stricter version of [`Omit`](https://www.typescriptlang.org/docs/handbook/utility-types.html#omittype-keys).
|
133 | - [`Writable`](source/writable.d.ts) - Create a type that strips `readonly` from the given type. Inverse of `Readonly<T>`.
|
134 | - [`WritableDeep`](source/writable-deep.d.ts) - Create a deeply mutable version of an `object`/`ReadonlyMap`/`ReadonlySet`/`ReadonlyArray` type. The inverse of `ReadonlyDeep<T>`. Use `Writable<T>` if you only need one level deep.
|
135 | - [`Merge`](source/merge.d.ts) - Merge two types into a new type. Keys of the second type overrides keys of the first type.
|
136 | - [`MergeDeep`](source/merge-deep.d.ts) - Merge two objects or two arrays/tuples recursively into a new type.
|
137 | - [`MergeExclusive`](source/merge-exclusive.d.ts) - Create a type that has mutually exclusive keys.
|
138 | - [`OverrideProperties`](source/override-properties.d.ts) - Override only existing properties of the given type. Similar to `Merge`, but enforces that the original type has the properties you want to override.
|
139 | - [`RequireAtLeastOne`](source/require-at-least-one.d.ts) - Create a type that requires at least one of the given keys.
|
140 | - [`RequireExactlyOne`](source/require-exactly-one.d.ts) - Create a type that requires exactly a single key of the given keys and disallows more.
|
141 | - [`RequireAllOrNone`](source/require-all-or-none.d.ts) - Create a type that requires all of the given keys or none of the given keys.
|
142 | - [`RequireOneOrNone`](source/require-one-or-none.d.ts) - Create a type that requires exactly a single key of the given keys and disallows more, or none of the given keys.
|
143 | - [`SingleKeyObject`](source/single-key-object.d.ts) - Create a type that only accepts an object with a single key.
|
144 | - [`RequiredDeep`](source/required-deep.d.ts) - Create a deeply required version of another type. Use [`Required<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#requiredtype) if you only need one level deep.
|
145 | - [`PickDeep`](source/pick-deep.d.ts) - Pick properties from a deeply-nested object. Use [`Pick<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#picktype-keys) if you only need one level deep.
|
146 | - [`OmitDeep`](source/omit-deep.d.ts) - Omit properties from a deeply-nested object. Use [`Omit<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#omittype-keys) if you only need one level deep.
|
147 | - [`OmitIndexSignature`](source/omit-index-signature.d.ts) - Omit any index signatures from the given object type, leaving only explicitly defined properties.
|
148 | - [`PickIndexSignature`](source/pick-index-signature.d.ts) - Pick only index signatures from the given object type, leaving out all explicitly defined properties.
|
149 | - [`PartialDeep`](source/partial-deep.d.ts) - Create a deeply optional version of another type. Use [`Partial<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#partialtype) if you only need one level deep.
|
150 | - [`PartialOnUndefinedDeep`](source/partial-on-undefined-deep.d.ts) - Create a deep version of another type where all keys accepting `undefined` type are set to optional.
|
151 | - [`UndefinedOnPartialDeep`](source/undefined-on-partial-deep.d.ts) - Create a deep version of another type where all optional keys are set to also accept `undefined`.
|
152 | - [`ReadonlyDeep`](source/readonly-deep.d.ts) - Create a deeply immutable version of an `object`/`Map`/`Set`/`Array` type. Use [`Readonly<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#readonlytype) if you only need one level deep.
|
153 | - [`LiteralUnion`](source/literal-union.d.ts) - Create a union type by combining primitive types and literal types without sacrificing auto-completion in IDEs for the literal type part of the union. Workaround for [Microsoft/TypeScript#29729](https://github.com/Microsoft/TypeScript/issues/29729).
|
154 | - [`Tagged`](source/opaque.d.ts) - Create a [tagged type](https://medium.com/@KevinBGreene/surviving-the-typescript-ecosystem-branding-and-type-tagging-6cf6e516523d) that can support [multiple tags](https://github.com/sindresorhus/type-fest/issues/665) and [per-tag metadata](https://medium.com/@ethanresnick/advanced-typescript-tagged-types-improved-with-type-level-metadata-5072fc125fcf). (This replaces the previous [`Opaque`](source/opaque.d.ts) type, which is now deprecated.)
|
155 | - [`UnwrapTagged`](source/opaque.d.ts) - Get the untagged portion of a tagged type created with `Tagged`. (This replaces the previous [`UnwrapOpaque`](source/opaque.d.ts) type, which is now deprecated.)
|
156 | - [`InvariantOf`](source/invariant-of.d.ts) - Create an [invariant type](https://basarat.gitbook.io/typescript/type-system/type-compatibility#footnote-invariance), which is a type that does not accept supertypes and subtypes.
|
157 | - [`SetOptional`](source/set-optional.d.ts) - Create a type that makes the given keys optional.
|
158 | - [`SetReadonly`](source/set-readonly.d.ts) - Create a type that makes the given keys readonly.
|
159 | - [`SetRequired`](source/set-required.d.ts) - Create a type that makes the given keys required.
|
160 | - [`SetNonNullable`](source/set-non-nullable.d.ts) - Create a type that makes the given keys non-nullable.
|
161 | - [`ValueOf`](source/value-of.d.ts) - Create a union of the given object's values, and optionally specify which keys to get the values from.
|
162 | - [`ConditionalKeys`](source/conditional-keys.d.ts) - Extract keys from a shape where values extend the given `Condition` type.
|
163 | - [`ConditionalPick`](source/conditional-pick.d.ts) - Like `Pick` except it selects properties from a shape where the values extend the given `Condition` type.
|
164 | - [`ConditionalPickDeep`](source/conditional-pick-deep.d.ts) - Like `ConditionalPick` except that it selects the properties deeply.
|
165 | - [`ConditionalExcept`](source/conditional-except.d.ts) - Like `Omit` except it removes properties from a shape where the values extend the given `Condition` type.
|
166 | - [`UnionToIntersection`](source/union-to-intersection.d.ts) - Convert a union type to an intersection type.
|
167 | - [`LiteralToPrimitive`](source/literal-to-primitive.d.ts) - Convert a [literal type](https://www.typescriptlang.org/docs/handbook/2/everyday-types.html#literal-types) to the [primitive type](source/primitive.d.ts) it belongs to.
|
168 | - [`LiteralToPrimitiveDeep`](source/literal-to-primitive-deep.d.ts) - Like `LiteralToPrimitive` except it converts literal types inside an object or array deeply.
|
169 | - [`Stringified`](source/stringified.d.ts) - Create a type with the keys of the given type changed to `string` type.
|
170 | - [`IterableElement`](source/iterable-element.d.ts) - Get the element type of an `Iterable`/`AsyncIterable`. For example, an array or a generator.
|
171 | - [`Entry`](source/entry.d.ts) - Create a type that represents the type of an entry of a collection.
|
172 | - [`Entries`](source/entries.d.ts) - Create a type that represents the type of the entries of a collection.
|
173 | - [`SetReturnType`](source/set-return-type.d.ts) - Create a function type with a return type of your choice and the same parameters as the given function type.
|
174 | - [`SetParameterType`](source/set-parameter-type.d.ts) - Create a function that replaces some parameters with the given parameters.
|
175 | - [`Simplify`](source/simplify.d.ts) - Useful to flatten the type output to improve type hints shown in editors. And also to transform an interface into a type to aide with assignability.
|
176 | - [`SimplifyDeep`](source/simplify-deep.d.ts) - Deeply simplifies an object type.
|
177 | - [`Get`](source/get.d.ts) - Get a deeply-nested property from an object using a key path, like [Lodash's `.get()`](https://lodash.com/docs/latest#get) function.
|
178 | - [`StringKeyOf`](source/string-key-of.d.ts) - Get keys of the given type as strings.
|
179 | - [`Schema`](source/schema.d.ts) - Create a deep version of another object type where property values are recursively replaced into a given value type.
|
180 | - [`Exact`](source/exact.d.ts) - Create a type that does not allow extra properties.
|
181 | - [`OptionalKeysOf`](source/optional-keys-of.d.ts) - Extract all optional keys from the given type.
|
182 | - [`KeysOfUnion`](source/keys-of-union.d.ts) - Create a union of all keys from a given type, even those exclusive to specific union members.
|
183 | - [`HasOptionalKeys`](source/has-optional-keys.d.ts) - Create a `true`/`false` type depending on whether the given type has any optional fields.
|
184 | - [`RequiredKeysOf`](source/required-keys-of.d.ts) - Extract all required keys from the given type.
|
185 | - [`HasRequiredKeys`](source/has-required-keys.d.ts) - Create a `true`/`false` type depending on whether the given type has any required fields.
|
186 | - [`ReadonlyKeysOf`](source/readonly-keys-of.d.ts) - Extract all readonly keys from the given type.
|
187 | - [`HasReadonlyKeys`](source/has-readonly-keys.d.ts) - Create a `true`/`false` type depending on whether the given type has any readonly fields.
|
188 | - [`WritableKeysOf`](source/writable-keys-of.d.ts) - Extract all writable (non-readonly) keys from the given type.
|
189 | - [`HasWritableKeys`](source/has-writable-keys.d.ts) - Create a `true`/`false` type depending on whether the given type has any writable fields.
|
190 | - [`Spread`](source/spread.d.ts) - Mimic the type inferred by TypeScript when merging two objects or two arrays/tuples using the spread syntax.
|
191 | - [`IsEqual`](source/is-equal.d.ts) - Returns a boolean for whether the two given types are equal.
|
192 | - [`TaggedUnion`](source/tagged-union.d.ts) - Create a union of types that share a common discriminant property.
|
193 | - [`IntRange`](source/int-range.d.ts) - Generate a union of numbers.
|
194 | - [`ArrayIndices`](source/array-indices.d.ts) - Provides valid indices for a constant array or tuple.
|
195 | - [`ArrayValues`](source/array-values.d.ts) - Provides all values for a constant array or tuple.
|
196 | - [`ArraySplice`](source/array-splice.d.ts) - Creates a new array type by adding or removing elements at a specified index range in the original array.
|
197 | - [`SetFieldType`](source/set-field-type.d.ts) - Create a type that changes the type of the given keys.
|
198 | - [`Paths`](source/paths.d.ts) - Generate a union of all possible paths to properties in the given object.
|
199 | - [`SharedUnionFieldsDeep`](source/shared-union-fields-deep.d.ts) - Create a type with shared fields from a union of object types, deeply traversing nested structures.
|
200 | - [`DistributedOmit`](source/distributed-omit.d.ts) - Omits keys from a type, distributing the operation over a union.
|
201 | - [`DistributedPick`](source/distributed-pick.d.ts) - Picks keys from a type, distributing the operation over a union.
|
202 | - [`And`](source/and.d.ts) - Returns a boolean for whether two given types are both true.
|
203 | - [`Or`](source/or.d.ts) - Returns a boolean for whether either of two given types are true.
|
204 |
|
205 | ### Type Guard
|
206 |
|
207 | #### `IsType` vs. `IfType`
|
208 |
|
209 | For every `IsT` type (e.g. `IsAny`), there is an associated `IfT` type that can help simplify conditional types. While the `IsT` types return a `boolean`, the `IfT` types act like an `If`/`Else` - they resolve to the given `TypeIfT` or `TypeIfNotT` depending on whether `IsX` is `true` or not. By default, `IfT` returns a `boolean`:
|
210 |
|
211 | ```ts
|
212 | type IfAny<T, TypeIfAny = true, TypeIfNotAny = false> = (
|
213 | IsAny<T> extends true ? TypeIfAny : TypeIfNotAny
|
214 | );
|
215 | ```
|
216 |
|
217 | #### Usage
|
218 |
|
219 | ```ts
|
220 | import type {IsAny, IfAny} from 'type-fest';
|
221 |
|
222 | type ShouldBeTrue = IsAny<any> extends true ? true : false;
|
223 | //=> true
|
224 |
|
225 | type ShouldBeFalse = IfAny<'not any'>;
|
226 | //=> false
|
227 |
|
228 | type ShouldBeNever = IfAny<'not any', 'not never', 'never'>;
|
229 | //=> 'never'
|
230 | ```
|
231 |
|
232 | - [`IsLiteral`](source/is-literal.d.ts) - Returns a boolean for whether the given type is a [literal type](https://www.typescriptlang.org/docs/handbook/2/everyday-types.html#literal-types).
|
233 | - [`IsStringLiteral`](source/is-literal.d.ts) - Returns a boolean for whether the given type is a `string` [literal type](https://www.typescriptlang.org/docs/handbook/2/everyday-types.html#literal-types).
|
234 | - [`IsNumericLiteral`](source/is-literal.d.ts) - Returns a boolean for whether the given type is a `number` or `bigint` [literal type](https://www.typescriptlang.org/docs/handbook/2/everyday-types.html#literal-types).
|
235 | - [`IsBooleanLiteral`](source/is-literal.d.ts) - Returns a boolean for whether the given type is a `true` or `false` [literal type](https://www.typescriptlang.org/docs/handbook/2/everyday-types.html#literal-types).
|
236 | - [`IsSymbolLiteral`](source/is-literal.d.ts) - Returns a boolean for whether the given type is a `symbol` [literal type](https://www.typescriptlang.org/docs/handbook/2/everyday-types.html#literal-types).
|
237 | - [`IsAny`](source/is-any.d.ts) - Returns a boolean for whether the given type is `any`. (Conditional version: [`IfAny`](source/if-any.d.ts))
|
238 | - [`IsNever`](source/is-never.d.ts) - Returns a boolean for whether the given type is `never`. (Conditional version: [`IfNever`](source/if-never.d.ts))
|
239 | - [`IsUnknown`](source/is-unknown.d.ts) - Returns a boolean for whether the given type is `unknown`. (Conditional version: [`IfUnknown`](source/if-unknown.d.ts))
|
240 | - [`IsEmptyObject`](source/empty-object.d.ts) - Returns a boolean for whether the type is strictly equal to an empty plain object, the `{}` value. (Conditional version: [`IfEmptyObject`](source/if-empty-object.d.ts))
|
241 | - [`IsNull`](source/is-null.d.ts) - Returns a boolean for whether the given type is `null`. (Conditional version: [`IfNull`](source/if-null.d.ts))
|
242 |
|
243 | ### JSON
|
244 |
|
245 | - [`Jsonify`](source/jsonify.d.ts) - Transform a type to one that is assignable to the `JsonValue` type.
|
246 | - [`Jsonifiable`](source/jsonifiable.d.ts) - Matches a value that can be losslessly converted to JSON.
|
247 | - [`JsonPrimitive`](source/basic.d.ts) - Matches a JSON primitive.
|
248 | - [`JsonObject`](source/basic.d.ts) - Matches a JSON object.
|
249 | - [`JsonArray`](source/basic.d.ts) - Matches a JSON array.
|
250 | - [`JsonValue`](source/basic.d.ts) - Matches any valid JSON value.
|
251 |
|
252 | ### Async
|
253 |
|
254 | - [`Promisable`](source/promisable.d.ts) - Create a type that represents either the value or the value wrapped in `PromiseLike`.
|
255 | - [`AsyncReturnType`](source/async-return-type.d.ts) - Unwrap the return type of a function that returns a `Promise`.
|
256 | - [`Asyncify`](source/asyncify.d.ts) - Create an async version of the given function type.
|
257 |
|
258 | ### String
|
259 |
|
260 | - [`Trim`](source/trim.d.ts) - Remove leading and trailing spaces from a string.
|
261 | - [`Split`](source/split.d.ts) - Represents an array of strings split using a given character or character set.
|
262 | - [`Replace`](source/replace.d.ts) - Represents a string with some or all matches replaced by a replacement.
|
263 | - [`StringSlice`](source/string-slice.d.ts) - Returns a string slice of a given range, just like `String#slice()`.
|
264 |
|
265 | ### Array
|
266 |
|
267 | - [`Includes`](source/includes.d.ts) - Returns a boolean for whether the given array includes the given item.
|
268 | - [`Join`](source/join.d.ts) - Join an array of strings and/or numbers using the given string as a delimiter.
|
269 | - [`ArraySlice`](source/array-slice.d.ts) - Returns an array slice of a given range, just like `Array#slice()`.
|
270 | - [`LastArrayElement`](source/last-array-element.d.ts) - Extracts the type of the last element of an array.
|
271 | - [`FixedLengthArray`](source/fixed-length-array.d.ts) - Create a type that represents an array of the given type and length.
|
272 | - [`MultidimensionalArray`](source/multidimensional-array.d.ts) - Create a type that represents a multidimensional array of the given type and dimensions.
|
273 | - [`MultidimensionalReadonlyArray`](source/multidimensional-readonly-array.d.ts) - Create a type that represents a multidimensional readonly array of the given type and dimensions.
|
274 | - [`ReadonlyTuple`](source/readonly-tuple.d.ts) - Create a type that represents a read-only tuple of the given type and length.
|
275 | - [`TupleToUnion`](source/tuple-to-union.d.ts) - Convert a tuple/array into a union type of its elements.
|
276 |
|
277 | ### Numeric
|
278 |
|
279 | - [`PositiveInfinity`](source/numeric.d.ts) - Matches the hidden `Infinity` type.
|
280 | - [`NegativeInfinity`](source/numeric.d.ts) - Matches the hidden `-Infinity` type.
|
281 | - [`Finite`](source/numeric.d.ts) - A finite `number`.
|
282 | - [`Integer`](source/numeric.d.ts) - A `number` that is an integer.
|
283 | - [`Float`](source/numeric.d.ts) - A `number` that is not an integer.
|
284 | - [`NegativeFloat`](source/numeric.d.ts) - A negative (`-∞ < x < 0`) `number` that is not an integer.
|
285 | - [`Negative`](source/numeric.d.ts) - A negative `number`/`bigint` (`-∞ < x < 0`)
|
286 | - [`NonNegative`](source/numeric.d.ts) - A non-negative `number`/`bigint` (`0 <= x < ∞`).
|
287 | - [`NegativeInteger`](source/numeric.d.ts) - A negative (`-∞ < x < 0`) `number` that is an integer.
|
288 | - [`NonNegativeInteger`](source/numeric.d.ts) - A non-negative (`0 <= x < ∞`) `number` that is an integer.
|
289 | - [`IsNegative`](source/numeric.d.ts) - Returns a boolean for whether the given number is a negative number.
|
290 | - [`IsFloat`](source/is-float.d.ts) - Returns a boolean for whether the given number is a float, like `1.5` or `-1.5`.
|
291 | - [`IsInteger`](source/is-integer.d.ts) - Returns a boolean for whether the given number is a integer, like `-5`, `1.0` or `100`.
|
292 | - [`GreaterThan`](source/greater-than.d.ts) - Returns a boolean for whether a given number is greater than another number.
|
293 | - [`GreaterThanOrEqual`](source/greater-than-or-equal.d.ts) - Returns a boolean for whether a given number is greater than or equal to another number.
|
294 | - [`LessThan`](source/less-than.d.ts) - Returns a boolean for whether a given number is less than another number.
|
295 | - [`LessThanOrEqual`](source/less-than-or-equal.d.ts) - Returns a boolean for whether a given number is less than or equal to another number.
|
296 | - [`Sum`](source/sum.d.ts) - Returns the sum of two numbers.
|
297 | - [`Subtract`](source/subtract.d.ts) - Returns the difference between two numbers.
|
298 |
|
299 | ### Change case
|
300 |
|
301 | - [`CamelCase`](source/camel-case.d.ts) - Convert a string literal to camel-case (`fooBar`).
|
302 | - [`CamelCasedProperties`](source/camel-cased-properties.d.ts) - Convert object properties to camel-case (`fooBar`).
|
303 | - [`CamelCasedPropertiesDeep`](source/camel-cased-properties-deep.d.ts) - Convert object properties to camel-case recursively (`fooBar`).
|
304 | - [`KebabCase`](source/kebab-case.d.ts) - Convert a string literal to kebab-case (`foo-bar`).
|
305 | - [`KebabCasedProperties`](source/kebab-cased-properties.d.ts) - Convert a object properties to kebab-case recursively (`foo-bar`).
|
306 | - [`KebabCasedPropertiesDeep`](source/kebab-cased-properties-deep.d.ts) - Convert object properties to kebab-case (`foo-bar`).
|
307 | - [`PascalCase`](source/pascal-case.d.ts) - Converts a string literal to pascal-case (`FooBar`)
|
308 | - [`PascalCasedProperties`](source/pascal-cased-properties.d.ts) - Converts object properties to pascal-case (`FooBar`)
|
309 | - [`PascalCasedPropertiesDeep`](source/pascal-cased-properties-deep.d.ts) - Converts object properties to pascal-case (`FooBar`)
|
310 | - [`SnakeCase`](source/snake-case.d.ts) - Convert a string literal to snake-case (`foo_bar`).
|
311 | - [`SnakeCasedProperties`](source/snake-cased-properties.d.ts) - Convert object properties to snake-case (`foo_bar`).
|
312 | - [`SnakeCasedPropertiesDeep`](source/snake-cased-properties-deep.d.ts) - Convert object properties to snake-case recursively (`foo_bar`).
|
313 | - [`ScreamingSnakeCase`](source/screaming-snake-case.d.ts) - Convert a string literal to screaming-snake-case (`FOO_BAR`).
|
314 | - [`DelimiterCase`](source/delimiter-case.d.ts) - Convert a string literal to a custom string delimiter casing.
|
315 | - [`DelimiterCasedProperties`](source/delimiter-cased-properties.d.ts) - Convert object properties to a custom string delimiter casing.
|
316 | - [`DelimiterCasedPropertiesDeep`](source/delimiter-cased-properties-deep.d.ts) - Convert object properties to a custom string delimiter casing recursively.
|
317 |
|
318 | ### Miscellaneous
|
319 |
|
320 | - [`GlobalThis`](source/global-this.d.ts) - Declare locally scoped properties on `globalThis`.
|
321 | - [`PackageJson`](source/package-json.d.ts) - Type for [npm's `package.json` file](https://docs.npmjs.com/creating-a-package-json-file). It also includes support for [TypeScript Declaration Files](https://www.typescriptlang.org/docs/handbook/declaration-files/publishing.html).
|
322 | - [`TsConfigJson`](source/tsconfig-json.d.ts) - Type for [TypeScript's `tsconfig.json` file](https://www.typescriptlang.org/docs/handbook/tsconfig-json.html).
|
323 |
|
324 | ## Declined types
|
325 |
|
326 | *If we decline a type addition, we will make sure to document the better solution here.*
|
327 |
|
328 | - [`Diff` and `Spread`](https://github.com/sindresorhus/type-fest/pull/7) - The pull request author didn't provide any real-world use-cases and the PR went stale. If you think this type is useful, provide some real-world use-cases and we might reconsider.
|
329 | - [`Dictionary`](https://github.com/sindresorhus/type-fest/issues/33) - You only save a few characters (`Dictionary<number>` vs `Record<string, number>`) from [`Record`](https://www.typescriptlang.org/docs/handbook/utility-types.html#recordkeys-type), which is more flexible and well-known. Also, you shouldn't use an object as a dictionary. We have `Map` in JavaScript now.
|
330 | - [`ExtractProperties` and `ExtractMethods`](https://github.com/sindresorhus/type-fest/pull/4) - The types violate the single responsibility principle. Instead, refine your types into more granular type hierarchies.
|
331 | - [`Url2Json`](https://github.com/sindresorhus/type-fest/pull/262) - Inferring search parameters from a URL string is a cute idea, but not very useful in practice, since search parameters are usually dynamic and defined separately.
|
332 | - [`Nullish`](https://github.com/sindresorhus/type-fest/pull/318) - The type only saves a couple of characters, not everyone knows what "nullish" means, and I'm also trying to [get away from `null`](https://github.com/sindresorhus/meta/discussions/7).
|
333 | - [`TitleCase`](https://github.com/sindresorhus/type-fest/pull/303) - It's not solving a common need and is a better fit for a separate package.
|
334 | - [`ExtendOr` and `ExtendAnd`](https://github.com/sindresorhus/type-fest/pull/247) - The benefits don't outweigh having to learn what they mean.
|
335 | - [`PackageJsonExtras`](https://github.com/sindresorhus/type-fest/issues/371) - There are too many possible configurations that can be put into `package.json`. If you would like to extend `PackageJson` to support an additional configuration in your project, please see the *Extending existing types* section below.
|
336 |
|
337 | ## Alternative type names
|
338 |
|
339 | *If you know one of our types by a different name, add it here for discovery.*
|
340 |
|
341 | - `Prettify`- See [`Simplify`](source/simplify.d.ts)
|
342 | - `Expand`- See [`Simplify`](source/simplify.d.ts)
|
343 | - `PartialBy` - See [`SetOptional`](source/set-optional.d.ts)
|
344 | - `RecordDeep`- See [`Schema`](source/schema.d.ts)
|
345 | - `Mutable`- See [`Writable`](source/writable.d.ts)
|
346 | - `RequireOnlyOne` - See [`RequireExactlyOne`](source/require-exactly-one.d.ts)
|
347 | - `AtMostOne` - See [`RequireOneOrNone`](source/require-one-or-none.d.ts)
|
348 | - `AllKeys` - See [`KeysOfUnion`](source/keys-of-union.d.ts)
|
349 | - `Branded` - See [`Tagged`](source/opaque.d.ts)
|
350 | - `Opaque` - See [`Tagged`](source/opaque.d.ts)
|
351 |
|
352 | ## Tips
|
353 |
|
354 | ### Extending existing types
|
355 |
|
356 | - [`PackageJson`](source/package-json.d.ts) - There are a lot of tools that place extra configurations inside the `package.json` file. You can extend `PackageJson` to support these additional configurations.
|
357 | <details>
|
358 | <summary>
|
359 | Example
|
360 | </summary>
|
361 |
|
362 | [Playground](https://www.typescriptlang.org/play?#code/JYWwDg9gTgLgBDAnmApnA3gBQIYGMDW2A5igFIDOEAdnNuXAEJ0o4HFmVUC+cAZlBBBwA5ElQBaXinIxhAbgCwAKFCRYCZGnQAZYFRgooPfoJHSANntmKlysWlaESFanAC8jZo-YuaAMgwLKwBhal5gIgB+AC44XX1DADpQqnCiLhsgA)
|
363 |
|
364 | ```ts
|
365 | import type {PackageJson as BasePackageJson} from 'type-fest';
|
366 | import type {Linter} from 'eslint';
|
367 |
|
368 | type PackageJson = BasePackageJson & {eslintConfig?: Linter.Config};
|
369 | ```
|
370 | </details>
|
371 |
|
372 | ### Related
|
373 |
|
374 | - [typed-query-selector](https://github.com/g-plane/typed-query-selector) - Enhances `document.querySelector` and `document.querySelectorAll` with a template literal type that matches element types returned from an HTML element query selector.
|
375 | - [`Linter.Config`](https://github.com/DefinitelyTyped/DefinitelyTyped/blob/master/types/eslint/index.d.ts) - Definitions for the [ESLint configuration schema](https://eslint.org/docs/user-guide/configuring/language-options).
|
376 |
|
377 | ### Built-in types
|
378 |
|
379 | There are many advanced types most users don't know about.
|
380 |
|
381 | - [`Partial<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#partialtype) - Make all properties in `T` optional.
|
382 | <details>
|
383 | <summary>
|
384 | Example
|
385 | </summary>
|
386 |
|
387 | [Playground](https://www.typescriptlang.org/play/#code/JYOwLgpgTgZghgYwgAgHIHsAmEDC6QzADmyA3gLABQyycADnanALYQBcyAzmFKEQNxUaddFDAcQAV2YAjaIMoBfKlQQAbOJ05osEAIIMAQpOBrsUMkOR1eANziRkCfISKSoD4Pg4ZseAsTIALyW1DS0DEysHADkvvoMMQA0VsKi4sgAzAAMuVaKClY2wPaOknSYDrguADwA0sgQAB6QIJjaANYQAJ7oMDp+LsQAfAAUXd0cdUnI9mo+uv6uANp1ALoAlKHhyGAAFsCcAHTOAW4eYF4gyxNrwbNwago0ypRWp66jH8QcAApwYmAjxq8SWIy2FDCNDA3ToKFBQyIdR69wmfQG1TOhShyBgomQX3w3GQE2Q6IA8jIAFYQBBgI4TTiEs5bTQYsFInrLTbbHZOIlgZDlSqQABqj0kKBC3yINx6a2xfOQwH6o2FVXFaklwSCIUkbQghBAEEwENSfNOlykEGefNe5uhB2O6sgS3GPRmLogmslG1tLxUOKgEDA7hAuydtteryAA)
|
388 |
|
389 | ```ts
|
390 | interface NodeConfig {
|
391 | appName: string;
|
392 | port: number;
|
393 | }
|
394 |
|
395 | class NodeAppBuilder {
|
396 | private configuration: NodeConfig = {
|
397 | appName: 'NodeApp',
|
398 | port: 3000
|
399 | };
|
400 |
|
401 | private updateConfig<Key extends keyof NodeConfig>(key: Key, value: NodeConfig[Key]) {
|
402 | this.configuration[key] = value;
|
403 | }
|
404 |
|
405 | config(config: Partial<NodeConfig>) {
|
406 | type NodeConfigKey = keyof NodeConfig;
|
407 |
|
408 | for (const key of Object.keys(config) as NodeConfigKey[]) {
|
409 | const updateValue = config[key];
|
410 |
|
411 | if (updateValue === undefined) {
|
412 | continue;
|
413 | }
|
414 |
|
415 | this.updateConfig(key, updateValue);
|
416 | }
|
417 |
|
418 | return this;
|
419 | }
|
420 | }
|
421 |
|
422 | // `Partial<NodeConfig>`` allows us to provide only a part of the
|
423 | // NodeConfig interface.
|
424 | new NodeAppBuilder().config({appName: 'ToDoApp'});
|
425 | ```
|
426 | </details>
|
427 |
|
428 | - [`Required<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#requiredtype) - Make all properties in `T` required.
|
429 | <details>
|
430 | <summary>
|
431 | Example
|
432 | </summary>
|
433 |
|
434 | [Playground](https://typescript-play.js.org/?target=6#code/AQ4SwOwFwUwJwGYEMDGNgGED21VQGJZwC2wA3gFCjXAzFJgA2A-AFzADOUckA5gNxUaIYjA4ckvGG07c+g6gF8KQkAgCuEFFDA5O6gEbEwUbLm2ESwABQIixACJIoSdgCUYAR3Vg4MACYAPGYuFvYAfACU5Ko0APRxwADKMBD+wFAAFuh2Vv7OSBlYGdmc8ABu8LHKsRyGxqY4oQT21pTCIHQMjOwA5DAAHgACxAAOjDAAdChYxL0ANLHUouKSMH0AEmAAhJhY6ozpAJ77GTCMjMCiV0ToSAb7UJPPC9WRgrEJwAAqR6MwSRQPFGUFocDgRHYxnEfGAowh-zgUCOwF6KwkUl6tXqJhCeEsxDaS1AXSYfUGI3GUxmc0WSneQA)
|
435 |
|
436 | ```ts
|
437 | interface ContactForm {
|
438 | email?: string;
|
439 | message?: string;
|
440 | }
|
441 |
|
442 | function submitContactForm(formData: Required<ContactForm>) {
|
443 | // Send the form data to the server.
|
444 | }
|
445 |
|
446 | submitContactForm({
|
447 | email: 'ex@mple.com',
|
448 | message: 'Hi! Could you tell me more about…',
|
449 | });
|
450 |
|
451 | // TypeScript error: missing property 'message'
|
452 | submitContactForm({
|
453 | email: 'ex@mple.com',
|
454 | });
|
455 | ```
|
456 | </details>
|
457 |
|
458 | - [`Readonly<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#readonlytype) - Make all properties in `T` readonly.
|
459 | <details>
|
460 | <summary>
|
461 | Example
|
462 | </summary>
|
463 |
|
464 | [Playground](https://typescript-play.js.org/?target=6#code/AQ4UwOwVwW2AZA9gc3mAbmANsA3gKFCOAHkAzMgGkOJABEwAjKZa2kAUQCcvEu32AMQCGAF2FYBIAL4BufDRABLCKLBcywgMZgEKZOoDCiCGSXI8i4hGEwwALmABnUVxXJ57YFgzZHSVF8sT1BpBSItLGEnJz1kAy5LLy0TM2RHACUwYQATEywATwAeAITjU3MAPnkrCJMXLigtUT4AClxgGztKbyDgaX99I1TzAEokr1BRAAslJwA6FIqLAF48TtswHp9MHDla9hJGACswZvmyLjAwAC8wVpm5xZHkUZDaMKIwqyWXYCW0oN4sNlsA1h0ug5gAByACyBQAggAHJHQ7ZBIFoXbzBjMCz7OoQP5YIaJNYQMAAdziCVaALGNSIAHomcAACoFJFgADKWjcSNEwG4vC4ji0wggEEQguiTnMEGALWAV1yAFp8gVgEjeFyuKICvMrCTgVxnst5jtsGC4ljsPNhXxGaAWcAAOq6YRXYDCRg+RWIcA5JSC+kWdCepQ+v3RYCU3RInzRMCGwlpC19NYBW1Ye08R1AA)
|
465 |
|
466 | ```ts
|
467 | enum LogLevel {
|
468 | Off,
|
469 | Debug,
|
470 | Error,
|
471 | Fatal
|
472 | };
|
473 |
|
474 | interface LoggerConfig {
|
475 | name: string;
|
476 | level: LogLevel;
|
477 | }
|
478 |
|
479 | class Logger {
|
480 | config: Readonly<LoggerConfig>;
|
481 |
|
482 | constructor({name, level}: LoggerConfig) {
|
483 | this.config = {name, level};
|
484 | Object.freeze(this.config);
|
485 | }
|
486 | }
|
487 |
|
488 | const config: LoggerConfig = {
|
489 | name: 'MyApp',
|
490 | level: LogLevel.Debug
|
491 | };
|
492 |
|
493 | const logger = new Logger(config);
|
494 |
|
495 | // TypeScript Error: cannot assign to read-only property.
|
496 | logger.config.level = LogLevel.Error;
|
497 |
|
498 | // We are able to edit config variable as we please.
|
499 | config.level = LogLevel.Error;
|
500 | ```
|
501 | </details>
|
502 |
|
503 | - [`Pick<T, K>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#picktype-keys) - From `T`, pick a set of properties whose keys are in the union `K`.
|
504 | <details>
|
505 | <summary>
|
506 | Example
|
507 | </summary>
|
508 |
|
509 | [Playground](https://typescript-play.js.org/?target=6#code/AQ4SwOwFwUwJwGYEMDGNgEE5TCgNugN4BQoZwOUBAXMAM5RyQDmA3KeSFABYCuAtgCMISMHloMmENh04oA9tBjQJjFuzIBfYrOAB6PcADCcGElh1gEGAHcKATwAO6ebyjB5CTNlwFwSxFR0BX5HeToYABNgBDh5fm8cfBg6AHIKG3ldA2BHOOcfFNpUygJ0pAhokr4hETFUgDpswywkggAFUwA3MFtgAF5gQgowKhhVKTYKGuFRcXo1aVZgbTIoJ3RW3xhOmB6+wfbcAGsAHi3kgBpgEtGy4AAfG54BWfqAPnZm4AAlZUj4MAkMA8GAGB4vEgfMlLLw6CwPBA8PYRmMgZVgAC6CgmI4cIommQELwICh8RBgKZKvALh1ur0bHQABR5PYMui0Wk7em2ADaAF0AJS0AASABUALIAGQAogR+Mp3CROCAFBBwVC2ikBpj5CgBIqGjizLA5TAFdAmalImAuqlBRoVQh5HBgEy1eDWfs7J5cjzGYKhroVfpDEhHM4MV6GRR5NN0JrtnRg6BVirTFBeHAKYmYY6QNpdB73LmCJZBlSAXAubtvczeSmQMNSuMbmKNgBlHFgPEUNwusBIPAAQlS1xetTmxT0SDoESgdD0C4aACtHMwxytLrohawgA)
|
510 |
|
511 | ```ts
|
512 | interface Article {
|
513 | title: string;
|
514 | thumbnail: string;
|
515 | content: string;
|
516 | }
|
517 |
|
518 | // Creates new type out of the `Article` interface composed
|
519 | // from the Articles' two properties: `title` and `thumbnail`.
|
520 | // `ArticlePreview = {title: string; thumbnail: string}`
|
521 | type ArticlePreview = Pick<Article, 'title' | 'thumbnail'>;
|
522 |
|
523 | // Render a list of articles using only title and description.
|
524 | function renderArticlePreviews(previews: ArticlePreview[]): HTMLElement {
|
525 | const articles = document.createElement('div');
|
526 |
|
527 | for (const preview of previews) {
|
528 | // Append preview to the articles.
|
529 | }
|
530 |
|
531 | return articles;
|
532 | }
|
533 |
|
534 | const articles = renderArticlePreviews([
|
535 | {
|
536 | title: 'TypeScript tutorial!',
|
537 | thumbnail: '/assets/ts.jpg'
|
538 | }
|
539 | ]);
|
540 | ```
|
541 | </details>
|
542 |
|
543 | - [`Record<K, T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#recordkeys-type) - Construct a type with a set of properties `K` of type `T`.
|
544 | <details>
|
545 | <summary>
|
546 | Example
|
547 | </summary>
|
548 |
|
549 | [Playground](https://typescript-play.js.org/?target=6#code/AQ4ejYAUHsGcCWAXBMB2dgwGbAKYC2ADgDYwCeeemCaWArgE7ADGMxAhmuQHQBQoYEnJE8wALKEARnkaxEKdMAC8wAOS0kstGuAAfdQBM8ANzxlRjXQbVaWACwC0JPB0NqA3HwGgIwAJJoWozYHCxixnAsjAhStADmwESMMJYo1Fi4HMCIaPEu+MRklHj8gpqyoeHAAKJFFFTAAN4+giDYCIxwSAByHAR4AFw5SDF5Xm2gJBzdfQPD3WPxE5PAlBxdAPLYNQAelgh4aOHDaPQEMowrIAC+3oJ+AMKMrlrAXFhSAFZ4LEhC9g4-0BmA4JBISXgiCkBQABpILrJ5MhUGhYcATGD6Bk4Hh-jNgABrPDkOBlXyQAAq9ngYmJpOAAHcEOCRjAXqwYODfoo6DhakUSph+Uh7GI4P0xER4Cj0OSQGwMP8tP1hgAlX7swwAHgRl2RvIANALSA08ABtAC6AD4VM1Wm0Kow0MMrYaHYJjGYLLJXZb3at1HYnC43Go-QHQDcvA6-JsmEJXARgCDgMYWAhjIYhDAU+YiMAAFIwex0ZmilMITCGF79TLAGRsAgJYAAZRwSEZGzEABFTOZUrJ5Yn+jwnWgeER6HB7AAKJrADpdXqS4ZqYultTG6azVfqHswPBbtauLY7fayQ7HIbAAAMwBuAEoYw9IBq2Ixs9h2eFMOQYPQObALQKJgggABeYhghCIpikkKRpOQRIknAsZUiIeCttECBEP8NSMCkjDDAARMGziuIYxHwYOjDCMBmDNnAuTxA6irdCOBB1Lh5Dqpqn66tISIykawBnOCtqqC0gbjqc9DgpGkxegOliyfJDrRkAA)
|
550 |
|
551 | ```ts
|
552 | // Positions of employees in our company.
|
553 | type MemberPosition = 'intern' | 'developer' | 'tech-lead';
|
554 |
|
555 | // Interface describing properties of a single employee.
|
556 | interface Employee {
|
557 | firstName: string;
|
558 | lastName: string;
|
559 | yearsOfExperience: number;
|
560 | }
|
561 |
|
562 | // Create an object that has all possible `MemberPosition` values set as keys.
|
563 | // Those keys will store a collection of Employees of the same position.
|
564 | const team: Record<MemberPosition, Employee[]> = {
|
565 | intern: [],
|
566 | developer: [],
|
567 | 'tech-lead': [],
|
568 | };
|
569 |
|
570 | // Our team has decided to help John with his dream of becoming Software Developer.
|
571 | team.intern.push({
|
572 | firstName: 'John',
|
573 | lastName: 'Doe',
|
574 | yearsOfExperience: 0
|
575 | });
|
576 |
|
577 | // `Record` forces you to initialize all of the property keys.
|
578 | // TypeScript Error: "tech-lead" property is missing
|
579 | const teamEmpty: Record<MemberPosition, null> = {
|
580 | intern: null,
|
581 | developer: null,
|
582 | };
|
583 | ```
|
584 | </details>
|
585 |
|
586 | - [`Exclude<T, U>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#excludetype-excludedunion) - Exclude from `T` those types that are assignable to `U`.
|
587 | <details>
|
588 | <summary>
|
589 | Example
|
590 | </summary>
|
591 |
|
592 | [Playground](https://typescript-play.js.org/?target=6#code/JYOwLgpgTgZghgYwgAgMrQG7QMIHsQzADmyA3gFDLIAOuUYAXMiAK4A2byAPsgM5hRQJHqwC2AI2gBucgF9y5MAE9qKAEoQAjiwj8AEnBAATNtGQBeZAAooWphu26wAGmS3e93bRC8IASgsAPmRDJRlyAHoI5ABRAA8ENhYjFFYOZGVVZBgoXFFkAAM0zh5+QRBhZhYJaAKAOkjogEkQZAQ4X2QAdwALCFbaemRgXmQtFjhOMFwq9K6ULuB0lk6U+HYwZAxJnQaYFhAEMGB8ZCIIMAAFOjAANR2IK0HGWISklIAedCgsKDwCYgAbQA5M9gQBdVzFQJ+JhiSRQMiUYYwayZCC4VHPCzmSzAspCYEBWxgFhQAZwKC+FpgJ43VwARgADH4ZFQSWSBjcZPJyPtDsdTvxKWBvr8rD1DCZoJ5HPopaYoK4EPhCEQmGKcKriLCtrhgEYkVQVT5Nr4fmZLLZtMBbFZgT0wGBqES6ghbHBIJqoBKFdBWQpjfh+DQbhY2tqiHVsbjLMVkAB+ZAAZiZaeQTHOVxu9ySjxNaujNwDVHNvzqbBGkBAdPoAfkQA)
|
593 |
|
594 | ```ts
|
595 | interface ServerConfig {
|
596 | port: null | string | number;
|
597 | }
|
598 |
|
599 | type RequestHandler = (request: Request, response: Response) => void;
|
600 |
|
601 | // Exclude `null` type from `null | string | number`.
|
602 | // In case the port is equal to `null`, we will use default value.
|
603 | function getPortValue(port: Exclude<ServerConfig['port'], null>): number {
|
604 | if (typeof port === 'string') {
|
605 | return parseInt(port, 10);
|
606 | }
|
607 |
|
608 | return port;
|
609 | }
|
610 |
|
611 | function startServer(handler: RequestHandler, config: ServerConfig): void {
|
612 | const server = require('http').createServer(handler);
|
613 |
|
614 | const port = config.port === null ? 3000 : getPortValue(config.port);
|
615 | server.listen(port);
|
616 | }
|
617 | ```
|
618 | </details>
|
619 |
|
620 | - [`Extract<T, U>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#extracttype-union) - Extract from `T` those types that are assignable to `U`.
|
621 | <details>
|
622 | <summary>
|
623 | Example
|
624 | </summary>
|
625 |
|
626 | [Playground](https://typescript-play.js.org/?target=6#code/CYUwxgNghgTiAEAzArgOzAFwJYHtXzSwEdkQBJYACgEoAueVZAWwCMQYBuAKDDwGcM8MgBF4AXngBlAJ6scESgHIRi6ty5ZUGdoihgEABXZ888AN5d48ANoiAuvUat23K6ihMQ9ATE0BzV3goPy8GZjZOLgBfLi4Aejj4AEEICBwAdz54MAALKFQQ+BxEeAAHY1NgKAwoIKy0grr4DByEUpgccpgMaXgAaxBerCzi+B9-ZulygDouFHRsU1z8kKMYE1RhaqgAHkt4AHkWACt4EAAPbVRgLLWNgBp9gGlBs8uQa6yAUUuYPQwdgNpKM7nh7mMML4CgA+R5WABqUAgpDeVxuhxO1he0jsXGh8EoOBO9COx3BQPo2PBADckaR6IjkSA6PBqTgsMBzPsicdrEC7OJWXSQNwYvFEgAVTS9JLXODpeDpKBZFg4GCoWa8VACIJykAKiQWKy2YQOAioYikCg0OEMDyhRSy4DyxS24KhAAMjyi6gS8AAwjh5OD0iBFHAkJoEOksC1mnkMJq8gUQKDNttKPlnfrwYp3J5XfBHXqoKpfYkAOI4ansTxaeDADmoRSCCBYAbxhC6TDx6rwYHIRX5bScjA4bLJwoDmDwDkfbA9JMrVMVdM1TN69LgkTgwgkchUahqIA)
|
627 |
|
628 | ```ts
|
629 | declare function uniqueId(): number;
|
630 |
|
631 | const ID = Symbol('ID');
|
632 |
|
633 | interface Person {
|
634 | [ID]: number;
|
635 | name: string;
|
636 | age: number;
|
637 | }
|
638 |
|
639 | // Allows changing the person data as long as the property key is of string type.
|
640 | function changePersonData<
|
641 | Obj extends Person,
|
642 | Key extends Extract<keyof Person, string>,
|
643 | Value extends Obj[Key]
|
644 | > (obj: Obj, key: Key, value: Value): void {
|
645 | obj[key] = value;
|
646 | }
|
647 |
|
648 | // Tiny Andrew was born.
|
649 | const andrew = {
|
650 | [ID]: uniqueId(),
|
651 | name: 'Andrew',
|
652 | age: 0,
|
653 | };
|
654 |
|
655 | // Cool, we're fine with that.
|
656 | changePersonData(andrew, 'name', 'Pony');
|
657 |
|
658 | // Government didn't like the fact that you wanted to change your identity.
|
659 | changePersonData(andrew, ID, uniqueId());
|
660 | ```
|
661 | </details>
|
662 |
|
663 | - [`NonNullable<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#nonnullabletype) - Exclude `null` and `undefined` from `T`.
|
664 | <details>
|
665 | <summary>
|
666 | Example
|
667 | </summary>
|
668 | Works with <a href="https://www.typescriptlang.org/tsconfig#strictNullChecks"><code>strictNullChecks</code></a> set to <code>true</code>.
|
669 |
|
670 | [Playground](https://typescript-play.js.org/?target=6#code/C4TwDgpgBACg9gJ2AOQK4FsBGEFQLxQDOwCAlgHYDmUAPlORtrnQwDasDcAUFwPQBU-WAEMkUOADMowqAGNWwwoSgATCBIqlgpOOSjAAFsOBRSy1IQgr9cKJlSlW1mZYQA3HFH68u8xcoBlHA8EACEHJ08Aby4oKDBUTFZSWXjEFEYcAEIALihkXTR2YSSIAB54JDQsHAA+blj4xOTUsHSACkMzPKD3HHDHNQQAGjSkPMqMmoQASh7g-oihqBi4uNIpdraxPAI2VhmVxrX9AzMAOm2ppnwoAA4ABifuE4BfKAhWSyOTuK7CS7pao3AhXF5rV48E4ICDAVAIPT-cGQyG+XTEIgLMJLTx7CAAdygvRCA0iCHaMwarhJOIQjUBSHaACJHk8mYdeLwxtdcVAAOSsh58+lXdr7Dlcq7A3n3J4PEUdADMcspUE53OluAIUGVTx46oAKuAIAFZGQwCYAKIIBCILjUxaDHAMnla+iodjcIA)
|
671 |
|
672 | ```ts
|
673 | type PortNumber = string | number | null;
|
674 |
|
675 | /** Part of a class definition that is used to build a server */
|
676 | class ServerBuilder {
|
677 | portNumber!: NonNullable<PortNumber>;
|
678 |
|
679 | port(this: ServerBuilder, port: PortNumber): ServerBuilder {
|
680 | if (port == null) {
|
681 | this.portNumber = 8000;
|
682 | } else {
|
683 | this.portNumber = port;
|
684 | }
|
685 |
|
686 | return this;
|
687 | }
|
688 | }
|
689 |
|
690 | const serverBuilder = new ServerBuilder();
|
691 |
|
692 | serverBuilder
|
693 | .port('8000') // portNumber = '8000'
|
694 | .port(null) // portNumber = 8000
|
695 | .port(3000); // portNumber = 3000
|
696 |
|
697 | // TypeScript error
|
698 | serverBuilder.portNumber = null;
|
699 | ```
|
700 | </details>
|
701 |
|
702 | - [`Parameters<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#parameterstype) - Obtain the parameters of a function type in a tuple.
|
703 | <details>
|
704 | <summary>
|
705 | Example
|
706 | </summary>
|
707 |
|
708 | [Playground](https://typescript-play.js.org/?target=6#code/GYVwdgxgLglg9mABAZwBYmMANgUwBQxgAOIUAXIgIZgCeA2gLoCUFAbnDACaIDeAUIkQB6IYgCypSlBxUATrMo1ECsJzgBbLEoipqAc0J7EMKMgDkiHLnU4wp46pwAPHMgB0fAL58+oSLARECEosLAA5ABUYG2QAHgAxJGdpVWREPDdMylk9ZApqemZEAF4APipacrw-CApEgBogkKwAYThwckQwEHUAIxxZJl4BYVEImiIZKF0oZRwiWVdbeygJmThgOYgcGFYcbhqApCJsyhtpWXcR1cnEePBoeDAABVPzgbTixFeFd8uEsClADcIxGiygIFkSEOT3SmTc2VydQeRx+ZxwF2QQ34gkEwDgsnSuFmMBKiAADEDjIhYk1Qm0OlSYABqZnYka4xA1DJZHJYkGc7yCbyeRA+CAIZCzNAYbA4CIAdxg2zJwVCkWirjwMswuEaACYmCCgA)
|
709 |
|
710 | ```ts
|
711 | function shuffle(input: any[]): void {
|
712 | // Mutate array randomly changing its' elements indexes.
|
713 | }
|
714 |
|
715 | function callNTimes<Fn extends (...arguments_: any[]) => any> (func: Fn, callCount: number) {
|
716 | // Type that represents the type of the received function parameters.
|
717 | type FunctionParameters = Parameters<Fn>;
|
718 |
|
719 | return function (...arguments_: FunctionParameters) {
|
720 | for (let i = 0; i < callCount; i++) {
|
721 | func(...arguments_);
|
722 | }
|
723 | }
|
724 | }
|
725 |
|
726 | const shuffleTwice = callNTimes(shuffle, 2);
|
727 | ```
|
728 | </details>
|
729 |
|
730 | - [`ConstructorParameters<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#constructorparameterstype) - Obtain the parameters of a constructor function type in a tuple.
|
731 | <details>
|
732 | <summary>
|
733 | Example
|
734 | </summary>
|
735 |
|
736 | [Playground](https://typescript-play.js.org/?target=6#code/MYGwhgzhAECCBOAXAlqApgWQPYBM0mgG8AoaaFRENALmgkXmQDsBzAblOmCycTV4D8teo1YdO3JiICuwRFngAKClWENmLAJRFOZRAAtkEAHQq00ALzlklNBzIBfYk+KhIMAJJTEYJsDQAwmDA+mgAPAAq0GgAHnxMODCKTGgA7tCKxllg8CwQtL4AngDaALraFgB80EWa1SRkAA6MAG5gfNAB4FABPDJyCrQR9tDNyG0dwMGhtBhgjWEiGgA00F70vv4RhY3hEZXVVinpc42KmuJkkv3y8Bly8EPaDWTkhiZd7r3e8LK3llwGCMXGQWGhEOsfH5zJlsrl8p0+gw-goAAo5MAAW3BaHgEEilU0tEhmzQ212BJ0ry4SOg+kg+gBBiMximIGA0nAfAQLGk2N4EAAEgzYcYcnkLsRdDTvNEYkYUKwSdCme9WdM0MYwYhFPSIPpJdTkAAzDKxBUaZX+aAAQgsVmkCTQxuYaBw2ng4Ok8CYcotSu8pMur09iG9vuObxZnx6SN+AyUWTF8MN0CcZE4Ywm5jZHK5aB5fP4iCFIqT4oRRTKRLo6lYVNeAHpG50wOzOe1zHr9NLQ+HoABybsD4HOKXXRA1JCoKhBELmI5pNaB6Fz0KKBAodDYPAgSUTmqYsAALx4m5nC6nW9nGq14KtaEUA9gR9PvuNCjQ9BgACNvcwNBtAcLiAA)
|
737 |
|
738 | ```ts
|
739 | class ArticleModel {
|
740 | title: string;
|
741 | content?: string;
|
742 |
|
743 | constructor(title: string) {
|
744 | this.title = title;
|
745 | }
|
746 | }
|
747 |
|
748 | class InstanceCache<T extends (new (...arguments_: any[]) => any)> {
|
749 | private ClassConstructor: T;
|
750 | private cache: Map<string, InstanceType<T>> = new Map();
|
751 |
|
752 | constructor (ctr: T) {
|
753 | this.ClassConstructor = ctr;
|
754 | }
|
755 |
|
756 | getInstance (...arguments_: ConstructorParameters<T>): InstanceType<T> {
|
757 | const hash = this.calculateArgumentsHash(...arguments_);
|
758 |
|
759 | const existingInstance = this.cache.get(hash);
|
760 | if (existingInstance !== undefined) {
|
761 | return existingInstance;
|
762 | }
|
763 |
|
764 | return new this.ClassConstructor(...arguments_);
|
765 | }
|
766 |
|
767 | private calculateArgumentsHash(...arguments_: any[]): string {
|
768 | // Calculate hash.
|
769 | return 'hash';
|
770 | }
|
771 | }
|
772 |
|
773 | const articleCache = new InstanceCache(ArticleModel);
|
774 | const amazonArticle = articleCache.getInstance('Amazon forests burning!');
|
775 | ```
|
776 | </details>
|
777 |
|
778 | - [`ReturnType<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#returntypetype) - Obtain the return type of a function type.
|
779 | <details>
|
780 | <summary>
|
781 | Example
|
782 | </summary>
|
783 |
|
784 | [Playground](https://typescript-play.js.org/?target=6#code/MYGwhgzhAECSAmICmBlJAnAbgS2E6A3gFDTTwD2AcuQC4AW2AdgOYAUAlAFzSbnbyEAvkWFFQkGJSQB3GMVI1sNZNwg10TZgG4S0YOUY0kh1es07d+xmvQBXYDXLpWi5UlMaWAGj0GjJ6BtNdkJdBQYIADpXZGgAXmgYpB1ScOwoq38aeN9DYxoU6GFRKzVoJjUwRjwAYXJbPPRuAFkwAAcAHgAxBodsAx9GWwBbACMMAD4cxhloVraOCyYjdAAzMDxoOut1e0d0UNIZ6WhWSPOwdGYIbiqATwBtAF0uaHudUQB6ACpv6ABpJBINqJdAbADW0Do5BOw3u5R2VTwMHIq2gAANtjZ0bkbHsnFCwJh8ONjHp0EgwEZ4JFoN9PkRVr1FAZoMwkDRYIjqkgOrosepoEgAB7+eAwAV2BxOLy6ACCVxgIrFEoMeOl6AACpcwMMORgIB1JRMiBNWKVdhruJKfOdIpdrtwFddXlzKjyACp3Nq842HaDIbL6BrZBIVGhIpB1EMYSLsmjmtWW-YhAA+qegAAYLKQLQj3ZsEsdccmnGcLor2Dn8xGedHGpEIBzEzspfsfMHDNAANTQACMVaIljV5GQkRA5DYmIpVKQAgAJARO9le33BDXIyi0YuLW2nJFGLqkOvxFB0YPdBSaLZ0IwNzyPkO8-xkGgsLh8Al427a3hWAhXwwHA8EHT5PmgAB1bAQBAANJ24adKWpft72RaBUTgRBUCAj89HAM8xCTaBjggABRQx0DuHJv25P9dCkWRZVIAAiBjoFImpmjlFBgA0NpsjadByDacgIDAEAIAAQmYpjoGYgAZSBsmGPw6DtZiiFA8CoJguDmAQmoZ2QvtUKQLdoAYmBTwgdEiCAA)
|
785 |
|
786 | ```ts
|
787 | /** Provides every element of the iterable `iter` into the `callback` function and stores the results in an array. */
|
788 | function mapIter<
|
789 | Elem,
|
790 | Func extends (elem: Elem) => any,
|
791 | Ret extends ReturnType<Func>
|
792 | >(iter: Iterable<Elem>, callback: Func): Ret[] {
|
793 | const mapped: Ret[] = [];
|
794 |
|
795 | for (const elem of iter) {
|
796 | mapped.push(callback(elem));
|
797 | }
|
798 |
|
799 | return mapped;
|
800 | }
|
801 |
|
802 | const setObject: Set<string> = new Set();
|
803 | const mapObject: Map<number, string> = new Map();
|
804 |
|
805 | mapIter(setObject, (value: string) => value.indexOf('Foo')); // number[]
|
806 |
|
807 | mapIter(mapObject, ([key, value]: [number, string]) => {
|
808 | return key % 2 === 0 ? value : 'Odd';
|
809 | }); // string[]
|
810 | ```
|
811 | </details>
|
812 |
|
813 | - [`InstanceType<T>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#instancetypetype) - Obtain the instance type of a constructor function type.
|
814 | <details>
|
815 | <summary>
|
816 | Example
|
817 | </summary>
|
818 |
|
819 | [Playground](https://typescript-play.js.org/?target=6#code/MYGwhgzhAECSAmICmBlJAnAbgS2E6A3gFDTTwD2AcuQC4AW2AdgOYAUAlAFzSbnbyEAvkWFFQkGJSQB3GMVI1sNZNwg10TZgG4S0YOUY0kh1es07d+xmvQBXYDXLpWi5UlMaWAGj0GjJ6BtNdkJdBQYIADpXZGgAXmgYpB1ScOwoq38aeN9DYxoU6GFRKzVoJjUwRjwAYXJbPPRuAFkwAAcAHgAxBodsAx9GWwBbACMMAD4cxhloVraOCyYjdAAzMDxoOut1e0d0UNIZ6WhWSPOwdGYIbiqATwBtAF0uaHudUQB6ACpv6ABpJBINqJdAbADW0Do5BOw3u5R2VTwMHIq2gAANtjZ0bkbHsnFCwJh8ONjHp0EgwEZ4JFoN9PkRVr1FAZoMwkDRYIjqkgOrosepoEgAB7+eAwAV2BxOLy6ACCVxgIrFEoMeOl6AACpcwMMORgIB1JRMiBNWKVdhruJKfOdIpdrtwFddXlzKjyACp3Nq842HaDIbL6BrZBIVGhIpB1EMYSLsmjmtWW-YhAA+qegAAYLKQLQj3ZsEsdccmnGcLor2Dn8xGedHGpEIBzEzspfsfMHDNAANTQACMVaIljV5GQkRA5DYmIpVKQAgAJARO9le33BDXIyi0YuLW2nJFGLqkOvxFB0YPdBSaLZ0IwNzyPkO8-xkGgsLh8Al427a3hWAhXwwHA8EHT5PmgAB1bAQBAANJ24adKWpft72RaBUTgRBUCAj89HAM8xCTaBjggABRQx0DuHJv25P9dCkWRZVIAAiBjoFImpmjlFBgA0NpsjadByDacgIDAEAIAAQmYpjoGYgAZSBsmGPw6DtZiiFA8CoJguDmAQmoZ2QvtUKQLdoAYmBTwgdEiCAA)
|
820 |
|
821 | ```ts
|
822 | class IdleService {
|
823 | doNothing (): void {}
|
824 | }
|
825 |
|
826 | class News {
|
827 | title: string;
|
828 | content: string;
|
829 |
|
830 | constructor(title: string, content: string) {
|
831 | this.title = title;
|
832 | this.content = content;
|
833 | }
|
834 | }
|
835 |
|
836 | const instanceCounter: Map<Function, number> = new Map();
|
837 |
|
838 | interface Constructor {
|
839 | new(...arguments_: any[]): any;
|
840 | }
|
841 |
|
842 | // Keep track how many instances of `Constr` constructor have been created.
|
843 | function getInstance<
|
844 | Constr extends Constructor,
|
845 | Arguments extends ConstructorParameters<Constr>
|
846 | >(constructor: Constr, ...arguments_: Arguments): InstanceType<Constr> {
|
847 | let count = instanceCounter.get(constructor) || 0;
|
848 |
|
849 | const instance = new constructor(...arguments_);
|
850 |
|
851 | instanceCounter.set(constructor, count + 1);
|
852 |
|
853 | console.log(`Created ${count + 1} instances of ${Constr.name} class`);
|
854 |
|
855 | return instance;
|
856 | }
|
857 |
|
858 |
|
859 | const idleService = getInstance(IdleService);
|
860 | // Will log: `Created 1 instances of IdleService class`
|
861 | const newsEntry = getInstance(News, 'New ECMAScript proposals!', 'Last month...');
|
862 | // Will log: `Created 1 instances of News class`
|
863 | ```
|
864 | </details>
|
865 |
|
866 | - [`Omit<T, K>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#omittype-keys) - Constructs a type by picking all properties from T and then removing K.
|
867 | <details>
|
868 | <summary>
|
869 | Example
|
870 | </summary>
|
871 |
|
872 | [Playground](https://typescript-play.js.org/?target=6#code/JYOwLgpgTgZghgYwgAgIImAWzgG2QbwChlks4BzCAVShwC5kBnMKUcgbmKYAcIFgIjBs1YgOXMpSFMWbANoBdTiW5woFddwAW0kfKWEAvoUIB6U8gDCUCHEiNkICAHdkYAJ69kz4GC3JcPG4oAHteKDABBxCYNAxsPFBIWEQUCAAPJG4wZABySUFcgJAAEzMLXNV1ck0dIuCw6EjBADpy5AB1FAQ4EGQAV0YUP2AHDy8wEOQbUugmBLwtEIA3OcmQnEjuZBgQqE7gAGtgZAhwKHdkHFGwNvGUdDIcAGUliIBJEF3kAF5kAHlML4ADyPBIAGjyBUYRQAPnkqho4NoYQA+TiEGD9EAISIhPozErQMG4AASK2gn2+AApek9pCSXm8wFSQooAJQMUkAFQAsgAZACiOAgmDOOSIJAQ+OYyGl4DgoDmf2QJRCCH6YvALQQNjsEGFovF1NyJWAy1y7OUyHMyE+yRAuFImG4Iq1YDswHxbRINjA-SgfXlHqVUE4xiAA)
|
873 |
|
874 | ```ts
|
875 | interface Animal {
|
876 | imageUrl: string;
|
877 | species: string;
|
878 | images: string[];
|
879 | paragraphs: string[];
|
880 | }
|
881 |
|
882 | // Creates new type with all properties of the `Animal` interface
|
883 | // except 'images' and 'paragraphs' properties. We can use this
|
884 | // type to render small hover tooltip for a wiki entry list.
|
885 | type AnimalShortInfo = Omit<Animal, 'images' | 'paragraphs'>;
|
886 |
|
887 | function renderAnimalHoverInfo (animals: AnimalShortInfo[]): HTMLElement {
|
888 | const container = document.createElement('div');
|
889 | // Internal implementation.
|
890 | return container;
|
891 | }
|
892 | ```
|
893 | </details>
|
894 |
|
895 | - [`Uppercase<S extends string>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#uppercasestringtype) - Transforms every character in a string into uppercase.
|
896 | <details>
|
897 | <summary>
|
898 | Example
|
899 | </summary>
|
900 |
|
901 | ```ts
|
902 | type T = Uppercase<'hello'>; // 'HELLO'
|
903 |
|
904 | type T2 = Uppercase<'foo' | 'bar'>; // 'FOO' | 'BAR'
|
905 |
|
906 | type T3<S extends string> = Uppercase<`aB${S}`>;
|
907 | type T4 = T3<'xYz'>; // 'ABXYZ'
|
908 |
|
909 | type T5 = Uppercase<string>; // string
|
910 | type T6 = Uppercase<any>; // any
|
911 | type T7 = Uppercase<never>; // never
|
912 | type T8 = Uppercase<42>; // Error, type 'number' does not satisfy the constraint 'string'
|
913 | ```
|
914 | </details>
|
915 |
|
916 | - [`Lowercase<S extends string>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#lowercasestringtype) - Transforms every character in a string into lowercase.
|
917 | <details>
|
918 | <summary>
|
919 | Example
|
920 | </summary>
|
921 |
|
922 | ```ts
|
923 | type T = Lowercase<'HELLO'>; // 'hello'
|
924 |
|
925 | type T2 = Lowercase<'FOO' | 'BAR'>; // 'foo' | 'bar'
|
926 |
|
927 | type T3<S extends string> = Lowercase<`aB${S}`>;
|
928 | type T4 = T3<'xYz'>; // 'abxyz'
|
929 |
|
930 | type T5 = Lowercase<string>; // string
|
931 | type T6 = Lowercase<any>; // any
|
932 | type T7 = Lowercase<never>; // never
|
933 | type T8 = Lowercase<42>; // Error, type 'number' does not satisfy the constraint 'string'
|
934 | ```
|
935 | </details>
|
936 |
|
937 | - [`Capitalize<S extends string>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#capitalizestringtype) - Transforms the first character in a string into uppercase.
|
938 | <details>
|
939 | <summary>
|
940 | Example
|
941 | </summary>
|
942 |
|
943 | ```ts
|
944 | type T = Capitalize<'hello'>; // 'Hello'
|
945 |
|
946 | type T2 = Capitalize<'foo' | 'bar'>; // 'Foo' | 'Bar'
|
947 |
|
948 | type T3<S extends string> = Capitalize<`aB${S}`>;
|
949 | type T4 = T3<'xYz'>; // 'ABxYz'
|
950 |
|
951 | type T5 = Capitalize<string>; // string
|
952 | type T6 = Capitalize<any>; // any
|
953 | type T7 = Capitalize<never>; // never
|
954 | type T8 = Capitalize<42>; // Error, type 'number' does not satisfy the constraint 'string'
|
955 | ```
|
956 | </details>
|
957 |
|
958 | - [`Uncapitalize<S extends string>`](https://www.typescriptlang.org/docs/handbook/utility-types.html#uncapitalizestringtype) - Transforms the first character in a string into lowercase.
|
959 | <details>
|
960 | <summary>
|
961 | Example
|
962 | </summary>
|
963 |
|
964 | ```ts
|
965 | type T = Uncapitalize<'Hello'>; // 'hello'
|
966 |
|
967 | type T2 = Uncapitalize<'Foo' | 'Bar'>; // 'foo' | 'bar'
|
968 |
|
969 | type T3<S extends string> = Uncapitalize<`AB${S}`>;
|
970 | type T4 = T3<'xYz'>; // 'aBxYz'
|
971 |
|
972 | type T5 = Uncapitalize<string>; // string
|
973 | type T6 = Uncapitalize<any>; // any
|
974 | type T7 = Uncapitalize<never>; // never
|
975 | type T8 = Uncapitalize<42>; // Error, type 'number' does not satisfy the constraint 'string'
|
976 | ```
|
977 | </details>
|
978 |
|
979 | You can find some examples in the [TypeScript docs](https://www.typescriptlang.org/docs/handbook/utility-types.html).
|
980 |
|
981 | ## Maintainers
|
982 |
|
983 | - [Sindre Sorhus](https://github.com/sindresorhus)
|
984 | - [Haozheng Li](https://github.com/Emiyaaaaa)
|
985 | - [Jarek Radosz](https://github.com/CvX)
|
986 | - [Dimitri Benin](https://github.com/BendingBender)
|
987 | - [Pelle Wessman](https://github.com/voxpelli)
|
988 | - [Sébastien Mischler](https://github.com/skarab42)
|
989 |
|
990 | ## License
|
991 |
|
992 | SPDX-License-Identifier: (MIT OR CC0-1.0)
|