@luxass/utils 2.6.0 → 2.6.2

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.
package/dist/index.d.ts CHANGED
@@ -1,9 +1,9 @@
1
1
  import { isNotNull, isNotNullish, isNotUndefined, isTruthy } from "./guards-SWdmRZ5e.js";
2
2
  import { clamp } from "./number-Culbli-Y.js";
3
3
  import { getChangedKeys, getOwnProperty, hasOwnProperty, omit } from "./object-BtzfqVfB.js";
4
- import { appendTrailingSlash, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-DqJkV3NT.js";
5
- import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-Cwp8CD7H.js";
6
- import { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature } from "./types-BtiMC8Uf.js";
4
+ import { appendTrailingSlash, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-CFkUYi0a.js";
5
+ import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-BgrFQWVx.js";
6
+ import { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature, SafeOmit } from "./types-DwW0ucVr.js";
7
7
  import pRetry from "p-retry";
8
8
 
9
9
  //#region src/common.d.ts
@@ -22,4 +22,4 @@ declare class InvariantError extends Error {
22
22
  */
23
23
  declare function invariant(predicate: unknown, message: string, ...positionals: unknown[]): asserts predicate;
24
24
  //#endregion
25
- export { ElementOf, InferArguments, InvariantError, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature, appendTrailingSlash, capitalize, clamp, dedent, dedentRaw, formatStr, getChangedKeys, getOwnProperty, hasOwnProperty, invariant, isNotNull, isNotNullish, isNotUndefined, isTruthy, omit, prependLeadingSlash, pRetry as promiseRetry, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase, trimLeadingSlash, trimTrailingSlash };
25
+ export { type ElementOf, type InferArguments, InvariantError, type MaybeArray, type MaybePromise, type Nullable, type Nullish, type Prettify, type RemoveIndexSignature, type SafeOmit, appendTrailingSlash, capitalize, clamp, dedent, dedentRaw, formatStr, getChangedKeys, getOwnProperty, hasOwnProperty, invariant, isNotNull, isNotNullish, isNotUndefined, isTruthy, omit, prependLeadingSlash, pRetry as promiseRetry, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase, trimLeadingSlash, trimTrailingSlash };
package/dist/index.js CHANGED
@@ -1,8 +1,8 @@
1
1
  import { isNotNull, isNotNullish, isNotUndefined, isTruthy } from "./guards-O1HGJraI.js";
2
- import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-pQApOGKP.js";
2
+ import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-BlwTLoKD.js";
3
3
  import { clamp } from "./number-BS9T5WGO.js";
4
4
  import { getChangedKeys, getOwnProperty, hasOwnProperty, omit } from "./object-CyGLe77G.js";
5
- import { appendTrailingSlash, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-BS-_BQ_d.js";
5
+ import { appendTrailingSlash, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-BcSxT2uo.js";
6
6
  import pRetry from "p-retry";
7
7
 
8
8
  //#region src/common.ts
@@ -74,9 +74,9 @@ function prependLeadingSlash(path) {
74
74
  return path[0] === "/" ? path : `/${path}`;
75
75
  }
76
76
  /**
77
- * Joins two URL paths together, handling trailing and leading slashes appropriately
78
- * @param {string | undefined} base - The base URL path
79
- * @param {string | undefined} path - The path to append to the base
77
+ * Joins URL paths together, handling trailing and leading slashes appropriately
78
+ * @param {string} base - The base URL path
79
+ * @param {...string} segments - Additional URL segments to join
80
80
  * @returns {string} The joined URL path
81
81
  *
82
82
  * @example
@@ -93,35 +93,38 @@ function prependLeadingSlash(path) {
93
93
  * joinURL("https://api.example.com", "v1/users") // "https://api.example.com/v1/users"
94
94
  * joinURL("https://api.example.com/", "/v1/users") // "https://api.example.com/v1/users"
95
95
  *
96
- * // Multiple slash normalization (POSIX-like)
96
+ * // Multiple slash normalization
97
97
  * joinURL("api//v1/", "//users///") // "api/v1/users/"
98
98
  * joinURL("base///", "///path") // "base/path"
99
99
  *
100
+ * // Root path handling
101
+ * joinURL("/", "users") // "/users"
102
+ * joinURL("api", "/") // "api/"
103
+ *
100
104
  * // Empty and undefined handling
101
105
  * joinURL("", "users") // "users"
102
106
  * joinURL("api", "") // "api"
103
- * joinURL(undefined, undefined) // "/"
107
+ * joinURL("", "") // "/"
104
108
  * ```
105
109
  */
106
- function joinURL(base, path) {
107
- if (!base && !path) return "/";
108
- if (!base || base === "/") return path || "/";
109
- if (!path || path === "/") return base;
110
- const normalize = (s) => s.replace(/\/+/g, "/");
111
- const joinPaths = (b, p) => {
112
- b = normalize(b);
113
- p = normalize(p);
114
- if (b.endsWith("/") && b !== "/") b = b.slice(0, -1);
115
- if (p.startsWith("/")) p = p.slice(1);
116
- return p ? `${b}/${p}` : b;
110
+ function joinURL(base, ...segments) {
111
+ if (!base && !segments) return "/";
112
+ if (!segments || segments.length === 0) return base || "/";
113
+ const normalize = (s) => {
114
+ return s.replace(/([^:])\/+/g, "$1/").replace(/^\/+/, "/");
117
115
  };
118
- try {
119
- const url = new URL(base);
120
- url.pathname = trimLeadingSlash(joinPaths(url.pathname, path));
121
- return url.toString();
122
- } catch {
123
- return joinPaths(base, path);
116
+ let path = base;
117
+ for (const seg of segments) {
118
+ if (!seg || seg === ".") continue;
119
+ if (path.length > 0) {
120
+ const pathTrailing = path[path.length - 1] === "/";
121
+ const segLeading = seg[0] === "/";
122
+ const both = pathTrailing && segLeading;
123
+ if (both) path += seg.slice(1);
124
+ else path += pathTrailing || segLeading ? seg : `/${seg}`;
125
+ } else path += seg;
124
126
  }
127
+ return normalize(path) || "/";
125
128
  }
126
129
 
127
130
  //#endregion
@@ -62,9 +62,9 @@ declare function appendTrailingSlash(path: string | undefined): string;
62
62
  */
63
63
  declare function prependLeadingSlash(path: string | undefined): string;
64
64
  /**
65
- * Joins two URL paths together, handling trailing and leading slashes appropriately
66
- * @param {string | undefined} base - The base URL path
67
- * @param {string | undefined} path - The path to append to the base
65
+ * Joins URL paths together, handling trailing and leading slashes appropriately
66
+ * @param {string} base - The base URL path
67
+ * @param {...string} segments - Additional URL segments to join
68
68
  * @returns {string} The joined URL path
69
69
  *
70
70
  * @example
@@ -81,16 +81,20 @@ declare function prependLeadingSlash(path: string | undefined): string;
81
81
  * joinURL("https://api.example.com", "v1/users") // "https://api.example.com/v1/users"
82
82
  * joinURL("https://api.example.com/", "/v1/users") // "https://api.example.com/v1/users"
83
83
  *
84
- * // Multiple slash normalization (POSIX-like)
84
+ * // Multiple slash normalization
85
85
  * joinURL("api//v1/", "//users///") // "api/v1/users/"
86
86
  * joinURL("base///", "///path") // "base/path"
87
87
  *
88
+ * // Root path handling
89
+ * joinURL("/", "users") // "/users"
90
+ * joinURL("api", "/") // "api/"
91
+ *
88
92
  * // Empty and undefined handling
89
93
  * joinURL("", "users") // "users"
90
94
  * joinURL("api", "") // "api"
91
- * joinURL(undefined, undefined) // "/"
95
+ * joinURL("", "") // "/"
92
96
  * ```
93
97
  */
94
- declare function joinURL(base: string | undefined, path: string | undefined): string;
98
+ declare function joinURL(base: string, ...segments: string[]): string;
95
99
  //#endregion
96
100
  export { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash };
package/dist/path.d.ts CHANGED
@@ -1,2 +1,2 @@
1
- import { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-DqJkV3NT.js";
1
+ import { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-CFkUYi0a.js";
2
2
  export { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash };
package/dist/path.js CHANGED
@@ -1,3 +1,3 @@
1
- import { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-BS-_BQ_d.js";
1
+ import { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash } from "./path-BcSxT2uo.js";
2
2
 
3
3
  export { appendTrailingSlash, joinURL, prependLeadingSlash, trimLeadingSlash, trimTrailingSlash };
@@ -68,35 +68,71 @@ declare function toPascalCase(str: string): string;
68
68
  */
69
69
  declare function toSnakeCase(str: string): string;
70
70
  /**
71
- * Removes leading and trailing whitespace from each line of a string
72
- * @param {TemplateStringsArray | string} literals - The string to dedent
71
+ * @overload
72
+ * @param {string} literals - The string to dedent
73
73
  * @returns {string} The dedented string
74
+ *
74
75
  * @example ```ts
75
- * dedent`
76
- * This is a test.
76
+ * import { dedent } from "@luxass/utils/string";
77
+ * const text = dedent(` * This is a test.
77
78
  * This is another line.
78
- * `
79
+ * `);
79
80
  * // "This is a test.\nThis is another line."
80
81
  * ```
81
82
  */
82
83
  declare function dedent(literals: string): string;
84
+ /**
85
+ * @overload
86
+ * @param {TemplateStringsArray} strings - The string to dedent
87
+ * @param {unknown[]} values - The values to insert into the string
88
+ * @returns {string} The dedented string
89
+ *
90
+ * @example
91
+ * ```ts
92
+ * import { dedent } from "@luxass/utils/string";
93
+ * const text = dedent`
94
+ * This is a test.
95
+ * This is another line.
96
+ * `;
97
+ * // "This is a test.\nThis is another line."
98
+ * ```
99
+ */
83
100
  declare function dedent(strings: TemplateStringsArray, ...values: unknown[]): string;
84
101
  declare namespace dedent {
85
102
  var raw: typeof dedentRaw;
86
103
  }
87
104
  /**
88
- * Removes leading and trailing whitespace from each line of a string
89
- * @param {TemplateStringsArray | string} literals - The string to dedent
105
+ * @overload
106
+ * @param {string} literals - The string to dedent
90
107
  * @returns {string} The dedented string
91
- * @example ```ts
92
- * dedent`
93
- * This is a test.
94
- * This is another line.
95
- * `
108
+ *
109
+ * @example
110
+ * ```ts
111
+ * import { dedentRaw } from "@luxass/utils/string";
112
+ * const text = dedentRaw(`
113
+ * This is a test.
114
+ * This is another line.
115
+ * `);
96
116
  * // "This is a test.\nThis is another line."
97
117
  * ```
98
118
  */
99
119
  declare function dedentRaw(literals: string): string;
120
+ /**
121
+ * @overload
122
+ * @param {TemplateStringsArray} strings - The string to dedent
123
+ * @param {unknown[]} values - The values to insert into the string
124
+ * @return {string} The dedented string
125
+ *
126
+ * @example
127
+ * ```ts
128
+ * import { dedentRaw } from "@luxass/utils/string";
129
+ * const text = dedentRaw`
130
+ * This is a test.
131
+ * This is another line.
132
+ * `
133
+ * // "This is a test.\nThis is another line."
134
+ * ```
135
+ */
100
136
  declare function dedentRaw(strings: TemplateStringsArray, ...values: unknown[]): string;
101
137
  /**
102
138
  * Ensures a string is a valid JavaScript identifier by prefixing with an underscore if necessary
@@ -93,10 +93,52 @@ function toSnakeCase(str) {
93
93
  if (!str) return "";
94
94
  return str.trim().replace(/-/g, "_").replace(/\s+/g, " ").replace(/([A-Z]+)([A-Z][a-z])/g, "$1_$2").replace(/([a-z0-9])([A-Z])/g, "$1_$2").replace(/\s+/g, "_").replace(/_+/g, "_").toLowerCase();
95
95
  }
96
+ /**
97
+ * Removes leading and trailing whitespace from each line of a string
98
+ * @param {TemplateStringsArray | string} strings - The string to dedent
99
+ * @param {unknown[]} values - The values to insert into the string
100
+ * @returns {string} The dedented string
101
+ *
102
+ * @example
103
+ * ```ts
104
+ * import { dedent } from "@luxass/utils/string";
105
+ * const text = dedent` * This is a test.
106
+ * This is another line.
107
+ * `;
108
+ * // "This is a test.\nThis is another line."
109
+ *
110
+ * const text = dedent(` * This is a test.
111
+ * This is another line.
112
+ * `);
113
+ * // "This is a test.\nThis is another line."
114
+ * ```
115
+ */
96
116
  function dedent(strings, ...values) {
97
117
  return internal_dedent(strings, values, false);
98
118
  }
99
119
  dedent.raw = dedentRaw;
120
+ /**
121
+ * Removes leading and trailing whitespace from each line of a string
122
+ * @param {TemplateStringsArray | string} strings - The string to dedent
123
+ * @param {unknown[]} values - The values to insert into the string
124
+ * @returns {string} The dedented string
125
+ *
126
+ * @example
127
+ * ```ts
128
+ * import { dedentRaw } from "@luxass/utils/string";
129
+ * const text = dedentRaw(`
130
+ * This is a test.
131
+ * This is another line.
132
+ * `);
133
+ * // "This is a test.\nThis is another line."
134
+ *
135
+ * const text = dedentRaw`
136
+ * This is a test.
137
+ * This is another line.
138
+ * `
139
+ * // "This is a test.\nThis is another line."
140
+ * ```
141
+ */
100
142
  function dedentRaw(strings, ...values) {
101
143
  return internal_dedent(strings, values, true);
102
144
  }
package/dist/string.d.ts CHANGED
@@ -1,2 +1,2 @@
1
- import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-Cwp8CD7H.js";
1
+ import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-BgrFQWVx.js";
2
2
  export { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase };
package/dist/string.js CHANGED
@@ -1,3 +1,3 @@
1
- import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-pQApOGKP.js";
1
+ import { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase } from "./string-BlwTLoKD.js";
2
2
 
3
3
  export { capitalize, dedent, dedentRaw, formatStr, sanitizeIdentifier, toCamelCase, toKebabCase, toPascalCase, toSnakeCase };
@@ -0,0 +1,143 @@
1
+ //#region src/types.d.ts
2
+ /**
3
+ * Whatever type, or null
4
+ * @template T
5
+ * @returns {T | null} T or null
6
+ *
7
+ * @example
8
+ * ```ts
9
+ * import { Nullable } from "@luxass/utils/types";
10
+ *
11
+ * type A = Nullable<string>
12
+ * // string | null
13
+ * ```
14
+ */
15
+ type Nullable<T> = T | null;
16
+ /**
17
+ * Whatever type, null or undefined
18
+ * @template T
19
+ * @returns {T | null | undefined} T, undefined or null
20
+ *
21
+ * @example
22
+ * ```ts
23
+ * import { Nullish } from "@luxass/utils/types";
24
+ *
25
+ * type A = Nullish<string>
26
+ * // string | null | undefined
27
+ * ```
28
+ */
29
+ type Nullish<T> = T | null | undefined;
30
+ /**
31
+ * A type that can be an array or a single value.
32
+ * @template T
33
+ * @returns {T | T[]} T or T[]
34
+ *
35
+ * @example
36
+ * ```ts
37
+ * import { MaybeArray } from "@luxass/utils/types";
38
+ *
39
+ * type A = MaybeArray<string>
40
+ * // string | string[]
41
+ * ```
42
+ */
43
+ type MaybeArray<T> = T | T[];
44
+ /**
45
+ * A type that can be a value or a promise.
46
+ * @template T
47
+ * @returns {T | Promise<T>} T or Promise<T>
48
+ *
49
+ * @example
50
+ * ```ts
51
+ * import { MaybePromise } from "@luxass/utils/types";
52
+ *
53
+ * type A = MaybePromise<string>
54
+ * // string | Promise<string>
55
+ * ```
56
+ */
57
+ type MaybePromise<T> = T | Promise<T>;
58
+ /**
59
+ * Infers the element type of an array
60
+ * @template T
61
+ * @returns {T extends (infer E)[] ? E : never} The inferred element type
62
+ *
63
+ * @example
64
+ * ```ts
65
+ * import { ElementOf } from "@luxass/utils/types";
66
+ *
67
+ * type A = ElementOf<string[]>
68
+ * // string
69
+ * ```
70
+ */
71
+ type ElementOf<T> = T extends (infer E)[] ? E : never;
72
+ /**
73
+ * Infers the arguments type of a function
74
+ * @template T
75
+ * @returns {T extends ((...args: infer A) => any) ? A : never} The inferred arguments type
76
+ *
77
+ * @example
78
+ * ```ts
79
+ * import { InferArguments } from "@luxass/utils/types";
80
+ *
81
+ * type A = InferArguments<(a: string, b: number) => void>
82
+ * // [string, number]
83
+ * ```
84
+ */
85
+ type InferArguments<T> = T extends ((...args: infer A) => any) ? A : never;
86
+ /**
87
+ * Makes complex nested types more readable in editor tooltips by flattening
88
+ * the type to a simple object type with all properties
89
+ * @template T
90
+ * @returns {{ [K in keyof T]: T[K] } & {}} A simplified representation of the same type
91
+ *
92
+ * @example
93
+ * ```ts
94
+ * import { Prettify } from "@luxass/utils/types";
95
+ *
96
+ * type Messy = { a: string } & { b: number } & { c: boolean }
97
+ * type Clean = Prettify<Messy>
98
+ * // { a: string; b: number; c: boolean }
99
+ * ```
100
+ */
101
+ type Prettify<T> = { [K in keyof T]: T[K] } & {};
102
+ /**
103
+ * Removes index signatures from a type while preserving specific properties
104
+ * @template T
105
+ * @returns {{ [K in keyof T as {} extends Record<K, 1> ? never : K]: T[K] }} A new type without index signatures
106
+ *
107
+ * @example
108
+ * ```ts
109
+ * import { RemoveIndexSignature } from "@luxass/utils/types";
110
+ *
111
+ * type WithIndex = { id: number; [key: string]: any }
112
+ * type Clean = RemoveIndexSignature<WithIndex>
113
+ * // { id: number }
114
+ * ```
115
+ */
116
+ type RemoveIndexSignature<T> = { [K in keyof T as {} extends Record<K, 1> ? never : K]: T[K] };
117
+ /**
118
+ * A safer version of the built-in Omit utility type that ensures the keys
119
+ * being omitted actually exist on the source type
120
+ * @template T
121
+ * @template {keyof T} K
122
+ * @returns {Omit<T, K>} A new type with the specified keys omitted
123
+ *
124
+ * @example
125
+ * ```ts
126
+ * import { SafeOmit } from "@luxass/utils/types";
127
+ *
128
+ * interface User {
129
+ * id: number;
130
+ * name: string;
131
+ * email: string;
132
+ * }
133
+ *
134
+ * type UserWithoutEmail = SafeOmit<User, 'email'>
135
+ * // { id: number; name: string }
136
+ *
137
+ * // TypeScript error - 'invalid' is not a key of User
138
+ * type Invalid = SafeOmit<User, 'invalid'>
139
+ * ```
140
+ */
141
+ type SafeOmit<T, K extends keyof T> = Omit<T, K>;
142
+ //#endregion
143
+ export { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature, SafeOmit };
package/dist/types.d.ts CHANGED
@@ -1,2 +1,2 @@
1
- import { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature } from "./types-BtiMC8Uf.js";
2
- export { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature };
1
+ import { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature, SafeOmit } from "./types-DwW0ucVr.js";
2
+ export { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature, SafeOmit };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@luxass/utils",
3
- "version": "2.6.0",
3
+ "version": "2.6.2",
4
4
  "description": "A collection of utilities for JavaScript/TypeScript",
5
5
  "type": "module",
6
6
  "author": {
@@ -44,13 +44,13 @@
44
44
  "p-retry": "^6.2.1"
45
45
  },
46
46
  "devDependencies": {
47
- "@luxass/eslint-config": "^5.1.0",
47
+ "@luxass/eslint-config": "^5.1.1",
48
48
  "@types/node": "^22.15.2",
49
49
  "@vitest/coverage-v8": "3.2.4",
50
- "eslint": "^9.30.1",
50
+ "eslint": "^9.32.0",
51
51
  "eslint-plugin-format": "^1.0.1",
52
52
  "publint": "^0.3.12",
53
- "tsdown": "^0.12.9",
53
+ "tsdown": "^0.13.0",
54
54
  "typescript": "^5.8.3",
55
55
  "vitest": "^3.2.4",
56
56
  "vitest-package-exports": "^0.1.1"
@@ -1,86 +0,0 @@
1
- //#region src/types.d.ts
2
- /**
3
- * Whatever type, or null
4
- * @param T - Type
5
- * @returns T or null
6
- *
7
- * @example
8
- * ```ts
9
- * type A = Nullable<string>
10
- * // string | null
11
- * ```
12
- */
13
- type Nullable<T> = T | null;
14
- /**
15
- * Whatever type, null or undefined
16
- * @param T - Type
17
- * @returns T, undefined or null
18
- *
19
- * @example
20
- * ```ts
21
- * type A = Nullish<string>
22
- * // string | null | undefined
23
- * ```
24
- */
25
- type Nullish<T> = T | null | undefined;
26
- /**
27
- * A type that can be an array or a single value.
28
- */
29
- type MaybeArray<T> = T | T[];
30
- /**
31
- * A type that can be a value or a promise.
32
- */
33
- type MaybePromise<T> = T | Promise<T>;
34
- /**
35
- * Infers the element type of an array
36
- * @param T - Array type
37
- * @returns The inferred element type
38
- *
39
- * @example
40
- * ```ts
41
- * type A = ElementOf<string[]>
42
- * // string
43
- * ```
44
- */
45
- type ElementOf<T> = T extends (infer E)[] ? E : never;
46
- /**
47
- * Infers the arguments type of a function
48
- * @param T - Function type
49
- * @returns The inferred arguments type
50
- *
51
- * @example
52
- * ```ts
53
- * type A = InferArguments<(a: string, b: number) => void>
54
- * // [string, number]
55
- * ```
56
- */
57
- type InferArguments<T> = T extends ((...args: infer A) => any) ? A : never;
58
- /**
59
- * Makes complex nested types more readable in editor tooltips by flattening
60
- * the type to a simple object type with all properties
61
- * @param T - The type to prettify
62
- * @returns A simplified representation of the same type
63
- *
64
- * @example
65
- * ```ts
66
- * type Messy = { a: string } & { b: number } & { c: boolean }
67
- * type Clean = Prettify<Messy>
68
- * // { a: string; b: number; c: boolean }
69
- * ```
70
- */
71
- type Prettify<T> = { [K in keyof T]: T[K] } & {};
72
- /**
73
- * Removes index signatures from a type while preserving specific properties
74
- * @param T - The type to remove index signatures from
75
- * @returns A new type without index signatures
76
- *
77
- * @example
78
- * ```ts
79
- * type WithIndex = { id: number; [key: string]: any }
80
- * type Clean = RemoveIndexSignature<WithIndex>
81
- * // { id: number }
82
- * ```
83
- */
84
- type RemoveIndexSignature<T> = { [K in keyof T as {} extends Record<K, 1> ? never : K]: T[K] };
85
- //#endregion
86
- export { ElementOf, InferArguments, MaybeArray, MaybePromise, Nullable, Nullish, Prettify, RemoveIndexSignature };