@catbee/utils 0.0.2 → 0.0.4
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/README.md +1 -4
- package/build/esm/config.d.ts +1 -5
- package/build/esm/config.js +6 -10
- package/build/esm/config.js.map +1 -1
- package/build/esm/index.d.ts +20 -19
- package/build/esm/index.js +20 -19
- package/build/esm/index.js.map +1 -1
- package/build/esm/types/api-response.d.ts +2 -2
- package/build/esm/types/api-response.js.map +1 -1
- package/build/esm/utils/array.utils.d.ts +1 -1
- package/build/esm/utils/array.utils.js +17 -27
- package/build/esm/utils/array.utils.js.map +1 -1
- package/build/esm/utils/async.utils.d.ts +1 -5
- package/build/esm/utils/async.utils.js +17 -20
- package/build/esm/utils/async.utils.js.map +1 -1
- package/build/esm/utils/cache.utils.js +2 -2
- package/build/esm/utils/cache.utils.js.map +1 -1
- package/build/esm/utils/context-store.utils.d.ts +1 -1
- package/build/esm/utils/context-store.utils.js +8 -8
- package/build/esm/utils/context-store.utils.js.map +1 -1
- package/build/esm/utils/crypto.utils.d.ts +2 -2
- package/build/esm/utils/crypto.utils.js +37 -45
- package/build/esm/utils/crypto.utils.js.map +1 -1
- package/build/esm/utils/decorators.utils.d.ts +2 -18
- package/build/esm/utils/decorators.utils.js +31 -31
- package/build/esm/utils/decorators.utils.js.map +1 -1
- package/build/esm/utils/dir.utils.d.ts +4 -4
- package/build/esm/utils/dir.utils.js +18 -20
- package/build/esm/utils/dir.utils.js.map +1 -1
- package/build/esm/utils/env.utils.js +22 -26
- package/build/esm/utils/env.utils.js.map +1 -1
- package/build/esm/utils/exception.utils.d.ts +1 -1
- package/build/esm/utils/exception.utils.js +26 -29
- package/build/esm/utils/exception.utils.js.map +1 -1
- package/build/esm/utils/fs.utils.d.ts +3 -3
- package/build/esm/utils/fs.utils.js +19 -23
- package/build/esm/utils/fs.utils.js.map +1 -1
- package/build/esm/utils/http-status-codes.js.map +1 -1
- package/build/esm/utils/id.utils.js +8 -8
- package/build/esm/utils/id.utils.js.map +1 -1
- package/build/esm/utils/logger.utils.d.ts +13 -4
- package/build/esm/utils/logger.utils.js +16 -18
- package/build/esm/utils/logger.utils.js.map +1 -1
- package/build/esm/utils/middleware.utils.d.ts +15 -26
- package/build/esm/utils/middleware.utils.js +80 -59
- package/build/esm/utils/middleware.utils.js.map +1 -1
- package/build/esm/utils/obj.utils.js +16 -27
- package/build/esm/utils/obj.utils.js.map +1 -1
- package/build/esm/utils/response.utils.d.ts +2 -2
- package/build/esm/utils/response.utils.js +11 -11
- package/build/esm/utils/response.utils.js.map +1 -1
- package/build/esm/utils/string.utils.js +17 -17
- package/build/esm/utils/string.utils.js.map +1 -1
- package/build/esm/utils/url.utils.js +20 -22
- package/build/esm/utils/url.utils.js.map +1 -1
- package/build/esm/utils/validate.utils.js +11 -15
- package/build/esm/utils/validate.utils.js.map +1 -1
- package/build/esnext/config.d.ts +1 -5
- package/build/esnext/config.js +6 -10
- package/build/esnext/config.js.map +1 -1
- package/build/esnext/index.d.ts +20 -19
- package/build/esnext/index.js +20 -19
- package/build/esnext/index.js.map +1 -1
- package/build/esnext/types/api-response.d.ts +2 -2
- package/build/esnext/types/api-response.js.map +1 -1
- package/build/esnext/utils/array.utils.d.ts +1 -1
- package/build/esnext/utils/array.utils.js +23 -31
- package/build/esnext/utils/array.utils.js.map +1 -1
- package/build/esnext/utils/async.utils.d.ts +1 -5
- package/build/esnext/utils/async.utils.js +22 -22
- package/build/esnext/utils/async.utils.js.map +1 -1
- package/build/esnext/utils/cache.utils.js +3 -3
- package/build/esnext/utils/cache.utils.js.map +1 -1
- package/build/esnext/utils/context-store.utils.d.ts +1 -1
- package/build/esnext/utils/context-store.utils.js +10 -10
- package/build/esnext/utils/context-store.utils.js.map +1 -1
- package/build/esnext/utils/crypto.utils.d.ts +2 -2
- package/build/esnext/utils/crypto.utils.js +37 -47
- package/build/esnext/utils/crypto.utils.js.map +1 -1
- package/build/esnext/utils/decorators.utils.d.ts +2 -18
- package/build/esnext/utils/decorators.utils.js +33 -33
- package/build/esnext/utils/decorators.utils.js.map +1 -1
- package/build/esnext/utils/dir.utils.d.ts +4 -4
- package/build/esnext/utils/dir.utils.js +22 -24
- package/build/esnext/utils/dir.utils.js.map +1 -1
- package/build/esnext/utils/env.utils.js +24 -26
- package/build/esnext/utils/env.utils.js.map +1 -1
- package/build/esnext/utils/exception.utils.d.ts +1 -1
- package/build/esnext/utils/exception.utils.js +26 -29
- package/build/esnext/utils/exception.utils.js.map +1 -1
- package/build/esnext/utils/fs.utils.d.ts +3 -3
- package/build/esnext/utils/fs.utils.js +21 -25
- package/build/esnext/utils/fs.utils.js.map +1 -1
- package/build/esnext/utils/http-status-codes.js.map +1 -1
- package/build/esnext/utils/id.utils.js +8 -8
- package/build/esnext/utils/id.utils.js.map +1 -1
- package/build/esnext/utils/logger.utils.d.ts +13 -4
- package/build/esnext/utils/logger.utils.js +16 -18
- package/build/esnext/utils/logger.utils.js.map +1 -1
- package/build/esnext/utils/middleware.utils.d.ts +15 -26
- package/build/esnext/utils/middleware.utils.js +78 -59
- package/build/esnext/utils/middleware.utils.js.map +1 -1
- package/build/esnext/utils/obj.utils.js +17 -26
- package/build/esnext/utils/obj.utils.js.map +1 -1
- package/build/esnext/utils/response.utils.d.ts +2 -2
- package/build/esnext/utils/response.utils.js +11 -11
- package/build/esnext/utils/response.utils.js.map +1 -1
- package/build/esnext/utils/string.utils.js +17 -17
- package/build/esnext/utils/string.utils.js.map +1 -1
- package/build/esnext/utils/url.utils.js +21 -23
- package/build/esnext/utils/url.utils.js.map +1 -1
- package/build/esnext/utils/validate.utils.js +14 -16
- package/build/esnext/utils/validate.utils.js.map +1 -1
- package/build/src/config.d.ts +1 -5
- package/build/src/config.js +5 -9
- package/build/src/config.js.map +1 -1
- package/build/src/index.d.ts +20 -19
- package/build/src/index.js +1 -0
- package/build/src/index.js.map +1 -1
- package/build/src/types/api-response.d.ts +2 -2
- package/build/src/types/api-response.js.map +1 -1
- package/build/src/utils/array.utils.d.ts +1 -1
- package/build/src/utils/array.utils.js +22 -30
- package/build/src/utils/array.utils.js.map +1 -1
- package/build/src/utils/async.utils.d.ts +1 -5
- package/build/src/utils/async.utils.js +22 -22
- package/build/src/utils/async.utils.js.map +1 -1
- package/build/src/utils/cache.utils.js +2 -2
- package/build/src/utils/cache.utils.js.map +1 -1
- package/build/src/utils/context-store.utils.d.ts +1 -1
- package/build/src/utils/context-store.utils.js +9 -9
- package/build/src/utils/context-store.utils.js.map +1 -1
- package/build/src/utils/crypto.utils.d.ts +2 -2
- package/build/src/utils/crypto.utils.js +35 -45
- package/build/src/utils/crypto.utils.js.map +1 -1
- package/build/src/utils/decorators.utils.d.ts +2 -18
- package/build/src/utils/decorators.utils.js +32 -32
- package/build/src/utils/decorators.utils.js.map +1 -1
- package/build/src/utils/dir.utils.d.ts +4 -4
- package/build/src/utils/dir.utils.js +16 -18
- package/build/src/utils/dir.utils.js.map +1 -1
- package/build/src/utils/env.utils.js +22 -24
- package/build/src/utils/env.utils.js.map +1 -1
- package/build/src/utils/exception.utils.d.ts +1 -1
- package/build/src/utils/exception.utils.js +23 -26
- package/build/src/utils/exception.utils.js.map +1 -1
- package/build/src/utils/fs.utils.d.ts +3 -3
- package/build/src/utils/fs.utils.js +15 -19
- package/build/src/utils/fs.utils.js.map +1 -1
- package/build/src/utils/http-status-codes.js.map +1 -1
- package/build/src/utils/id.utils.js +7 -7
- package/build/src/utils/id.utils.js.map +1 -1
- package/build/src/utils/logger.utils.d.ts +13 -4
- package/build/src/utils/logger.utils.js +13 -15
- package/build/src/utils/logger.utils.js.map +1 -1
- package/build/src/utils/middleware.utils.d.ts +15 -26
- package/build/src/utils/middleware.utils.js +72 -52
- package/build/src/utils/middleware.utils.js.map +1 -1
- package/build/src/utils/obj.utils.js +17 -26
- package/build/src/utils/obj.utils.js.map +1 -1
- package/build/src/utils/response.utils.d.ts +2 -2
- package/build/src/utils/response.utils.js +9 -9
- package/build/src/utils/response.utils.js.map +1 -1
- package/build/src/utils/string.utils.js +17 -17
- package/build/src/utils/string.utils.js.map +1 -1
- package/build/src/utils/url.utils.js +20 -22
- package/build/src/utils/url.utils.js.map +1 -1
- package/build/src/utils/validate.utils.js +14 -16
- package/build/src/utils/validate.utils.js.map +1 -1
- package/package.json +3 -3
package/build/src/config.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/config.ts"],"names":[],"mappings":";;;AAAA,iDAAwC;
|
|
1
|
+
{"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/config.ts"],"names":[],"mappings":";;;AAAA,iDAAwC;AAIxC;;GAEG;AACU,QAAA,MAAM,GAAG;IACpB,MAAM,EAAE;QACN;;WAEG;QACH,KAAK,EAAE,eAAG,CAAC,GAAG,CAAC,cAAc,EAAE,MAAM,CAAa;QAElD;;WAEG;QACH,IAAI,EAAE,eAAG,CAAC,GAAG,CAAC,aAAa,EAAE,eAAG,CAAC,GAAG,CAAC,kBAAkB,EAAE,eAAe,CAAC,CAAC;KAC3E;IAED,IAAI,EAAE;QACJ;;WAEG;QACH,OAAO,EAAE,eAAG,CAAC,SAAS,CAAC,cAAc,EAAE,KAAK,CAAC;KAC9C;IAED,KAAK,EAAE;QACL;;WAEG;QACH,UAAU,EAAE,eAAG,CAAC,SAAS,CAAC,mBAAmB,EAAE,GAAG,CAAC;KACpD;CACF,CAAC","sourcesContent":["import { Env } from './utils/env.utils';\n\ntype LogLevel = 'fatal' | 'error' | 'warn' | 'info' | 'debug' | 'trace' | 'silent';\n\n/**\n * Application runtime configuration loaded from environment variables.\n */\nexport const Config = {\n Logger: {\n /**\n * Logging level (e.g., 'info', 'debug', 'warn', 'error').\n */\n level: Env.get('LOGGER_LEVEL', 'info') as LogLevel,\n\n /**\n * Name of the logger instance (defaults to npm package name).\n */\n name: Env.get('LOGGER_NAME', Env.get('npm_package_name', '@catbee/utils'))\n },\n\n Http: {\n /**\n * Timeout for HTTP requests in milliseconds\n */\n timeout: Env.getNumber('HTTP_TIMEOUT', 30000)\n },\n\n Cache: {\n /**\n * Default TTL (time to live) for cache entries in seconds\n */\n defaultTtl: Env.getNumber('CACHE_DEFAULT_TTL', 300)\n }\n};\n"]}
|
package/build/src/index.d.ts
CHANGED
|
@@ -1,20 +1,21 @@
|
|
|
1
|
-
export * from
|
|
2
|
-
export * from
|
|
3
|
-
export * from
|
|
4
|
-
export * from
|
|
5
|
-
export * from
|
|
6
|
-
export * from
|
|
7
|
-
export * from
|
|
8
|
-
export * from
|
|
9
|
-
export * from
|
|
10
|
-
export * from
|
|
11
|
-
export * from
|
|
12
|
-
export * from
|
|
13
|
-
export * from
|
|
14
|
-
export * from
|
|
15
|
-
export * from
|
|
16
|
-
export * from
|
|
17
|
-
export * from
|
|
18
|
-
export * from
|
|
19
|
-
export * from
|
|
1
|
+
export * from './utils/array.utils';
|
|
2
|
+
export * from './utils/async.utils';
|
|
3
|
+
export * from './utils/cache.utils';
|
|
4
|
+
export * from './utils/context-store.utils';
|
|
5
|
+
export * from './utils/crypto.utils';
|
|
6
|
+
export * from './utils/decorators.utils';
|
|
7
|
+
export * from './utils/dir.utils';
|
|
8
|
+
export * from './utils/env.utils';
|
|
9
|
+
export * from './utils/exception.utils';
|
|
10
|
+
export * from './utils/fs.utils';
|
|
11
|
+
export * from './utils/http-status-codes';
|
|
12
|
+
export * from './utils/id.utils';
|
|
13
|
+
export * from './utils/logger.utils';
|
|
14
|
+
export * from './utils/middleware.utils';
|
|
15
|
+
export * from './utils/obj.utils';
|
|
16
|
+
export * from './utils/response.utils';
|
|
17
|
+
export * from './utils/string.utils';
|
|
18
|
+
export * from './utils/url.utils';
|
|
19
|
+
export * from './utils/validate.utils';
|
|
20
|
+
export * from './types/api-response';
|
|
20
21
|
//# sourceMappingURL=index.d.ts.map
|
package/build/src/index.js
CHANGED
|
@@ -19,6 +19,7 @@ __exportStar(require("./utils/async.utils"), exports);
|
|
|
19
19
|
__exportStar(require("./utils/cache.utils"), exports);
|
|
20
20
|
__exportStar(require("./utils/context-store.utils"), exports);
|
|
21
21
|
__exportStar(require("./utils/crypto.utils"), exports);
|
|
22
|
+
__exportStar(require("./utils/decorators.utils"), exports);
|
|
22
23
|
__exportStar(require("./utils/dir.utils"), exports);
|
|
23
24
|
__exportStar(require("./utils/env.utils"), exports);
|
|
24
25
|
__exportStar(require("./utils/exception.utils"), exports);
|
package/build/src/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,sDAAoC;AACpC,sDAAoC;AACpC,sDAAoC;AACpC,8DAA4C;AAC5C,uDAAqC;AACrC,oDAAkC;AAClC,oDAAkC;AAClC,0DAAwC;AACxC,mDAAiC;AACjC,4DAA0C;AAC1C,mDAAiC;AACjC,uDAAqC;AACrC,2DAAyC;AACzC,oDAAkC;AAClC,yDAAuC;AACvC,uDAAqC;AACrC,oDAAkC;AAClC,yDAAuC;AAEvC,uDAAqC","sourcesContent":["export * from
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,sDAAoC;AACpC,sDAAoC;AACpC,sDAAoC;AACpC,8DAA4C;AAC5C,uDAAqC;AACrC,2DAAyC;AACzC,oDAAkC;AAClC,oDAAkC;AAClC,0DAAwC;AACxC,mDAAiC;AACjC,4DAA0C;AAC1C,mDAAiC;AACjC,uDAAqC;AACrC,2DAAyC;AACzC,oDAAkC;AAClC,yDAAuC;AACvC,uDAAqC;AACrC,oDAAkC;AAClC,yDAAuC;AAEvC,uDAAqC","sourcesContent":["export * from './utils/array.utils';\nexport * from './utils/async.utils';\nexport * from './utils/cache.utils';\nexport * from './utils/context-store.utils';\nexport * from './utils/crypto.utils';\nexport * from './utils/decorators.utils';\nexport * from './utils/dir.utils';\nexport * from './utils/env.utils';\nexport * from './utils/exception.utils';\nexport * from './utils/fs.utils';\nexport * from './utils/http-status-codes';\nexport * from './utils/id.utils';\nexport * from './utils/logger.utils';\nexport * from './utils/middleware.utils';\nexport * from './utils/obj.utils';\nexport * from './utils/response.utils';\nexport * from './utils/string.utils';\nexport * from './utils/url.utils';\nexport * from './utils/validate.utils';\n\nexport * from './types/api-response';\n"]}
|
|
@@ -33,7 +33,7 @@ export interface Pagination<T = any> {
|
|
|
33
33
|
/** Field by which the data is sorted. */
|
|
34
34
|
sortBy: string;
|
|
35
35
|
/** Sort order: ascending or descending. */
|
|
36
|
-
sortOrder:
|
|
36
|
+
sortOrder: 'asc' | 'desc';
|
|
37
37
|
};
|
|
38
38
|
}
|
|
39
39
|
/**
|
|
@@ -45,7 +45,7 @@ export type PaginationResponse<T = any> = Pagination<T>;
|
|
|
45
45
|
* Error response structure with additional metadata.
|
|
46
46
|
* Used for providing richer error information to clients.
|
|
47
47
|
*/
|
|
48
|
-
export interface ApiErrorResponse extends Omit<ApiResponse<never>,
|
|
48
|
+
export interface ApiErrorResponse extends Omit<ApiResponse<never>, 'data'> {
|
|
49
49
|
/** Error always true for error responses */
|
|
50
50
|
error: true;
|
|
51
51
|
/** HTTP status code */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"api-response.js","sourceRoot":"","sources":["../../../src/types/api-response.ts"],"names":[],"mappings":"","sourcesContent":["/**\n * Generic API response format.\n * Used to wrap any successful or failed response from the server.\n */\nexport interface ApiResponse<T = any> {\n /** Payload returned from the API. Can be any shape depending on the endpoint. */\n data: T | null;\n\n /** Indicates whether an error occurred (true = error, false = success). */\n error: boolean;\n\n /** Human-readable message to describe the result or error. */\n message: string;\n\n /** Unique request ID for traceability in logs (e.g., from a middleware). */\n requestId: string;\n\n /** ISO timestamp when the response was generated. */\n timestamp: string;\n}\n\n/**\n * Generic pagination structure used for paged lists (e.g., /users?page=1).\n */\nexport interface Pagination<T = any> {\n /** List of records for the current page. */\n content: T[];\n\n /** Metadata about the pagination state. */\n pagination: {\n /** Total number of records across all pages. */\n totalRecords: number;\n\n /** Total number of pages available. */\n totalPages: number;\n\n /** Current page number (1-based index). */\n page: number;\n\n /** Number of records per page. */\n limit: number;\n\n /** Field by which the data is sorted. */\n sortBy: string;\n\n /** Sort order: ascending or descending. */\n sortOrder:
|
|
1
|
+
{"version":3,"file":"api-response.js","sourceRoot":"","sources":["../../../src/types/api-response.ts"],"names":[],"mappings":"","sourcesContent":["/**\n * Generic API response format.\n * Used to wrap any successful or failed response from the server.\n */\nexport interface ApiResponse<T = any> {\n /** Payload returned from the API. Can be any shape depending on the endpoint. */\n data: T | null;\n\n /** Indicates whether an error occurred (true = error, false = success). */\n error: boolean;\n\n /** Human-readable message to describe the result or error. */\n message: string;\n\n /** Unique request ID for traceability in logs (e.g., from a middleware). */\n requestId: string;\n\n /** ISO timestamp when the response was generated. */\n timestamp: string;\n}\n\n/**\n * Generic pagination structure used for paged lists (e.g., /users?page=1).\n */\nexport interface Pagination<T = any> {\n /** List of records for the current page. */\n content: T[];\n\n /** Metadata about the pagination state. */\n pagination: {\n /** Total number of records across all pages. */\n totalRecords: number;\n\n /** Total number of pages available. */\n totalPages: number;\n\n /** Current page number (1-based index). */\n page: number;\n\n /** Number of records per page. */\n limit: number;\n\n /** Field by which the data is sorted. */\n sortBy: string;\n\n /** Sort order: ascending or descending. */\n sortOrder: 'asc' | 'desc';\n };\n}\n\n/**\n * Alias for paginated API response.\n * Allows semantic naming like `PaginationResponse<User>` or `PaginationResponse<Post>`.\n */\nexport type PaginationResponse<T = any> = Pagination<T>;\n\n/**\n * Error response structure with additional metadata.\n * Used for providing richer error information to clients.\n */\nexport interface ApiErrorResponse extends Omit<ApiResponse<never>, 'data'> {\n /** Error always true for error responses */\n error: true;\n\n /** HTTP status code */\n status: number;\n\n /** Error code for client-side error handling */\n code?: string;\n\n /** Optional detailed validation errors */\n details?: Record<string, string[]>;\n\n /** Link to error documentation */\n docUrl?: string;\n}\n\n/**\n * Success response structure with strongly typed data.\n * Used for providing successful responses to clients.\n */\nexport interface ApiSuccessResponse<T = any> extends ApiResponse<T> {\n /** Error always false for success responses */\n error: false;\n\n /** HTTP status code (usually 200) */\n status?: number;\n}\n\n/**\n * Response structure for batch operations.\n * Used when multiple operations are performed in a single request.\n */\nexport interface BatchResponse<T = any> {\n /** Overall success/failure indicator */\n success: boolean;\n\n /** Total number of operations */\n total: number;\n\n /** Number of successful operations */\n successful: number;\n\n /** Number of failed operations */\n failed: number;\n\n /** Results of individual operations */\n results: Array<{\n /** Identifier for this operation */\n id: string | number;\n\n /** Success/failure indicator for this operation */\n success: boolean;\n\n /** Response data for this operation */\n data?: T;\n\n /** Error information if this operation failed */\n error?: {\n message: string;\n code?: string;\n };\n }>;\n}\n\n/**\n * Response structure for asynchronous operations.\n * Used when the operation will complete in the future.\n */\nexport interface AsyncOperationResponse {\n /** Always true for async operations */\n async: true;\n\n /** Job or task ID to check status later */\n jobId: string;\n\n /** Estimated completion time in seconds (if known) */\n estimatedTime?: number;\n\n /** URL to check status */\n statusUrl: string;\n}\n\n/**\n * Response structure for streaming operations.\n * Used when data is returned as a stream rather than all at once.\n */\nexport interface StreamResponse {\n /** Stream identifier */\n streamId: string;\n\n /** Stream type (e.g., 'json', 'binary') */\n streamType: string;\n\n /** Total size in bytes (if known) */\n totalSize?: number;\n\n /** Chunk size in bytes */\n chunkSize: number;\n}\n"]}
|
|
@@ -101,7 +101,7 @@ export declare function intersect<T>(a: T[], b: T[]): T[];
|
|
|
101
101
|
* @returns {T[]} A new sorted array.
|
|
102
102
|
* @throws {TypeError} If array is not an array.
|
|
103
103
|
*/
|
|
104
|
-
export declare function mergeSort<T>(array: T[], key: string | ((item: T) => any), direction?:
|
|
104
|
+
export declare function mergeSort<T>(array: T[], key: string | ((item: T) => any), direction?: 'asc' | 'desc'): T[];
|
|
105
105
|
/**
|
|
106
106
|
* Combines multiple arrays into a single array of grouped elements.
|
|
107
107
|
* Output array length equals the length of the shortest input array.
|
|
@@ -30,11 +30,11 @@ const obj_utils_1 = require("./obj.utils");
|
|
|
30
30
|
*/
|
|
31
31
|
function chunk(array, size) {
|
|
32
32
|
if (!Array.isArray(array))
|
|
33
|
-
throw new TypeError(
|
|
33
|
+
throw new TypeError('Expected an array');
|
|
34
34
|
if (!array.length)
|
|
35
35
|
return [];
|
|
36
36
|
if (!Number.isInteger(size) || size <= 0)
|
|
37
|
-
throw new Error(
|
|
37
|
+
throw new Error('Chunk size must be a positive integer');
|
|
38
38
|
return Array.from({ length: Math.ceil(array.length / size) }, (_, i) => array.slice(i * size, i * size + size));
|
|
39
39
|
}
|
|
40
40
|
/**
|
|
@@ -52,7 +52,7 @@ function unique(array, keyFn) {
|
|
|
52
52
|
if (!keyFn)
|
|
53
53
|
return Array.from(new Set(array));
|
|
54
54
|
const seen = new Set();
|
|
55
|
-
return array.filter(
|
|
55
|
+
return array.filter(item => {
|
|
56
56
|
const key = keyFn(item);
|
|
57
57
|
if (seen.has(key))
|
|
58
58
|
return false;
|
|
@@ -95,9 +95,7 @@ function random(array) {
|
|
|
95
95
|
function groupBy(array, keyOrFn) {
|
|
96
96
|
if (!Array.isArray(array) || array.length === 0)
|
|
97
97
|
return {};
|
|
98
|
-
const keyFn = typeof keyOrFn ===
|
|
99
|
-
? keyOrFn
|
|
100
|
-
: (item) => item[keyOrFn];
|
|
98
|
+
const keyFn = typeof keyOrFn === 'function' ? keyOrFn : (item) => item[keyOrFn];
|
|
101
99
|
return array.reduce((acc, item) => {
|
|
102
100
|
const key = keyFn(item);
|
|
103
101
|
if (!acc[key])
|
|
@@ -117,7 +115,7 @@ function groupBy(array, keyOrFn) {
|
|
|
117
115
|
*/
|
|
118
116
|
function shuffle(array) {
|
|
119
117
|
if (!Array.isArray(array))
|
|
120
|
-
throw new TypeError(
|
|
118
|
+
throw new TypeError('Expected an array');
|
|
121
119
|
const copy = array.slice();
|
|
122
120
|
for (let i = copy.length - 1; i > 0; i--) {
|
|
123
121
|
const j = Math.floor(Math.random() * (i + 1));
|
|
@@ -137,7 +135,7 @@ function shuffle(array) {
|
|
|
137
135
|
function pluck(array, key) {
|
|
138
136
|
if (!Array.isArray(array))
|
|
139
137
|
return [];
|
|
140
|
-
return array.map(
|
|
138
|
+
return array.map(item => item[key]);
|
|
141
139
|
}
|
|
142
140
|
/**
|
|
143
141
|
* Returns values in array A that are not in array B.
|
|
@@ -151,7 +149,7 @@ function difference(a, b) {
|
|
|
151
149
|
if (!Array.isArray(a) || !Array.isArray(b))
|
|
152
150
|
return [];
|
|
153
151
|
const setB = new Set(b);
|
|
154
|
-
return a.filter(
|
|
152
|
+
return a.filter(item => !setB.has(item));
|
|
155
153
|
}
|
|
156
154
|
/**
|
|
157
155
|
* Returns common values between arrays A and B.
|
|
@@ -165,7 +163,7 @@ function intersect(a, b) {
|
|
|
165
163
|
if (!Array.isArray(a) || !Array.isArray(b))
|
|
166
164
|
return [];
|
|
167
165
|
const setB = new Set(b);
|
|
168
|
-
return a.filter(
|
|
166
|
+
return a.filter(item => setB.has(item));
|
|
169
167
|
}
|
|
170
168
|
/**
|
|
171
169
|
* Sorts an array of objects by a nested key using Merge Sort (O(n log n)).
|
|
@@ -178,14 +176,12 @@ function intersect(a, b) {
|
|
|
178
176
|
* @returns {T[]} A new sorted array.
|
|
179
177
|
* @throws {TypeError} If array is not an array.
|
|
180
178
|
*/
|
|
181
|
-
function mergeSort(array, key, direction =
|
|
179
|
+
function mergeSort(array, key, direction = 'asc') {
|
|
182
180
|
if (!Array.isArray(array))
|
|
183
|
-
throw new TypeError(
|
|
181
|
+
throw new TypeError('Expected array');
|
|
184
182
|
if (array.length <= 1)
|
|
185
183
|
return array.slice();
|
|
186
|
-
const keyFn = typeof key ===
|
|
187
|
-
? key
|
|
188
|
-
: (item) => (0, obj_utils_1.getValueByPath)(item, key);
|
|
184
|
+
const keyFn = typeof key === 'function' ? key : (item) => (0, obj_utils_1.getValueByPath)(item, key);
|
|
189
185
|
const compare = (a, b) => {
|
|
190
186
|
const aVal = keyFn(a);
|
|
191
187
|
const bVal = keyFn(b);
|
|
@@ -193,10 +189,10 @@ function mergeSort(array, key, direction = "asc") {
|
|
|
193
189
|
if (aVal === bVal)
|
|
194
190
|
return 0;
|
|
195
191
|
if (aVal == null)
|
|
196
|
-
return direction ===
|
|
192
|
+
return direction === 'asc' ? 1 : -1;
|
|
197
193
|
if (bVal == null)
|
|
198
|
-
return direction ===
|
|
199
|
-
return direction ===
|
|
194
|
+
return direction === 'asc' ? -1 : 1;
|
|
195
|
+
return direction === 'asc' ? (aVal < bVal ? -1 : 1) : aVal > bVal ? -1 : 1;
|
|
200
196
|
};
|
|
201
197
|
const merge = (left, right) => {
|
|
202
198
|
const result = [];
|
|
@@ -230,13 +226,13 @@ function mergeSort(array, key, direction = "asc") {
|
|
|
230
226
|
function zip(...arrays) {
|
|
231
227
|
if (arrays.length === 0)
|
|
232
228
|
return [];
|
|
233
|
-
if (arrays.some(
|
|
234
|
-
throw new TypeError(
|
|
229
|
+
if (arrays.some(arr => !Array.isArray(arr))) {
|
|
230
|
+
throw new TypeError('All arguments must be arrays');
|
|
235
231
|
}
|
|
236
|
-
const minLength = Math.min(...arrays.map(
|
|
232
|
+
const minLength = Math.min(...arrays.map(arr => arr.length));
|
|
237
233
|
const result = [];
|
|
238
234
|
for (let i = 0; i < minLength; i++) {
|
|
239
|
-
result.push(arrays.map(
|
|
235
|
+
result.push(arrays.map(arr => arr[i]));
|
|
240
236
|
}
|
|
241
237
|
return result;
|
|
242
238
|
}
|
|
@@ -252,9 +248,7 @@ function partition(array, predicate) {
|
|
|
252
248
|
if (!Array.isArray(array))
|
|
253
249
|
return [[], []];
|
|
254
250
|
return array.reduce(([pass, fail], item, index) => {
|
|
255
|
-
return predicate(item, index, array)
|
|
256
|
-
? [[...pass, item], fail]
|
|
257
|
-
: [pass, [...fail, item]];
|
|
251
|
+
return predicate(item, index, array) ? [[...pass, item], fail] : [pass, [...fail, item]];
|
|
258
252
|
}, [[], []]);
|
|
259
253
|
}
|
|
260
254
|
/**
|
|
@@ -266,13 +260,11 @@ function partition(array, predicate) {
|
|
|
266
260
|
* @returns {number[]} Array of numbers in range.
|
|
267
261
|
*/
|
|
268
262
|
function range(start, end, step = 1) {
|
|
269
|
-
if (!Number.isFinite(start) ||
|
|
270
|
-
|
|
271
|
-
!Number.isFinite(step)) {
|
|
272
|
-
throw new TypeError("Arguments must be finite numbers");
|
|
263
|
+
if (!Number.isFinite(start) || !Number.isFinite(end) || !Number.isFinite(step)) {
|
|
264
|
+
throw new TypeError('Arguments must be finite numbers');
|
|
273
265
|
}
|
|
274
266
|
if (step === 0)
|
|
275
|
-
throw new Error(
|
|
267
|
+
throw new Error('Step cannot be zero');
|
|
276
268
|
const isAscending = step > 0;
|
|
277
269
|
if ((isAscending && start >= end) || (!isAscending && start <= end)) {
|
|
278
270
|
return [];
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"array.utils.js","sourceRoot":"","sources":["../../../src/utils/array.utils.ts"],"names":[],"mappings":"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","sourcesContent":["import { getValueByPath } from \"./obj.utils\";\n\n/**\n * Splits an array into chunks of the specified size.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The array to split into chunks.\n * @param {number} size - The number of elements per chunk.\n * @returns {T[][]} A new array containing chunked arrays.\n * @throws {TypeError} If array is not an array.\n * @throws {Error} If chunk size is not a positive integer.\n */\nexport function chunk<T>(array: T[], size: number): T[][] {\n if (!Array.isArray(array)) throw new TypeError(\"Expected an array\");\n if (!array.length) return [];\n if (!Number.isInteger(size) || size <= 0)\n throw new Error(\"Chunk size must be a positive integer\");\n return Array.from({ length: Math.ceil(array.length / size) }, (_, i) =>\n array.slice(i * size, i * size + size),\n );\n}\n\n/**\n * Removes duplicate values from an array.\n * Optionally enforces uniqueness by a key function.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T) => unknown} [keyFn] - Optional function to determine uniqueness by key.\n * @returns {T[]} A new array with unique values.\n */\nexport function unique<T>(array: T[], keyFn?: (item: T) => unknown): T[] {\n if (!Array.isArray(array) || array.length === 0) return [];\n if (!keyFn) return Array.from(new Set(array));\n const seen = new Set<unknown>();\n return array.filter((item) => {\n const key = keyFn(item);\n if (seen.has(key)) return false;\n seen.add(key);\n return true;\n });\n}\n\n/**\n * Deeply flattens a nested array to a single-level array.\n *\n * @template T The leaf type of array elements.\n * @param {any[]} array - The (possibly deeply nested) input array.\n * @returns {T[]} A deeply flattened array.\n */\nexport function flattenDeep<T>(array: any[]): T[] {\n if (!Array.isArray(array)) return [];\n return array.reduce<T[]>((acc, val) => {\n if (Array.isArray(val)) {\n acc.push(...flattenDeep<T>(val));\n } else {\n acc.push(val);\n }\n return acc;\n }, []);\n}\n\n/**\n * Returns a random element from an array, or undefined if empty.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @returns {T | undefined} A randomly selected item, or undefined if array is empty or not an array.\n */\nexport function random<T>(array: T[]): T | undefined {\n if (!Array.isArray(array) || array.length === 0) return undefined;\n return array[Math.floor(Math.random() * array.length)];\n}\n\n/* eslint-disable no-redeclare */\n/**\n * Groups items in an array by a key or key function.\n *\n * @template T The type of array elements.\n * @overload\n * @param {T[]} array - The array to group.\n * @param {keyof T} key - Property key to group by.\n * @returns {Record<string, T[]>}\n * @overload\n * @param {T[]} array - The array to group.\n * @param {(item: T) => string | number | symbol} keyFn - Function to generate group key from item.\n * @returns {Record<K, T[]>}\n * @param {T[]} array - The array to group.\n * @param {keyof T | ((item: T) => string | number | symbol)} keyOrFn - Property key or key-generating function.\n * @returns {Record<string | number | symbol, T[]>} An object mapping group keys to item arrays.\n */\nexport function groupBy<T>(array: T[], key: keyof T): Record<string, T[]>;\nexport function groupBy<T, K extends string | number | symbol>(\n array: T[],\n keyFn: (item: T) => K,\n): Record<K, T[]>;\nexport function groupBy<T>(\n array: T[],\n keyOrFn: keyof T | ((item: T) => string | number | symbol),\n): Record<string | number | symbol, T[]> {\n if (!Array.isArray(array) || array.length === 0) return {};\n const keyFn =\n typeof keyOrFn === \"function\"\n ? keyOrFn\n : (item: T) => item[keyOrFn as keyof T];\n return array.reduce(\n (acc, item) => {\n const key = keyFn(item) as string | number | symbol;\n if (!acc[key]) acc[key] = [];\n acc[key].push(item);\n return acc;\n },\n {} as Record<string | number | symbol, T[]>,\n );\n}\n/* eslint-enable no-redeclare */\n\n/**\n * Shuffles an array using the Fisher-Yates algorithm.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @returns {T[]} A new shuffled array.\n * @throws {TypeError} If array is not an array.\n */\nexport function shuffle<T>(array: T[]): T[] {\n if (!Array.isArray(array)) throw new TypeError(\"Expected an array\");\n const copy = array.slice();\n for (let i = copy.length - 1; i > 0; i--) {\n const j = Math.floor(Math.random() * (i + 1));\n [copy[i], copy[j]] = [copy[j], copy[i]];\n }\n return copy;\n}\n\n/**\n * Returns an array of property values from an array of objects.\n *\n * @template T The type of array elements.\n * @template K The object property to pluck.\n * @param {T[]} array - The input array.\n * @param {K} key - The property name to pluck.\n * @returns {T[K][]} Array of property values.\n */\nexport function pluck<T, K extends keyof T>(array: T[], key: K): T[K][] {\n if (!Array.isArray(array)) return [];\n return array.map((item) => item[key]);\n}\n\n/**\n * Returns values in array A that are not in array B.\n *\n * @template T The type of array elements.\n * @param {T[]} a - First array.\n * @param {T[]} b - Second array.\n * @returns {T[]} Elements in A that are not in B.\n */\nexport function difference<T>(a: T[], b: T[]): T[] {\n if (!Array.isArray(a) || !Array.isArray(b)) return [];\n const setB = new Set(b);\n return a.filter((item) => !setB.has(item));\n}\n\n/**\n * Returns common values between arrays A and B.\n *\n * @template T The type of array elements.\n * @param {T[]} a - First array.\n * @param {T[]} b - Second array.\n * @returns {T[]} Elements that exist in both arrays.\n */\nexport function intersect<T>(a: T[], b: T[]): T[] {\n if (!Array.isArray(a) || !Array.isArray(b)) return [];\n const setB = new Set(b);\n return a.filter((item) => setB.has(item));\n}\n\n/**\n * Sorts an array of objects by a nested key using Merge Sort (O(n log n)).\n * Missing/undefined keys are sorted to the \"end\" (asc) or \"start\" (desc).\n *\n * @template T The type of array elements (objects).\n * @param {T[]} array - Array of objects to sort.\n * @param {string | ((item: T) => any)} key - Dot-notated key (e.g., \"profile.age\") or function.\n * @param {\"asc\" | \"desc\"} [direction=\"asc\"] - Sort direction: 'asc' or 'desc'.\n * @returns {T[]} A new sorted array.\n * @throws {TypeError} If array is not an array.\n */\nexport function mergeSort<T>(\n array: T[],\n key: string | ((item: T) => any),\n direction: \"asc\" | \"desc\" = \"asc\",\n): T[] {\n if (!Array.isArray(array)) throw new TypeError(\"Expected array\");\n if (array.length <= 1) return array.slice();\n\n const keyFn =\n typeof key === \"function\"\n ? key\n : (item: T) => getValueByPath(item as object, key);\n\n const compare = (a: T, b: T) => {\n const aVal = keyFn(a);\n const bVal = keyFn(b);\n // Sorts undefined/null last for \"asc\", first for \"desc\"\n if (aVal === bVal) return 0;\n if (aVal == null) return direction === \"asc\" ? 1 : -1;\n if (bVal == null) return direction === \"asc\" ? -1 : 1;\n return direction === \"asc\" ? (aVal < bVal ? -1 : 1) : aVal > bVal ? -1 : 1;\n };\n\n const merge = (left: T[], right: T[]): T[] => {\n const result: T[] = [];\n let i = 0,\n j = 0;\n while (i < left.length && j < right.length) {\n if (compare(left[i], right[j]) <= 0) result.push(left[i++]);\n else result.push(right[j++]);\n }\n return result.concat(left.slice(i)).concat(right.slice(j));\n };\n\n const sort = (arr: T[]): T[] => {\n if (arr.length <= 1) return arr;\n const mid = Math.floor(arr.length / 2);\n const left = sort(arr.slice(0, mid));\n const right = sort(arr.slice(mid));\n return merge(left, right);\n };\n return sort(array);\n}\n\n/**\n * Combines multiple arrays into a single array of grouped elements.\n * Output array length equals the length of the shortest input array.\n *\n * @example zip([1, 2], ['a', 'b']) => [[1, 'a'], [2, 'b']]\n * @param {...Array<T>[]} arrays - Two or more arrays to zip together.\n * @returns {Array<T[]>} Array of grouped elements.\n */\nexport function zip<T>(...arrays: T[][]): T[][] {\n if (arrays.length === 0) return [];\n if (arrays.some((arr) => !Array.isArray(arr))) {\n throw new TypeError(\"All arguments must be arrays\");\n }\n\n const minLength = Math.min(...arrays.map((arr) => arr.length));\n const result: T[][] = [];\n\n for (let i = 0; i < minLength; i++) {\n result.push(arrays.map((arr) => arr[i]));\n }\n\n return result;\n}\n\n/**\n * Splits an array into two arrays based on a predicate function.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T, index: number, array: T[]) => boolean} predicate - Function to test each element.\n * @returns {[T[], T[]]} A tuple of two arrays: [matched, unmatched].\n */\nexport function partition<T>(\n array: T[],\n predicate: (item: T, index: number, array: T[]) => boolean,\n): [T[], T[]] {\n if (!Array.isArray(array)) return [[], []];\n\n return array.reduce(\n ([pass, fail], item, index) => {\n return predicate(item, index, array)\n ? [[...pass, item], fail]\n : [pass, [...fail, item]];\n },\n [[] as T[], [] as T[]],\n );\n}\n\n/**\n * Generates an array of numbers within a specified range.\n *\n * @param {number} start - Start of range (inclusive).\n * @param {number} end - End of range (exclusive).\n * @param {number} [step=1] - Step between numbers.\n * @returns {number[]} Array of numbers in range.\n */\nexport function range(start: number, end: number, step: number = 1): number[] {\n if (\n !Number.isFinite(start) ||\n !Number.isFinite(end) ||\n !Number.isFinite(step)\n ) {\n throw new TypeError(\"Arguments must be finite numbers\");\n }\n if (step === 0) throw new Error(\"Step cannot be zero\");\n\n const isAscending = step > 0;\n if ((isAscending && start >= end) || (!isAscending && start <= end)) {\n return [];\n }\n\n const length = Math.max(Math.ceil((end - start) / step), 0);\n const result = new Array(length);\n\n for (let i = 0, value = start; i < length; i++, value += step) {\n result[i] = value;\n }\n\n return result;\n}\n\n/**\n * Returns the first n elements of an array.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {number} [n=1] - Number of elements to take.\n * @returns {T[]} New array with first n elements.\n */\nexport function take<T>(array: T[], n: number = 1): T[] {\n if (!Array.isArray(array) || n <= 0) return [];\n return array.slice(0, n);\n}\n\n/**\n * Takes elements from the array while predicate returns true.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T, index: number) => boolean} predicate - Function to test each element.\n * @returns {T[]} New array with taken elements.\n */\nexport function takeWhile<T>(\n array: T[],\n predicate: (item: T, index: number) => boolean,\n): T[] {\n if (!Array.isArray(array)) return [];\n\n const result: T[] = [];\n for (let i = 0; i < array.length; i++) {\n if (!predicate(array[i], i)) break;\n result.push(array[i]);\n }\n\n return result;\n}\n\n/**\n * Removes all falsy values from an array.\n * False, null, 0, \"\", undefined, and NaN are falsy.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @returns {NonNullable<T>[]} New array with falsy values removed.\n */\nexport function compact<T>(array: T[]): NonNullable<T>[] {\n if (!Array.isArray(array)) return [];\n return array.filter(Boolean) as NonNullable<T>[];\n}\n\n/**\n * Counts array elements by a key function.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T) => string | number | symbol} keyFn - Function to generate count key.\n * @returns {Record<string, number>} Object with counts by key.\n */\nexport function countBy<T>(\n array: T[],\n keyFn: (item: T) => string | number | symbol,\n): Record<string, number> {\n if (!Array.isArray(array)) return {};\n\n return array.reduce(\n (acc, item) => {\n const key = String(keyFn(item));\n acc[key] = (acc[key] || 0) + 1;\n return acc;\n },\n {} as Record<string, number>,\n );\n}\n"]}
|
|
1
|
+
{"version":3,"file":"array.utils.js","sourceRoot":"","sources":["../../../src/utils/array.utils.ts"],"names":[],"mappings":"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","sourcesContent":["import { getValueByPath } from './obj.utils';\n\n/**\n * Splits an array into chunks of the specified size.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The array to split into chunks.\n * @param {number} size - The number of elements per chunk.\n * @returns {T[][]} A new array containing chunked arrays.\n * @throws {TypeError} If array is not an array.\n * @throws {Error} If chunk size is not a positive integer.\n */\nexport function chunk<T>(array: T[], size: number): T[][] {\n if (!Array.isArray(array)) throw new TypeError('Expected an array');\n if (!array.length) return [];\n if (!Number.isInteger(size) || size <= 0) throw new Error('Chunk size must be a positive integer');\n return Array.from({ length: Math.ceil(array.length / size) }, (_, i) => array.slice(i * size, i * size + size));\n}\n\n/**\n * Removes duplicate values from an array.\n * Optionally enforces uniqueness by a key function.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T) => unknown} [keyFn] - Optional function to determine uniqueness by key.\n * @returns {T[]} A new array with unique values.\n */\nexport function unique<T>(array: T[], keyFn?: (item: T) => unknown): T[] {\n if (!Array.isArray(array) || array.length === 0) return [];\n if (!keyFn) return Array.from(new Set(array));\n const seen = new Set<unknown>();\n return array.filter(item => {\n const key = keyFn(item);\n if (seen.has(key)) return false;\n seen.add(key);\n return true;\n });\n}\n\n/**\n * Deeply flattens a nested array to a single-level array.\n *\n * @template T The leaf type of array elements.\n * @param {any[]} array - The (possibly deeply nested) input array.\n * @returns {T[]} A deeply flattened array.\n */\nexport function flattenDeep<T>(array: any[]): T[] {\n if (!Array.isArray(array)) return [];\n return array.reduce<T[]>((acc, val) => {\n if (Array.isArray(val)) {\n acc.push(...flattenDeep<T>(val));\n } else {\n acc.push(val);\n }\n return acc;\n }, []);\n}\n\n/**\n * Returns a random element from an array, or undefined if empty.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @returns {T | undefined} A randomly selected item, or undefined if array is empty or not an array.\n */\nexport function random<T>(array: T[]): T | undefined {\n if (!Array.isArray(array) || array.length === 0) return undefined;\n return array[Math.floor(Math.random() * array.length)];\n}\n\n/* eslint-disable no-redeclare */\n/**\n * Groups items in an array by a key or key function.\n *\n * @template T The type of array elements.\n * @overload\n * @param {T[]} array - The array to group.\n * @param {keyof T} key - Property key to group by.\n * @returns {Record<string, T[]>}\n * @overload\n * @param {T[]} array - The array to group.\n * @param {(item: T) => string | number | symbol} keyFn - Function to generate group key from item.\n * @returns {Record<K, T[]>}\n * @param {T[]} array - The array to group.\n * @param {keyof T | ((item: T) => string | number | symbol)} keyOrFn - Property key or key-generating function.\n * @returns {Record<string | number | symbol, T[]>} An object mapping group keys to item arrays.\n */\nexport function groupBy<T>(array: T[], key: keyof T): Record<string, T[]>;\nexport function groupBy<T, K extends string | number | symbol>(array: T[], keyFn: (item: T) => K): Record<K, T[]>;\nexport function groupBy<T>(\n array: T[],\n keyOrFn: keyof T | ((item: T) => string | number | symbol)\n): Record<string | number | symbol, T[]> {\n if (!Array.isArray(array) || array.length === 0) return {};\n const keyFn = typeof keyOrFn === 'function' ? keyOrFn : (item: T) => item[keyOrFn as keyof T];\n return array.reduce(\n (acc, item) => {\n const key = keyFn(item) as string | number | symbol;\n if (!acc[key]) acc[key] = [];\n acc[key].push(item);\n return acc;\n },\n {} as Record<string | number | symbol, T[]>\n );\n}\n/* eslint-enable no-redeclare */\n\n/**\n * Shuffles an array using the Fisher-Yates algorithm.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @returns {T[]} A new shuffled array.\n * @throws {TypeError} If array is not an array.\n */\nexport function shuffle<T>(array: T[]): T[] {\n if (!Array.isArray(array)) throw new TypeError('Expected an array');\n const copy = array.slice();\n for (let i = copy.length - 1; i > 0; i--) {\n const j = Math.floor(Math.random() * (i + 1));\n [copy[i], copy[j]] = [copy[j], copy[i]];\n }\n return copy;\n}\n\n/**\n * Returns an array of property values from an array of objects.\n *\n * @template T The type of array elements.\n * @template K The object property to pluck.\n * @param {T[]} array - The input array.\n * @param {K} key - The property name to pluck.\n * @returns {T[K][]} Array of property values.\n */\nexport function pluck<T, K extends keyof T>(array: T[], key: K): T[K][] {\n if (!Array.isArray(array)) return [];\n return array.map(item => item[key]);\n}\n\n/**\n * Returns values in array A that are not in array B.\n *\n * @template T The type of array elements.\n * @param {T[]} a - First array.\n * @param {T[]} b - Second array.\n * @returns {T[]} Elements in A that are not in B.\n */\nexport function difference<T>(a: T[], b: T[]): T[] {\n if (!Array.isArray(a) || !Array.isArray(b)) return [];\n const setB = new Set(b);\n return a.filter(item => !setB.has(item));\n}\n\n/**\n * Returns common values between arrays A and B.\n *\n * @template T The type of array elements.\n * @param {T[]} a - First array.\n * @param {T[]} b - Second array.\n * @returns {T[]} Elements that exist in both arrays.\n */\nexport function intersect<T>(a: T[], b: T[]): T[] {\n if (!Array.isArray(a) || !Array.isArray(b)) return [];\n const setB = new Set(b);\n return a.filter(item => setB.has(item));\n}\n\n/**\n * Sorts an array of objects by a nested key using Merge Sort (O(n log n)).\n * Missing/undefined keys are sorted to the \"end\" (asc) or \"start\" (desc).\n *\n * @template T The type of array elements (objects).\n * @param {T[]} array - Array of objects to sort.\n * @param {string | ((item: T) => any)} key - Dot-notated key (e.g., \"profile.age\") or function.\n * @param {\"asc\" | \"desc\"} [direction=\"asc\"] - Sort direction: 'asc' or 'desc'.\n * @returns {T[]} A new sorted array.\n * @throws {TypeError} If array is not an array.\n */\nexport function mergeSort<T>(array: T[], key: string | ((item: T) => any), direction: 'asc' | 'desc' = 'asc'): T[] {\n if (!Array.isArray(array)) throw new TypeError('Expected array');\n if (array.length <= 1) return array.slice();\n\n const keyFn = typeof key === 'function' ? key : (item: T) => getValueByPath(item as object, key);\n\n const compare = (a: T, b: T) => {\n const aVal = keyFn(a);\n const bVal = keyFn(b);\n // Sorts undefined/null last for \"asc\", first for \"desc\"\n if (aVal === bVal) return 0;\n if (aVal == null) return direction === 'asc' ? 1 : -1;\n if (bVal == null) return direction === 'asc' ? -1 : 1;\n return direction === 'asc' ? (aVal < bVal ? -1 : 1) : aVal > bVal ? -1 : 1;\n };\n\n const merge = (left: T[], right: T[]): T[] => {\n const result: T[] = [];\n let i = 0,\n j = 0;\n while (i < left.length && j < right.length) {\n if (compare(left[i], right[j]) <= 0) result.push(left[i++]);\n else result.push(right[j++]);\n }\n return result.concat(left.slice(i)).concat(right.slice(j));\n };\n\n const sort = (arr: T[]): T[] => {\n if (arr.length <= 1) return arr;\n const mid = Math.floor(arr.length / 2);\n const left = sort(arr.slice(0, mid));\n const right = sort(arr.slice(mid));\n return merge(left, right);\n };\n return sort(array);\n}\n\n/**\n * Combines multiple arrays into a single array of grouped elements.\n * Output array length equals the length of the shortest input array.\n *\n * @example zip([1, 2], ['a', 'b']) => [[1, 'a'], [2, 'b']]\n * @param {...Array<T>[]} arrays - Two or more arrays to zip together.\n * @returns {Array<T[]>} Array of grouped elements.\n */\nexport function zip<T>(...arrays: T[][]): T[][] {\n if (arrays.length === 0) return [];\n if (arrays.some(arr => !Array.isArray(arr))) {\n throw new TypeError('All arguments must be arrays');\n }\n\n const minLength = Math.min(...arrays.map(arr => arr.length));\n const result: T[][] = [];\n\n for (let i = 0; i < minLength; i++) {\n result.push(arrays.map(arr => arr[i]));\n }\n\n return result;\n}\n\n/**\n * Splits an array into two arrays based on a predicate function.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T, index: number, array: T[]) => boolean} predicate - Function to test each element.\n * @returns {[T[], T[]]} A tuple of two arrays: [matched, unmatched].\n */\nexport function partition<T>(array: T[], predicate: (item: T, index: number, array: T[]) => boolean): [T[], T[]] {\n if (!Array.isArray(array)) return [[], []];\n\n return array.reduce(\n ([pass, fail], item, index) => {\n return predicate(item, index, array) ? [[...pass, item], fail] : [pass, [...fail, item]];\n },\n [[] as T[], [] as T[]]\n );\n}\n\n/**\n * Generates an array of numbers within a specified range.\n *\n * @param {number} start - Start of range (inclusive).\n * @param {number} end - End of range (exclusive).\n * @param {number} [step=1] - Step between numbers.\n * @returns {number[]} Array of numbers in range.\n */\nexport function range(start: number, end: number, step: number = 1): number[] {\n if (!Number.isFinite(start) || !Number.isFinite(end) || !Number.isFinite(step)) {\n throw new TypeError('Arguments must be finite numbers');\n }\n if (step === 0) throw new Error('Step cannot be zero');\n\n const isAscending = step > 0;\n if ((isAscending && start >= end) || (!isAscending && start <= end)) {\n return [];\n }\n\n const length = Math.max(Math.ceil((end - start) / step), 0);\n const result = new Array(length);\n\n for (let i = 0, value = start; i < length; i++, value += step) {\n result[i] = value;\n }\n\n return result;\n}\n\n/**\n * Returns the first n elements of an array.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {number} [n=1] - Number of elements to take.\n * @returns {T[]} New array with first n elements.\n */\nexport function take<T>(array: T[], n: number = 1): T[] {\n if (!Array.isArray(array) || n <= 0) return [];\n return array.slice(0, n);\n}\n\n/**\n * Takes elements from the array while predicate returns true.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T, index: number) => boolean} predicate - Function to test each element.\n * @returns {T[]} New array with taken elements.\n */\nexport function takeWhile<T>(array: T[], predicate: (item: T, index: number) => boolean): T[] {\n if (!Array.isArray(array)) return [];\n\n const result: T[] = [];\n for (let i = 0; i < array.length; i++) {\n if (!predicate(array[i], i)) break;\n result.push(array[i]);\n }\n\n return result;\n}\n\n/**\n * Removes all falsy values from an array.\n * False, null, 0, \"\", undefined, and NaN are falsy.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @returns {NonNullable<T>[]} New array with falsy values removed.\n */\nexport function compact<T>(array: T[]): NonNullable<T>[] {\n if (!Array.isArray(array)) return [];\n return array.filter(Boolean) as NonNullable<T>[];\n}\n\n/**\n * Counts array elements by a key function.\n *\n * @template T The type of array elements.\n * @param {T[]} array - The input array.\n * @param {(item: T) => string | number | symbol} keyFn - Function to generate count key.\n * @returns {Record<string, number>} Object with counts by key.\n */\nexport function countBy<T>(array: T[], keyFn: (item: T) => string | number | symbol): Record<string, number> {\n if (!Array.isArray(array)) return {};\n\n return array.reduce(\n (acc, item) => {\n const key = String(keyFn(item));\n acc[key] = (acc[key] || 0) + 1;\n return acc;\n },\n {} as Record<string, number>\n );\n}\n"]}
|
|
@@ -150,11 +150,7 @@ export declare function abortable<T>(promise: Promise<T>, signal: AbortSignal, a
|
|
|
150
150
|
* @returns {[Promise<T>, (value: T | PromiseLike<T>) => void, (reason?: any) => void]}
|
|
151
151
|
* Tuple of [promise, resolve, reject]
|
|
152
152
|
*/
|
|
153
|
-
export declare function createDeferred<T>(): [
|
|
154
|
-
Promise<T>,
|
|
155
|
-
(value: T | PromiseLike<T>) => void,
|
|
156
|
-
(reason?: any) => void
|
|
157
|
-
];
|
|
153
|
+
export declare function createDeferred<T>(): [Promise<T>, (value: T | PromiseLike<T>) => void, (reason?: any) => void];
|
|
158
154
|
/**
|
|
159
155
|
* Chains a series of async functions, passing the result of each to the next.
|
|
160
156
|
* Similar to function composition but for async functions.
|
|
@@ -22,7 +22,7 @@ exports.rateLimit = rateLimit;
|
|
|
22
22
|
* @returns {Promise<void>} A Promise that resolves after the given time.
|
|
23
23
|
*/
|
|
24
24
|
function sleep(ms) {
|
|
25
|
-
return new Promise(
|
|
25
|
+
return new Promise(resolve => setTimeout(resolve, ms));
|
|
26
26
|
}
|
|
27
27
|
/**
|
|
28
28
|
* Creates a debounced version of a function that delays its execution.
|
|
@@ -73,7 +73,7 @@ function debounce(fn, delay) {
|
|
|
73
73
|
*/
|
|
74
74
|
function throttle(fn, limit, opts = {
|
|
75
75
|
leading: true,
|
|
76
|
-
trailing: false
|
|
76
|
+
trailing: false
|
|
77
77
|
}) {
|
|
78
78
|
let lastCall = 0;
|
|
79
79
|
let timer = null;
|
|
@@ -130,7 +130,7 @@ async function retry(fn, retries = 3, delay = 500, backoff = false, onRetry) {
|
|
|
130
130
|
await sleep(backoff ? delay * Math.pow(2, i) : delay);
|
|
131
131
|
}
|
|
132
132
|
}
|
|
133
|
-
throw new Error(
|
|
133
|
+
throw new Error('Retry failed'); // should never reach here
|
|
134
134
|
}
|
|
135
135
|
/**
|
|
136
136
|
* Wraps a promise and rejects it if it doesn't resolve within the specified timeout.
|
|
@@ -141,15 +141,15 @@ async function retry(fn, retries = 3, delay = 500, backoff = false, onRetry) {
|
|
|
141
141
|
* @param {string} [message="Operation timed out"] - Optional timeout message.
|
|
142
142
|
* @returns {Promise<T>} A promise that resolves or rejects within the timeout.
|
|
143
143
|
*/
|
|
144
|
-
function withTimeout(promise, ms, message =
|
|
144
|
+
function withTimeout(promise, ms, message = 'Operation timed out') {
|
|
145
145
|
return new Promise((resolve, reject) => {
|
|
146
146
|
const timeoutHandle = setTimeout(() => reject(new Error(message)), ms);
|
|
147
147
|
promise
|
|
148
|
-
.then(
|
|
148
|
+
.then(result => {
|
|
149
149
|
clearTimeout(timeoutHandle);
|
|
150
150
|
resolve(result);
|
|
151
151
|
})
|
|
152
|
-
.catch(
|
|
152
|
+
.catch(err => {
|
|
153
153
|
clearTimeout(timeoutHandle);
|
|
154
154
|
reject(err);
|
|
155
155
|
});
|
|
@@ -170,7 +170,7 @@ async function runInBatches(tasks, limit) {
|
|
|
170
170
|
const results = [];
|
|
171
171
|
for (let i = 0; i < tasks.length; i += limit) {
|
|
172
172
|
const batch = tasks.slice(i, i + limit);
|
|
173
|
-
const batchResults = await Promise.all(batch.map(
|
|
173
|
+
const batchResults = await Promise.all(batch.map(fn => fn()));
|
|
174
174
|
results.push(...batchResults);
|
|
175
175
|
}
|
|
176
176
|
return results;
|
|
@@ -195,7 +195,7 @@ function singletonAsync(fn, drop = false) {
|
|
|
195
195
|
});
|
|
196
196
|
}
|
|
197
197
|
else if (drop) {
|
|
198
|
-
return Promise.reject(new Error(
|
|
198
|
+
return Promise.reject(new Error('Busy: function already running'));
|
|
199
199
|
}
|
|
200
200
|
return promise;
|
|
201
201
|
};
|
|
@@ -208,7 +208,7 @@ function singletonAsync(fn, drop = false) {
|
|
|
208
208
|
* @returns {Promise<PromiseSettledResult<T>[]>} Results including status and value/reason.
|
|
209
209
|
*/
|
|
210
210
|
async function settleAll(tasks) {
|
|
211
|
-
return Promise.allSettled(tasks.map(
|
|
211
|
+
return Promise.allSettled(tasks.map(task => task()));
|
|
212
212
|
}
|
|
213
213
|
/**
|
|
214
214
|
* A simple task queue that executes async tasks with a concurrency limit.
|
|
@@ -249,7 +249,7 @@ function createTaskQueue(limit) {
|
|
|
249
249
|
*/
|
|
250
250
|
get isPaused() {
|
|
251
251
|
return paused;
|
|
252
|
-
}
|
|
252
|
+
}
|
|
253
253
|
};
|
|
254
254
|
const next = () => {
|
|
255
255
|
if (paused || queue.length === 0 || activeCount >= limit)
|
|
@@ -284,11 +284,11 @@ function createTaskQueue(limit) {
|
|
|
284
284
|
};
|
|
285
285
|
enqueue.pause = state.pause;
|
|
286
286
|
enqueue.resume = state.resume;
|
|
287
|
-
Object.defineProperty(enqueue,
|
|
288
|
-
get: () => queue.length
|
|
287
|
+
Object.defineProperty(enqueue, 'length', {
|
|
288
|
+
get: () => queue.length
|
|
289
289
|
});
|
|
290
|
-
Object.defineProperty(enqueue,
|
|
291
|
-
get: () => paused
|
|
290
|
+
Object.defineProperty(enqueue, 'isPaused', {
|
|
291
|
+
get: () => paused
|
|
292
292
|
});
|
|
293
293
|
return enqueue;
|
|
294
294
|
}
|
|
@@ -331,7 +331,7 @@ function memoizeAsync(fn, options = {}) {
|
|
|
331
331
|
const result = await fn(...args);
|
|
332
332
|
cache.set(key, {
|
|
333
333
|
value: result,
|
|
334
|
-
expires: ttl ? Date.now() + ttl : Infinity
|
|
334
|
+
expires: ttl ? Date.now() + ttl : Infinity
|
|
335
335
|
});
|
|
336
336
|
return result;
|
|
337
337
|
};
|
|
@@ -345,7 +345,7 @@ function memoizeAsync(fn, options = {}) {
|
|
|
345
345
|
* @param {any} [abortValue] - Value to use when rejecting on abort
|
|
346
346
|
* @returns {Promise<T>} Promise that rejects if the signal is aborted
|
|
347
347
|
*/
|
|
348
|
-
function abortable(promise, signal, abortValue = new Error(
|
|
348
|
+
function abortable(promise, signal, abortValue = new Error('Operation aborted')) {
|
|
349
349
|
if (signal.aborted) {
|
|
350
350
|
return Promise.reject(abortValue);
|
|
351
351
|
}
|
|
@@ -353,9 +353,9 @@ function abortable(promise, signal, abortValue = new Error("Operation aborted"))
|
|
|
353
353
|
promise,
|
|
354
354
|
new Promise((_, reject) => {
|
|
355
355
|
const abort = () => reject(abortValue);
|
|
356
|
-
signal.addEventListener(
|
|
357
|
-
promise.finally(() => signal.removeEventListener(
|
|
358
|
-
})
|
|
356
|
+
signal.addEventListener('abort', abort, { once: true });
|
|
357
|
+
promise.finally(() => signal.removeEventListener('abort', abort));
|
|
358
|
+
})
|
|
359
359
|
]);
|
|
360
360
|
}
|
|
361
361
|
/**
|
|
@@ -402,19 +402,19 @@ function rateLimit(fn, maxCalls, interval) {
|
|
|
402
402
|
const calls = [];
|
|
403
403
|
return async function (...args) {
|
|
404
404
|
const now = Date.now();
|
|
405
|
-
calls.splice(0, calls.length, ...calls.filter(
|
|
405
|
+
calls.splice(0, calls.length, ...calls.filter(time => now - time < interval));
|
|
406
406
|
if (calls.length >= maxCalls) {
|
|
407
407
|
const oldestCall = calls[0];
|
|
408
408
|
const delay = interval - (now - oldestCall);
|
|
409
409
|
await sleep(Math.max(1, delay));
|
|
410
410
|
// Remove potentially stale entries after sleep
|
|
411
411
|
const currentTime = Date.now();
|
|
412
|
-
calls.splice(0, calls.length, ...calls.filter(
|
|
412
|
+
calls.splice(0, calls.length, ...calls.filter(time => currentTime - time < interval));
|
|
413
413
|
// If still at limit after sleep, wait for another cycle
|
|
414
414
|
if (calls.length >= maxCalls) {
|
|
415
415
|
const nextDelay = interval - (currentTime - calls[0]);
|
|
416
416
|
await sleep(Math.max(1, nextDelay));
|
|
417
|
-
calls.splice(0, calls.length, ...calls.filter(
|
|
417
|
+
calls.splice(0, calls.length, ...calls.filter(time => Date.now() - time < interval));
|
|
418
418
|
}
|
|
419
419
|
}
|
|
420
420
|
calls.push(Date.now());
|