type-fest 4.40.1 → 5.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (156) hide show
  1. package/index.d.ts +174 -152
  2. package/package.json +20 -44
  3. package/readme.md +46 -68
  4. package/source/all-extend.d.ts +115 -0
  5. package/source/all-union-fields.d.ts +12 -12
  6. package/source/and.d.ts +60 -8
  7. package/source/array-slice.d.ts +11 -11
  8. package/source/array-splice.d.ts +4 -4
  9. package/source/array-tail.d.ts +40 -48
  10. package/source/arrayable.d.ts +2 -2
  11. package/source/asyncify.d.ts +1 -1
  12. package/source/basic.d.ts +1 -33
  13. package/source/camel-case.d.ts +6 -6
  14. package/source/camel-cased-properties-deep.d.ts +7 -7
  15. package/source/camel-cased-properties.d.ts +4 -4
  16. package/source/characters.d.ts +60 -0
  17. package/source/conditional-except.d.ts +4 -4
  18. package/source/conditional-keys.d.ts +33 -19
  19. package/source/conditional-pick-deep.d.ts +9 -9
  20. package/source/conditional-pick.d.ts +3 -3
  21. package/source/conditional-simplify-deep.d.ts +71 -0
  22. package/source/conditional-simplify.d.ts +36 -20
  23. package/source/delimiter-case.d.ts +9 -12
  24. package/source/delimiter-cased-properties-deep.d.ts +4 -4
  25. package/source/delimiter-cased-properties.d.ts +3 -3
  26. package/source/distributed-omit.d.ts +1 -1
  27. package/source/distributed-pick.d.ts +1 -1
  28. package/source/enforce-optional.d.ts +1 -1
  29. package/source/entries.d.ts +1 -1
  30. package/source/exact.d.ts +6 -6
  31. package/source/except.d.ts +2 -2
  32. package/source/exclude-strict.d.ts +45 -0
  33. package/source/extends-strict.d.ts +42 -0
  34. package/source/extract-strict.d.ts +45 -0
  35. package/source/find-global-type.d.ts +1 -1
  36. package/source/fixed-length-array.d.ts +2 -2
  37. package/source/get.d.ts +15 -14
  38. package/source/globals/index.d.ts +1 -0
  39. package/source/{observable-like.d.ts → globals/observable-like.d.ts} +10 -0
  40. package/source/greater-than-or-equal.d.ts +1 -1
  41. package/source/greater-than.d.ts +37 -32
  42. package/source/has-optional-keys.d.ts +1 -1
  43. package/source/has-readonly-keys.d.ts +1 -1
  44. package/source/has-required-keys.d.ts +1 -1
  45. package/source/has-writable-keys.d.ts +1 -1
  46. package/source/if-any.d.ts +3 -1
  47. package/source/if-empty-object.d.ts +3 -1
  48. package/source/if-never.d.ts +3 -1
  49. package/source/if-null.d.ts +3 -1
  50. package/source/if-unknown.d.ts +3 -1
  51. package/source/if.d.ts +65 -0
  52. package/source/includes.d.ts +1 -1
  53. package/source/int-closed-range.d.ts +2 -2
  54. package/source/int-range.d.ts +6 -4
  55. package/source/internal/array.d.ts +54 -22
  56. package/source/internal/characters.d.ts +0 -4
  57. package/source/internal/index.d.ts +8 -8
  58. package/source/internal/keys.d.ts +24 -23
  59. package/source/internal/numeric.d.ts +45 -15
  60. package/source/internal/object.d.ts +58 -29
  61. package/source/internal/string.d.ts +4 -14
  62. package/source/internal/tuple.d.ts +4 -4
  63. package/source/internal/type.d.ts +42 -25
  64. package/source/is-any.d.ts +0 -4
  65. package/source/is-float.d.ts +1 -3
  66. package/source/is-integer.d.ts +4 -4
  67. package/source/is-literal.d.ts +44 -28
  68. package/source/is-lowercase.d.ts +36 -0
  69. package/source/is-nullable.d.ts +28 -0
  70. package/source/is-optional-key-of.d.ts +49 -0
  71. package/source/is-optional.d.ts +26 -0
  72. package/source/is-readonly-key-of.d.ts +53 -0
  73. package/source/is-required-key-of.d.ts +49 -0
  74. package/source/is-tuple.d.ts +15 -14
  75. package/source/is-undefined.d.ts +20 -0
  76. package/source/is-union.d.ts +37 -0
  77. package/source/is-unknown.d.ts +1 -1
  78. package/source/is-uppercase.d.ts +36 -0
  79. package/source/is-writable-key-of.d.ts +49 -0
  80. package/source/json-value.d.ts +31 -0
  81. package/source/jsonifiable.d.ts +1 -1
  82. package/source/jsonify.d.ts +18 -14
  83. package/source/kebab-case.d.ts +3 -3
  84. package/source/kebab-cased-properties-deep.d.ts +4 -4
  85. package/source/kebab-cased-properties.d.ts +4 -4
  86. package/source/{string-key-of.d.ts → key-as-string.d.ts} +5 -5
  87. package/source/keys-of-union.d.ts +1 -1
  88. package/source/less-than-or-equal.d.ts +1 -1
  89. package/source/less-than.d.ts +6 -2
  90. package/source/literal-to-primitive-deep.d.ts +2 -2
  91. package/source/literal-union.d.ts +1 -1
  92. package/source/merge-deep.d.ts +43 -34
  93. package/source/merge.d.ts +5 -5
  94. package/source/multidimensional-array.d.ts +2 -2
  95. package/source/multidimensional-readonly-array.d.ts +2 -2
  96. package/source/non-empty-object.d.ts +2 -2
  97. package/source/numeric.d.ts +4 -4
  98. package/source/omit-deep.d.ts +11 -11
  99. package/source/opaque.d.ts +1 -1
  100. package/source/optional-keys-of.d.ts +10 -5
  101. package/source/or.d.ts +67 -7
  102. package/source/override-properties.d.ts +1 -1
  103. package/source/package-json.d.ts +78 -78
  104. package/source/partial-deep.d.ts +22 -21
  105. package/source/partial-on-undefined-deep.d.ts +5 -4
  106. package/source/pascal-case.d.ts +13 -6
  107. package/source/pascal-cased-properties-deep.d.ts +11 -3
  108. package/source/pascal-cased-properties.d.ts +7 -3
  109. package/source/paths.d.ts +42 -39
  110. package/source/pick-deep.d.ts +6 -6
  111. package/source/readonly-deep.d.ts +2 -2
  112. package/source/readonly-keys-of.d.ts +10 -4
  113. package/source/remove-prefix.d.ts +128 -0
  114. package/source/replace.d.ts +1 -1
  115. package/source/require-all-or-none.d.ts +12 -2
  116. package/source/require-at-least-one.d.ts +16 -2
  117. package/source/require-exactly-one.d.ts +12 -0
  118. package/source/require-one-or-none.d.ts +13 -3
  119. package/source/required-deep.d.ts +26 -32
  120. package/source/required-keys-of.d.ts +4 -4
  121. package/source/schema.d.ts +74 -74
  122. package/source/screaming-snake-case.d.ts +4 -4
  123. package/source/set-field-type.d.ts +2 -2
  124. package/source/set-non-nullable-deep.d.ts +83 -0
  125. package/source/set-optional.d.ts +11 -6
  126. package/source/set-parameter-type.d.ts +7 -7
  127. package/source/set-readonly.d.ts +12 -10
  128. package/source/set-required-deep.d.ts +12 -12
  129. package/source/set-required.d.ts +15 -9
  130. package/source/set-return-type.d.ts +1 -1
  131. package/source/shared-union-fields-deep.d.ts +10 -10
  132. package/source/shared-union-fields.d.ts +5 -4
  133. package/source/simplify-deep.d.ts +3 -3
  134. package/source/single-key-object.d.ts +4 -3
  135. package/source/snake-case.d.ts +3 -3
  136. package/source/snake-cased-properties-deep.d.ts +4 -4
  137. package/source/snake-cased-properties.d.ts +4 -4
  138. package/source/split.d.ts +9 -9
  139. package/source/spread.d.ts +3 -3
  140. package/source/string-repeat.d.ts +2 -2
  141. package/source/string-slice.d.ts +3 -3
  142. package/source/structured-cloneable.d.ts +25 -25
  143. package/source/subtract.d.ts +3 -3
  144. package/source/sum.d.ts +3 -3
  145. package/source/tagged-union.d.ts +1 -1
  146. package/source/tagged.d.ts +3 -1
  147. package/source/trim.d.ts +1 -1
  148. package/source/tsconfig-json.d.ts +2 -1
  149. package/source/tuple-to-object.d.ts +5 -4
  150. package/source/undefined-on-partial-deep.d.ts +1 -1
  151. package/source/union-to-tuple.d.ts +2 -2
  152. package/source/value-of.d.ts +1 -1
  153. package/source/words.d.ts +5 -5
  154. package/source/writable-deep.d.ts +1 -1
  155. package/source/writable-keys-of.d.ts +5 -6
  156. package/source/writable.d.ts +4 -4
@@ -1,6 +1,6 @@
1
- import type {CamelCaseOptions, DefaultCamelCaseOptions} from './camel-case';
2
- import type {ApplyDefaultOptions} from './internal';
3
- import type {PascalCase} from './pascal-case';
1
+ import type {CamelCaseOptions, DefaultCamelCaseOptions} from './camel-case.d.ts';
2
+ import type {ApplyDefaultOptions} from './internal/index.d.ts';
3
+ import type {PascalCase} from './pascal-case.d.ts';
4
4
 
5
5
  /**
6
6
  Convert object properties to pascal case but not recursively.
@@ -23,6 +23,10 @@ const result: PascalCasedProperties<User> = {
23
23
  UserId: 1,
24
24
  UserName: 'Tom',
25
25
  };
26
+
27
+ const preserveConsecutiveUppercase: PascalCasedProperties<{fooBAR: string}, {preserveConsecutiveUppercase: true}> = {
28
+ FooBAR: 'string',
29
+ };
26
30
  ```
27
31
 
28
32
  @category Change case
package/source/paths.d.ts CHANGED
@@ -1,9 +1,9 @@
1
- import type {StaticPartOfArray, VariablePartOfArray, NonRecursiveType, ToString, IsNumberLike, ApplyDefaultOptions} from './internal';
2
- import type {EmptyObject} from './empty-object';
3
- import type {IsAny} from './is-any';
4
- import type {UnknownArray} from './unknown-array';
5
- import type {Subtract} from './subtract';
6
- import type {GreaterThan} from './greater-than';
1
+ import type {StaticPartOfArray, VariablePartOfArray, NonRecursiveType, ToString, IsNumberLike, ApplyDefaultOptions} from './internal/index.d.ts';
2
+ import type {IsAny} from './is-any.d.ts';
3
+ import type {UnknownArray} from './unknown-array.d.ts';
4
+ import type {Subtract} from './subtract.d.ts';
5
+ import type {GreaterThan} from './greater-than.d.ts';
6
+ import type {IsNever} from './is-never.d.ts';
7
7
 
8
8
  /**
9
9
  Paths options.
@@ -12,9 +12,9 @@ Paths options.
12
12
  */
13
13
  export type PathsOptions = {
14
14
  /**
15
- The maximum depth to recurse when searching for paths.
15
+ The maximum depth to recurse when searching for paths. Range: 0 ~ 10.
16
16
 
17
- @default 10
17
+ @default 5
18
18
  */
19
19
  maxRecursionDepth?: number;
20
20
 
@@ -129,7 +129,7 @@ export type PathsOptions = {
129
129
  };
130
130
 
131
131
  type DefaultPathsOptions = {
132
- maxRecursionDepth: 10;
132
+ maxRecursionDepth: 5;
133
133
  bracketNotation: false;
134
134
  leavesOnly: false;
135
135
  depth: number;
@@ -186,8 +186,7 @@ type _Paths<T, Options extends Required<PathsOptions>> =
186
186
  : T extends UnknownArray
187
187
  ? number extends T['length']
188
188
  // We need to handle the fixed and non-fixed index part of the array separately.
189
- ? InternalPaths<StaticPartOfArray<T>, Options>
190
- | InternalPaths<Array<VariablePartOfArray<T>[number]>, Options>
189
+ ? InternalPaths<StaticPartOfArray<T>, Options> | InternalPaths<Array<VariablePartOfArray<T>[number]>, Options>
191
190
  : InternalPaths<T, Options>
192
191
  : T extends object
193
192
  ? InternalPaths<T, Options>
@@ -196,30 +195,34 @@ type _Paths<T, Options extends Required<PathsOptions>> =
196
195
  type InternalPaths<T, Options extends Required<PathsOptions>> =
197
196
  Options['maxRecursionDepth'] extends infer MaxDepth extends number
198
197
  ? Required<T> extends infer T
199
- ? T extends EmptyObject | readonly []
198
+ ? T extends readonly []
200
199
  ? never
201
- : {
202
- [Key in keyof T]:
203
- Key extends string | number // Limit `Key` to string or number.
204
- ? (
205
- Options['bracketNotation'] extends true
206
- ? IsNumberLike<Key> extends true
207
- ? `[${Key}]`
208
- : (Key | ToString<Key>)
209
- : never
210
- |
211
- Options['bracketNotation'] extends false
212
- // If `Key` is a number, return `Key | `${Key}``, because both `array[0]` and `array['0']` work.
213
- ? (Key | ToString<Key>)
214
- : never
215
- ) extends infer TranformedKey extends string | number ?
216
- // 1. If style is 'a[0].b' and 'Key' is a numberlike value like 3 or '3', transform 'Key' to `[${Key}]`, else to `${Key}` | Key
217
- // 2. If style is 'a.0.b', transform 'Key' to `${Key}` | Key
200
+ : IsNever<keyof T> extends true // Check for empty object
201
+ ? never
202
+ : {
203
+ [Key in keyof T]:
204
+ Key extends string | number // Limit `Key` to string or number.
205
+ ? (
206
+ Options['bracketNotation'] extends true
207
+ ? IsNumberLike<Key> extends true
208
+ ? `[${Key}]`
209
+ : (Key | ToString<Key>)
210
+ : Options['bracketNotation'] extends false
211
+ // If `Key` is a number, return `Key | `${Key}``, because both `array[0]` and `array['0']` work.
212
+ ? (Key | ToString<Key>)
213
+ : never
214
+ ) extends infer TranformedKey extends string | number ?
215
+ // 1. If style is 'a[0].b' and 'Key' is a numberlike value like 3 or '3', transform 'Key' to `[${Key}]`, else to `${Key}` | Key
216
+ // 2. If style is 'a.0.b', transform 'Key' to `${Key}` | Key
218
217
  | ((Options['leavesOnly'] extends true
219
218
  ? MaxDepth extends 0
220
219
  ? TranformedKey
221
- : T[Key] extends EmptyObject | readonly [] | NonRecursiveType | ReadonlyMap<unknown, unknown> | ReadonlySet<unknown>
222
- ? TranformedKey
220
+ : T[Key] extends infer Value
221
+ ? (Value extends readonly [] | NonRecursiveType | ReadonlyMap<unknown, unknown> | ReadonlySet<unknown>
222
+ ? TranformedKey
223
+ : IsNever<keyof Value> extends true // Check for empty object
224
+ ? TranformedKey
225
+ : never)
223
226
  : never
224
227
  : TranformedKey
225
228
  ) extends infer _TransformedKey
@@ -233,12 +236,12 @@ type InternalPaths<T, Options extends Required<PathsOptions>> =
233
236
  // Recursively generate paths for the current key
234
237
  GreaterThan<MaxDepth, 0> extends true // Limit the depth to prevent infinite recursion
235
238
  ? _Paths<T[Key],
236
- {
237
- bracketNotation: Options['bracketNotation'];
238
- maxRecursionDepth: Subtract<MaxDepth, 1>;
239
- leavesOnly: Options['leavesOnly'];
240
- depth: Subtract<Options['depth'], 1>;
241
- }> extends infer SubPath
239
+ {
240
+ bracketNotation: Options['bracketNotation'];
241
+ maxRecursionDepth: Subtract<MaxDepth, 1>;
242
+ leavesOnly: Options['leavesOnly'];
243
+ depth: Subtract<Options['depth'], 1>;
244
+ }> extends infer SubPath
242
245
  ? SubPath extends string | number
243
246
  ? (
244
247
  Options['bracketNotation'] extends true
@@ -255,8 +258,8 @@ type InternalPaths<T, Options extends Required<PathsOptions>> =
255
258
  : never
256
259
  : never
257
260
  )
261
+ : never
258
262
  : never
259
- : never
260
- }[keyof T & (T extends UnknownArray ? number : unknown)]
263
+ }[keyof T & (T extends UnknownArray ? number : unknown)]
261
264
  : never
262
265
  : never;
@@ -1,9 +1,9 @@
1
- import type {BuildObject, BuildTuple, NonRecursiveType, ObjectValue} from './internal';
2
- import type {IsNever} from './is-never';
3
- import type {Paths} from './paths';
4
- import type {Simplify} from './simplify.d';
5
- import type {UnionToIntersection} from './union-to-intersection.d';
6
- import type {UnknownArray} from './unknown-array';
1
+ import type {BuildObject, BuildTuple, NonRecursiveType, ObjectValue} from './internal/index.d.ts';
2
+ import type {IsNever} from './is-never.d.ts';
3
+ import type {Paths} from './paths.d.ts';
4
+ import type {Simplify} from './simplify.d.ts';
5
+ import type {UnionToIntersection} from './union-to-intersection.d.ts';
6
+ import type {UnknownArray} from './unknown-array.d.ts';
7
7
 
8
8
  /**
9
9
  Pick properties from a deeply-nested object.
@@ -1,4 +1,4 @@
1
- import type {BuiltIns, HasMultipleCallSignatures} from './internal';
1
+ import type {BuiltIns, HasMultipleCallSignatures} from './internal/index.d.ts';
2
2
 
3
3
  /**
4
4
  Convert `object`s, `Map`s, `Set`s, and `Array`s and all of their keys/elements into immutable structures recursively.
@@ -23,7 +23,7 @@ const data: ReadonlyDeep<typeof dataJson> = dataJson;
23
23
  export default data;
24
24
 
25
25
  // test.ts
26
- import data from './main';
26
+ import data from './main.d.ts';
27
27
 
28
28
  data.foo.push('bar');
29
29
  //=> error TS2339: Property 'push' does not exist on type 'readonly string[]'
@@ -1,4 +1,4 @@
1
- import type {WritableKeysOf} from './writable-keys-of';
1
+ import type {IsReadonlyKeyOf} from './is-readonly-key-of.d.ts';
2
2
 
3
3
  /**
4
4
  Extract all readonly keys from the given type.
@@ -12,6 +12,7 @@ import type {ReadonlyKeysOf} from 'type-fest';
12
12
  interface User {
13
13
  name: string;
14
14
  surname: string;
15
+
15
16
  readonly id: number;
16
17
  }
17
18
 
@@ -24,7 +25,12 @@ const update1: UpdateResponse<User> = {
24
25
 
25
26
  @category Utilities
26
27
  */
27
- export type ReadonlyKeysOf<T> =
28
- T extends unknown // For distributing `T`
29
- ? Exclude<keyof T, WritableKeysOf<T>>
28
+ export type ReadonlyKeysOf<Type extends object> =
29
+ Type extends unknown // For distributing `Type`
30
+ ? (keyof {[Key in keyof Type as
31
+ IsReadonlyKeyOf<Type, Key> extends false
32
+ ? never
33
+ : Key
34
+ ]: never
35
+ }) & keyof Type // Intersect with `keyof Type` to ensure result of `ReadonlyKeysOf<Type>` is always assignable to `keyof Type`
30
36
  : never; // Should never happen
@@ -0,0 +1,128 @@
1
+ import type {ApplyDefaultOptions} from './internal/object.d.ts';
2
+ import type {IfNotAnyOrNever, Not} from './internal/type.d.ts';
3
+ import type {IsStringLiteral} from './is-literal.d.ts';
4
+ import type {Or} from './or.d.ts';
5
+
6
+ /**
7
+ @see {@link RemovePrefix}
8
+ */
9
+ type RemovePrefixOptions = {
10
+ /**
11
+ When enabled, instantiations with non-literal prefixes (e.g., `string`, `Uppercase<string>`, `` `on${string}` ``) simply return `string`, since their precise structure cannot be statically determined.
12
+
13
+ Note: Disabling this option can produce misleading results that might not reflect the actual runtime behavior.
14
+ For example, ``RemovePrefix<'on-change', `${string}-`, {strict: false}>`` returns `'change'`, but at runtime, prefix could be `'handle-'` (which satisfies `` `${string}-` ``) and removing `'handle-'` from `'on-change'` would not result in `'change'`.
15
+
16
+ So, it is recommended to not disable this option unless you are aware of the implications.
17
+
18
+ @default true
19
+
20
+ @example
21
+ ```
22
+ type A = RemovePrefix<'on-change', `${string}-`, {strict: true}>;
23
+ //=> string
24
+
25
+ type B = RemovePrefix<'on-change', `${string}-`, {strict: false}>;
26
+ //=> 'change'
27
+
28
+ type C = RemovePrefix<'on-change', string, {strict: true}>;
29
+ //=> string
30
+
31
+ type D = RemovePrefix<'on-change', string, {strict: false}>;
32
+ //=> 'n-change'
33
+
34
+ type E = RemovePrefix<`${string}/${number}`, `${string}/`, {strict: true}>;
35
+ //=> string
36
+
37
+ type F = RemovePrefix<`${string}/${number}`, `${string}/`, {strict: false}>;
38
+ //=> `${number}`
39
+ ```
40
+
41
+ Note: This option has no effect when only the input string type is non-literal. For example, ``RemovePrefix<`on-${string}`, 'on-'>`` will always return `string`.
42
+
43
+ @example
44
+ ```
45
+ import type {RemovePrefix} from 'type-fest';
46
+
47
+ type A = RemovePrefix<`on-${string}`, 'on-', {strict: true}>;
48
+ //=> string
49
+
50
+ type B = RemovePrefix<`on-${string}`, 'on-', {strict: false}>;
51
+ //=> string
52
+
53
+ type C = RemovePrefix<`id-${number}`, 'id-', {strict: true}>;
54
+ //=> `${number}`
55
+
56
+ type D = RemovePrefix<`id-${number}`, 'id-', {strict: false}>;
57
+ //=> `${number}`
58
+ ```
59
+
60
+ Note: If it can be statically determined that the input string can never start with the specified non-literal prefix, then the input string is returned as-is, regardless of the value of this option.
61
+ For example, ``RemovePrefix<`${string}/${number}`, `${string}:`>`` returns `` `${string}/${number}` ``, since a string of type `` `${string}/${number}` `` can never start with a prefix of type `` `${string}:` ``.
62
+ ```
63
+ import type {RemovePrefix} from 'type-fest';
64
+
65
+ type A = RemovePrefix<`${string}/${number}`, `${string}:`, {strict: true}>;
66
+ //=> `${string}/${number}`
67
+
68
+ type B = RemovePrefix<`${string}/${number}`, `${string}:`, {strict: false}>;
69
+ //=> `${string}/${number}`
70
+
71
+ type C = RemovePrefix<'on-change', `${number}-`, {strict: true}>;
72
+ //=> 'on-change'
73
+
74
+ type D = RemovePrefix<'on-change', `${number}-`, {strict: false}>;
75
+ //=> 'on-change'
76
+ ```
77
+ */
78
+ strict?: boolean;
79
+ };
80
+
81
+ type DefaultRemovePrefixOptions = {
82
+ strict: true;
83
+ };
84
+
85
+ /**
86
+ Removes the specified prefix from the start of a string.
87
+
88
+ @example
89
+ ```
90
+ import type {RemovePrefix} from 'type-fest';
91
+
92
+ type A = RemovePrefix<'on-change', 'on-'>;
93
+ //=> 'change'
94
+
95
+ type B = RemovePrefix<'sm:flex' | 'sm:p-4' | 'sm:gap-2', 'sm:'>;
96
+ //=> 'flex' | 'p-4' | 'gap-2'
97
+
98
+ type C = RemovePrefix<'on-change', 'off-'>;
99
+ //=> 'on-change'
100
+
101
+ type D = RemovePrefix<`handle${Capitalize<string>}`, 'handle'>;
102
+ //=> Capitalize<string>
103
+ ```
104
+
105
+ @see {@link RemovePrefixOptions}
106
+
107
+ @category String
108
+ @category Template literal
109
+ */
110
+ export type RemovePrefix<S extends string, Prefix extends string, Options extends RemovePrefixOptions = {}> =
111
+ IfNotAnyOrNever<
112
+ S,
113
+ IfNotAnyOrNever<
114
+ Prefix,
115
+ _RemovePrefix<S, Prefix, ApplyDefaultOptions<RemovePrefixOptions, DefaultRemovePrefixOptions, Options>>,
116
+ string,
117
+ S
118
+ >
119
+ >;
120
+
121
+ type _RemovePrefix<S extends string, Prefix extends string, Options extends Required<RemovePrefixOptions>> =
122
+ Prefix extends string // For distributing `Prefix`
123
+ ? S extends `${Prefix}${infer Rest}`
124
+ ? Or<IsStringLiteral<Prefix>, Not<Options['strict']>> extends true
125
+ ? Rest
126
+ : string // Fallback to `string` when `Prefix` is non-literal and `strict` is disabled
127
+ : S // Return back `S` when `Prefix` is not present at the start of `S`
128
+ : never;
@@ -1,4 +1,4 @@
1
- import type {ApplyDefaultOptions} from './internal';
1
+ import type {ApplyDefaultOptions} from './internal/index.d.ts';
2
2
 
3
3
  type ReplaceOptions = {
4
4
  all?: boolean;
@@ -1,4 +1,7 @@
1
- import type {RequireNone} from './internal';
1
+ import type {If} from './if.d.ts';
2
+ import type {IfNotAnyOrNever, RequireNone} from './internal/index.d.ts';
3
+ import type {IsAny} from './is-any.d.ts';
4
+ import type {IsNever} from './is-never.d.ts';
2
5
 
3
6
  /**
4
7
  Requires all of the keys in the given object.
@@ -36,7 +39,14 @@ const responder2: RequireAllOrNone<Responder, 'text' | 'json'> = {
36
39
 
37
40
  @category Object
38
41
  */
39
- export type RequireAllOrNone<ObjectType, KeysType extends keyof ObjectType = keyof ObjectType> = (
42
+ export type RequireAllOrNone<ObjectType, KeysType extends keyof ObjectType = keyof ObjectType> =
43
+ IfNotAnyOrNever<ObjectType,
44
+ If<IsNever<KeysType>,
45
+ ObjectType,
46
+ _RequireAllOrNone<ObjectType, If<IsAny<KeysType>, keyof ObjectType, KeysType>>
47
+ >>;
48
+
49
+ type _RequireAllOrNone<ObjectType, KeysType extends keyof ObjectType> = (
40
50
  | RequireAll<ObjectType, KeysType>
41
51
  | RequireNone<KeysType>
42
52
  ) & Omit<ObjectType, KeysType>; // The rest of the keys.
@@ -1,4 +1,8 @@
1
- import type {Except} from './except';
1
+ import type {Except} from './except.d.ts';
2
+ import type {If} from './if.d.ts';
3
+ import type {IfNotAnyOrNever} from './internal/index.d.ts';
4
+ import type {IsAny} from './is-any.d.ts';
5
+ import type {IsNever} from './is-never.d.ts';
2
6
 
3
7
  /**
4
8
  Create a type that requires at least one of the given keys. The remaining keys are kept as is.
@@ -24,11 +28,21 @@ const responder: RequireAtLeastOne<Responder, 'text' | 'json'> = {
24
28
  export type RequireAtLeastOne<
25
29
  ObjectType,
26
30
  KeysType extends keyof ObjectType = keyof ObjectType,
31
+ > =
32
+ IfNotAnyOrNever<ObjectType,
33
+ If<IsNever<KeysType>,
34
+ never,
35
+ _RequireAtLeastOne<ObjectType, If<IsAny<KeysType>, keyof ObjectType, KeysType>>
36
+ >>;
37
+
38
+ type _RequireAtLeastOne<
39
+ ObjectType,
40
+ KeysType extends keyof ObjectType,
27
41
  > = {
28
42
  // For each `Key` in `KeysType` make a mapped type:
29
43
  [Key in KeysType]-?: Required<Pick<ObjectType, Key>> & // 1. Make `Key`'s type required
30
44
  // 2. Make all other keys in `KeysType` optional
31
- Partial<Pick<ObjectType, Exclude<KeysType, Key>>>;
45
+ Partial<Pick<ObjectType, Exclude<KeysType, Key>>>;
32
46
  }[KeysType] &
33
47
  // 3. Add the remaining keys not in `KeysType`
34
48
  Except<ObjectType, KeysType>;
@@ -1,3 +1,8 @@
1
+ import type {If} from './if.d.ts';
2
+ import type {IfNotAnyOrNever} from './internal/index.d.ts';
3
+ import type {IsAny} from './is-any.d.ts';
4
+ import type {IsNever} from './is-never.d.ts';
5
+
1
6
  /**
2
7
  Create a type that requires exactly one of the given keys and disallows more. The remaining keys are kept as is.
3
8
 
@@ -28,6 +33,13 @@ const responder: RequireExactlyOne<Responder, 'text' | 'json'> = {
28
33
  @category Object
29
34
  */
30
35
  export type RequireExactlyOne<ObjectType, KeysType extends keyof ObjectType = keyof ObjectType> =
36
+ IfNotAnyOrNever<ObjectType,
37
+ If<IsNever<KeysType>,
38
+ never,
39
+ _RequireExactlyOne<ObjectType, If<IsAny<KeysType>, keyof ObjectType, KeysType>>
40
+ >>;
41
+
42
+ type _RequireExactlyOne<ObjectType, KeysType extends keyof ObjectType> =
31
43
  {[Key in KeysType]: (
32
44
  Required<Pick<ObjectType, Key>> &
33
45
  Partial<Record<Exclude<KeysType, Key>, never>>
@@ -1,5 +1,8 @@
1
- import type {RequireExactlyOne} from './require-exactly-one';
2
- import type {RequireNone} from './internal';
1
+ import type {RequireExactlyOne} from './require-exactly-one.d.ts';
2
+ import type {IfNotAnyOrNever, RequireNone} from './internal/index.d.ts';
3
+ import type {If} from './if.d.ts';
4
+ import type {IsAny} from './is-any.d.ts';
5
+ import type {IsNever} from './is-never.d.ts';
3
6
 
4
7
  /**
5
8
  Create a type that requires exactly one of the given keys and disallows more, or none of the given keys. The remaining keys are kept as is.
@@ -31,7 +34,14 @@ const responder3: Responder = {
31
34
 
32
35
  @category Object
33
36
  */
34
- export type RequireOneOrNone<ObjectType, KeysType extends keyof ObjectType = keyof ObjectType> = (
37
+ export type RequireOneOrNone<ObjectType, KeysType extends keyof ObjectType = keyof ObjectType> =
38
+ IfNotAnyOrNever<ObjectType,
39
+ If<IsNever<KeysType>,
40
+ ObjectType,
41
+ _RequireOneOrNone<ObjectType, If<IsAny<KeysType>, keyof ObjectType, KeysType>>
42
+ >>;
43
+
44
+ type _RequireOneOrNone<ObjectType, KeysType extends keyof ObjectType> = (
35
45
  | RequireExactlyOne<ObjectType, KeysType>
36
46
  | RequireNone<KeysType>
37
47
  ) & Omit<ObjectType, KeysType>; // Ignore unspecified keys.
@@ -1,6 +1,4 @@
1
- import type {BuiltIns, HasMultipleCallSignatures} from './internal';
2
-
3
- type ExcludeUndefined<T> = Exclude<T, undefined>;
1
+ import type {BuiltIns, HasMultipleCallSignatures} from './internal/index.d.ts';
4
2
 
5
3
  /**
6
4
  Create a type from another type with all keys and nested keys set to required.
@@ -15,23 +13,23 @@ import type {RequiredDeep} from 'type-fest';
15
13
 
16
14
  type Settings = {
17
15
  textEditor?: {
18
- fontSize?: number | undefined;
19
- fontColor?: string | undefined;
16
+ fontSize?: number;
17
+ fontColor?: string;
20
18
  fontWeight?: number | undefined;
21
- }
22
- autocomplete?: boolean | undefined;
19
+ };
20
+ autocomplete?: boolean;
23
21
  autosave?: boolean | undefined;
24
22
  };
25
23
 
26
24
  type RequiredSettings = RequiredDeep<Settings>;
27
- // type RequiredSettings = {
25
+ //=> {
28
26
  // textEditor: {
29
27
  // fontSize: number;
30
28
  // fontColor: string;
31
- // fontWeight: number;
32
- // }
29
+ // fontWeight: number | undefined;
30
+ // };
33
31
  // autocomplete: boolean;
34
- // autosave: boolean;
32
+ // autosave: boolean | undefined;
35
33
  // }
36
34
  ```
37
35
 
@@ -43,34 +41,30 @@ Note that types containing overloaded functions are not made deeply required due
43
41
  @category Set
44
42
  @category Map
45
43
  */
46
- export type RequiredDeep<T, E extends ExcludeUndefined<T> = ExcludeUndefined<T>> = E extends BuiltIns
47
- ? E
48
- : E extends Map<infer KeyType, infer ValueType>
44
+ export type RequiredDeep<T> = T extends BuiltIns
45
+ ? T
46
+ : T extends Map<infer KeyType, infer ValueType>
49
47
  ? Map<RequiredDeep<KeyType>, RequiredDeep<ValueType>>
50
- : E extends Set<infer ItemType>
48
+ : T extends Set<infer ItemType>
51
49
  ? Set<RequiredDeep<ItemType>>
52
- : E extends ReadonlyMap<infer KeyType, infer ValueType>
50
+ : T extends ReadonlyMap<infer KeyType, infer ValueType>
53
51
  ? ReadonlyMap<RequiredDeep<KeyType>, RequiredDeep<ValueType>>
54
- : E extends ReadonlySet<infer ItemType>
52
+ : T extends ReadonlySet<infer ItemType>
55
53
  ? ReadonlySet<RequiredDeep<ItemType>>
56
- : E extends WeakMap<infer KeyType, infer ValueType>
54
+ : T extends WeakMap<infer KeyType, infer ValueType>
57
55
  ? WeakMap<RequiredDeep<KeyType>, RequiredDeep<ValueType>>
58
- : E extends WeakSet<infer ItemType>
56
+ : T extends WeakSet<infer ItemType>
59
57
  ? WeakSet<RequiredDeep<ItemType>>
60
- : E extends Promise<infer ValueType>
58
+ : T extends Promise<infer ValueType>
61
59
  ? Promise<RequiredDeep<ValueType>>
62
- : E extends (...arguments_: any[]) => unknown
63
- ? {} extends RequiredObjectDeep<E>
64
- ? E
65
- : HasMultipleCallSignatures<E> extends true
66
- ? E
67
- : ((...arguments_: Parameters<E>) => ReturnType<E>) & RequiredObjectDeep<E>
68
- : E extends object
69
- ? E extends Array<infer ItemType> // Test for arrays/tuples, per https://github.com/microsoft/TypeScript/issues/35156
70
- ? ItemType[] extends E // Test for arrays (non-tuples) specifically
71
- ? Array<RequiredDeep<ItemType>> // Recreate relevant array type to prevent eager evaluation of circular reference
72
- : RequiredObjectDeep<E> // Tuples behave properly
73
- : RequiredObjectDeep<E>
60
+ : T extends (...arguments_: any[]) => unknown
61
+ ? {} extends RequiredObjectDeep<T>
62
+ ? T
63
+ : HasMultipleCallSignatures<T> extends true
64
+ ? T
65
+ : ((...arguments_: Parameters<T>) => ReturnType<T>) & RequiredObjectDeep<T>
66
+ : T extends object
67
+ ? RequiredObjectDeep<T>
74
68
  : unknown;
75
69
 
76
70
  type RequiredObjectDeep<ObjectType extends object> = {
@@ -1,4 +1,4 @@
1
- import type {OptionalKeysOf} from './optional-keys-of';
1
+ import type {OptionalKeysOf} from './optional-keys-of.d.ts';
2
2
 
3
3
  /**
4
4
  Extract all required keys from the given type.
@@ -24,7 +24,7 @@ const validator2 = createValidation<User>('surname', value => value.length < 25)
24
24
 
25
25
  @category Utilities
26
26
  */
27
- export type RequiredKeysOf<BaseType extends object> =
28
- BaseType extends unknown // For distributing `BaseType`
29
- ? Exclude<keyof BaseType, OptionalKeysOf<BaseType>>
27
+ export type RequiredKeysOf<Type extends object> =
28
+ Type extends unknown // For distributing `Type`
29
+ ? Exclude<keyof Type, OptionalKeysOf<Type>>
30
30
  : never; // Should never happen