@simplysm/core-common 13.0.16 → 13.0.18

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 CHANGED
@@ -1,7 +1,6 @@
1
1
  # @simplysm/core-common
2
2
 
3
- A common utility package for the Simplysm framework.
4
- As a neutral base module usable in both Node.js and browser environments, it provides date/time types, error classes, object/array/string utilities, JSON serialization, ZIP processing, prototype extensions, and more.
3
+ A common utility package for the Simplysm framework. As a neutral base module usable in both Node.js and browser environments, it provides date/time types, error classes, object/array/string utilities, JSON serialization, ZIP processing, prototype extensions, and more.
5
4
 
6
5
  ## Installation
7
6
 
@@ -11,7 +10,7 @@ npm install @simplysm/core-common
11
10
  pnpm add @simplysm/core-common
12
11
  ```
13
12
 
14
- ## Initialization
13
+ ### Initialization
15
14
 
16
15
  Import the package at your application entry point (e.g., `index.ts`, `main.ts`):
17
16
 
@@ -22,61 +21,16 @@ import "@simplysm/core-common";
22
21
  This import globally activates Array, Map, and Set prototype extensions.
23
22
  To use extension methods (`getOrCreate()`, `toggle()`, etc.), you must import this at app startup.
24
23
 
25
- ## Caveats
26
-
27
- ### Prototype Extension Conflicts
28
-
29
- This package extends Array, Map, and Set prototypes.
30
- Conflicts may occur when used with other libraries that extend the same method names.
31
- In case of conflict, the last defined implementation is applied based on load order.
32
-
33
- ### Timezone Handling
34
-
35
- When using `DateOnly.parse()`, `DateTime.parse()`:
36
- - `yyyy-MM-dd`, `yyyyMMdd` format: parse directly from string (no timezone influence)
37
- - ISO 8601 format (`2024-01-15T00:00:00Z`): interpret as UTC then convert to local
38
-
39
- When server and client timezones differ, actively use `yyyy-MM-dd` format.
40
-
41
- ### Memory Management (LazyGcMap)
42
-
43
- `LazyGcMap` has an internal GC timer, so it must be cleaned up.
44
-
45
- ```typescript
46
- // using statement (recommended)
47
- // gcInterval: GC execution interval (ms), expireTime: item expiration time (ms)
48
- using map = new LazyGcMap({ gcInterval: 10000, expireTime: 60000 }); // GC every 10 seconds, expire after 60 seconds
49
-
50
- // Or explicit dispose() call
51
- const map = new LazyGcMap({ gcInterval: 10000, expireTime: 60000 }); // GC every 10 seconds, expire after 60 seconds
52
- try {
53
- // ... use
54
- } finally {
55
- map.dispose();
56
- }
57
- ```
58
-
59
- ### jsonStringify's __type__ Reserved Word
60
-
61
- `jsonStringify`/`jsonParse` uses objects with `__type__` and `data` keys for type restoration.
62
- Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may be unintentionally type-converted.
63
-
64
- ### Circular References
65
-
66
- - `objClone`: supports circular references (tracked with WeakMap)
67
- - `jsonStringify`: throws TypeError on circular reference
68
- - `transferableEncode`: throws TypeError on circular reference (includes path information)
24
+ ## Main Modules
69
25
 
70
- ---
71
-
72
- ## Errors
26
+ ### Errors
73
27
 
74
28
  - [`SdError`](docs/types.md#sderror) - Base error class with cause chain tracking
75
29
  - [`ArgumentError`](docs/types.md#argumenterror) - Argument validation error with YAML formatting
76
30
  - [`NotImplementedError`](docs/types.md#notimplementederror) - Indicates unimplemented functionality
77
31
  - [`TimeoutError`](docs/types.md#timeouterror) - Timeout error
78
32
 
79
- ## Custom Types
33
+ ### Custom Types
80
34
 
81
35
  - [`DateTime`](docs/types.md#datetime) - Date + time (millisecond precision, local timezone)
82
36
  - [`DateOnly`](docs/types.md#dateonly) - Date only (no time)
@@ -84,14 +38,14 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
84
38
  - [`Uuid`](docs/types.md#uuid) - UUID v4 (cryptographically secure)
85
39
  - [`LazyGcMap`](docs/types.md#lazygcmap) - Map with auto-expiration (LRU style)
86
40
 
87
- ## Features
41
+ ### Features
88
42
 
89
43
  - [`DebounceQueue`](docs/features.md#debouncequeue) - Async debounce queue (executes only last request)
90
44
  - [`SerialQueue`](docs/features.md#serialqueue) - Async serial queue (sequential execution)
91
45
  - [`EventEmitter`](docs/features.md#eventemitter) - EventTarget wrapper with type-safe events
92
46
  - [`ZipArchive`](docs/features.md#ziparchive) - ZIP file compression/decompression utility
93
47
 
94
- ## Object Utilities
48
+ ### Object Utilities
95
49
 
96
50
  - [`objClone`](docs/utils.md#objclone) - Deep clone (supports circular references, custom types)
97
51
  - [`objEqual`](docs/utils.md#objequal) - Deep comparison with options
@@ -107,17 +61,17 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
107
61
  - [`objFromEntries`](docs/utils.md#objfromentries) - Type-safe `Object.fromEntries`
108
62
  - [`objMap`](docs/utils.md#objmap) - Transform each entry of object
109
63
 
110
- ## JSON Utilities
64
+ ### JSON Utilities
111
65
 
112
66
  - [`jsonStringify`](docs/utils.md#jsonstringify) - JSON serialization with custom type support
113
67
  - [`jsonParse`](docs/utils.md#jsonparse) - JSON deserialization with custom type restoration
114
68
 
115
- ## XML Utilities
69
+ ### XML Utilities
116
70
 
117
71
  - [`xmlParse`](docs/utils.md#xmlparse) - Parse XML string to object
118
72
  - [`xmlStringify`](docs/utils.md#xmlstringify) - Serialize object to XML string
119
73
 
120
- ## String Utilities
74
+ ### String Utilities
121
75
 
122
76
  - [`strGetSuffix`](docs/utils.md#strgetsuffix) - Korean postposition handling
123
77
  - [`strReplaceFullWidth`](docs/utils.md#strreplacefullwidth) - Convert full-width to half-width
@@ -128,7 +82,7 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
128
82
  - [`strIsNullOrEmpty`](docs/utils.md#strisnullorempty) - Check for undefined/null/empty (type guard)
129
83
  - [`strInsert`](docs/utils.md#strinsert) - Insert at position in string
130
84
 
131
- ## Number Utilities
85
+ ### Number Utilities
132
86
 
133
87
  - [`numParseInt`](docs/utils.md#numparseint) - Parse string to integer
134
88
  - [`numParseFloat`](docs/utils.md#numparsefloat) - Parse string to float
@@ -136,12 +90,12 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
136
90
  - [`numFormat`](docs/utils.md#numformat) - Thousands separator formatting
137
91
  - [`numIsNullOrEmpty`](docs/utils.md#numisnullorempty) - Check for undefined/null/0 (type guard)
138
92
 
139
- ## Date/Time Formatting
93
+ ### Date/Time Formatting
140
94
 
141
95
  - [`formatDate`](docs/utils.md#formatdate) - Convert date/time to formatted string
142
96
  - [`normalizeMonth`](docs/utils.md#normalizemonth) - Normalize year/month/day when setting month
143
97
 
144
- ## Byte Utilities
98
+ ### Byte Utilities
145
99
 
146
100
  - [`bytesConcat`](docs/utils.md#bytesconcat) - Concatenate multiple Uint8Arrays
147
101
  - [`bytesToHex`](docs/utils.md#bytestohex) - Convert Uint8Array to hex string
@@ -149,23 +103,23 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
149
103
  - [`bytesToBase64`](docs/utils.md#bytestobase64) - Convert Uint8Array to base64 string
150
104
  - [`bytesFromBase64`](docs/utils.md#bytesfrombase64) - Convert base64 string to Uint8Array
151
105
 
152
- ## Async Wait
106
+ ### Async Wait
153
107
 
154
108
  - [`waitTime`](docs/utils.md#waittime) - Wait for specified time
155
109
  - [`waitUntil`](docs/utils.md#waituntil) - Wait until condition is true
156
110
 
157
- ## Worker Data Conversion
111
+ ### Worker Data Conversion
158
112
 
159
113
  - [`transferableEncode`](docs/utils.md#transferableencode) - Serialize custom types for Worker transfer
160
114
  - [`transferableDecode`](docs/utils.md#transferabledecode) - Deserialize Worker data to custom types
161
115
 
162
- ## Path Utilities
116
+ ### Path Utilities
163
117
 
164
118
  - [`pathJoin`](docs/utils.md#pathjoin) - Combine paths (POSIX-style only)
165
119
  - [`pathBasename`](docs/utils.md#pathbasename) - Extract filename
166
120
  - [`pathExtname`](docs/utils.md#pathextname) - Extract extension
167
121
 
168
- ## Template Literal Tags
122
+ ### Template Literal Tags
169
123
 
170
124
  - [`js`](docs/utils.md#js) - JavaScript code highlighting
171
125
  - [`ts`](docs/utils.md#ts) - TypeScript code highlighting
@@ -174,44 +128,30 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
174
128
  - [`mysql`](docs/utils.md#mysql) - MySQL SQL highlighting
175
129
  - [`pgsql`](docs/utils.md#pgsql) - PostgreSQL SQL highlighting
176
130
 
177
- ## Other Utilities
131
+ ### Other Utilities
178
132
 
179
133
  - [`getPrimitiveTypeStr`](docs/utils.md#getprimitivetypestr) - Infer `PrimitiveTypeStr` from runtime value
180
134
  - [`env`](docs/utils.md#env) - Environment variable object
181
135
 
182
- ## Type Utilities
183
-
184
- - [`Bytes`](docs/types.md#bytes) - Alias for `Uint8Array`
185
- - [`PrimitiveTypeStr`](docs/types.md#primitivetypestr) - Primitive type string keys
186
- - [`PrimitiveTypeMap`](docs/types.md#primitivetypemap) - Mapping from type string to type
187
- - [`PrimitiveType`](docs/types.md#primitivetype) - Union of all primitive types
188
- - [`DeepPartial`](docs/types.md#deeppartial) - Recursively convert properties to optional
189
- - [`Type`](docs/types.md#type) - Constructor type
190
- - [`ObjUndefToOptional`](docs/types.md#objundeftooptional) - Convert `undefined` properties to optional
191
- - [`ObjOptionalToUndef`](docs/types.md#objoptionaltoundef) - Convert optional properties to `required + undefined`
192
- - [`ArrayDiffsResult`](docs/types.md#arraydiffsresult) - Result type of `Array.diffs()`
193
- - [`ArrayDiffs2Result`](docs/types.md#arraydiffs2result) - Result type of `Array.oneWayDiffs()`
194
- - [`TreeArray`](docs/types.md#treearray) - Result type of `Array.toTree()`
195
-
196
- ## Array Extensions
136
+ ### Array Extensions
197
137
 
198
- ### Query
138
+ #### Query
199
139
  - [`single`](docs/extensions.md#single) - Return single element (error if 2+)
200
140
  - [`first`](docs/extensions.md#first) - Return first element
201
141
  - [`last`](docs/extensions.md#last) - Return last element
202
142
 
203
- ### Filtering
143
+ #### Filtering
204
144
  - [`filterExists`](docs/extensions.md#filterexists) - Remove `null`/`undefined`
205
145
  - [`ofType`](docs/extensions.md#oftype) - Filter by type
206
146
  - [`filterAsync`](docs/extensions.md#filterasync) - Async filter
207
147
 
208
- ### Mapping/Transformation
148
+ #### Mapping/Transformation
209
149
  - [`mapAsync`](docs/extensions.md#mapasync) - Async mapping (sequential)
210
150
  - [`mapMany`](docs/extensions.md#mapmany) - flat + filterExists
211
151
  - [`mapManyAsync`](docs/extensions.md#mapmanyasync) - Async mapMany
212
152
  - [`parallelAsync`](docs/extensions.md#parallelasync) - Parallel async mapping
213
153
 
214
- ### Grouping
154
+ #### Grouping
215
155
  - [`groupBy`](docs/extensions.md#groupby) - Group by key
216
156
  - [`toMap`](docs/extensions.md#tomap) - Convert to Map
217
157
  - [`toMapAsync`](docs/extensions.md#tomapasync) - Async Map conversion
@@ -221,43 +161,102 @@ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may
221
161
  - [`toObject`](docs/extensions.md#toobject) - Convert to `Record<string, V>`
222
162
  - [`toTree`](docs/extensions.md#totree) - Convert to tree structure
223
163
 
224
- ### Deduplication
164
+ #### Deduplication
225
165
  - [`distinct`](docs/extensions.md#distinct) - Remove duplicates (new array)
226
166
  - [`distinctThis`](docs/extensions.md#distinctthis) - Remove duplicates (modify original)
227
167
 
228
- ### Sorting
168
+ #### Sorting
229
169
  - [`orderBy`](docs/extensions.md#orderby) - Ascending sort (new array)
230
170
  - [`orderByDesc`](docs/extensions.md#orderbydesc) - Descending sort (new array)
231
171
  - [`orderByThis`](docs/extensions.md#orderbythis) - Ascending sort (modify original)
232
172
  - [`orderByDescThis`](docs/extensions.md#orderbydescthis) - Descending sort (modify original)
233
173
 
234
- ### Comparison/Merging
174
+ #### Comparison/Merging
235
175
  - [`diffs`](docs/extensions.md#diffs) - Compare differences between arrays
236
176
  - [`oneWayDiffs`](docs/extensions.md#onewaydiffs) - One-way diff comparison
237
177
  - [`merge`](docs/extensions.md#merge) - Merge arrays
238
178
 
239
- ### Aggregation
179
+ #### Aggregation
240
180
  - [`sum`](docs/extensions.md#sum) - Sum
241
181
  - [`min`](docs/extensions.md#min) - Minimum
242
182
  - [`max`](docs/extensions.md#max) - Maximum
243
183
 
244
- ### Mutation
184
+ #### Mutation
245
185
  - [`insert`](docs/extensions.md#insert) - Insert at specific position
246
186
  - [`remove`](docs/extensions.md#remove) - Remove item
247
187
  - [`toggle`](docs/extensions.md#toggle) - Toggle item
248
188
  - [`clear`](docs/extensions.md#clear) - Remove all items
249
189
  - [`shuffle`](docs/extensions.md#shuffle) - Shuffle array
250
190
 
251
- ## Map Extensions
191
+ ### Map Extensions
252
192
 
253
193
  - [`getOrCreate`](docs/extensions.md#getorcreate) - Get or create and return value
254
194
  - [`update`](docs/extensions.md#update) - Update value using function
255
195
 
256
- ## Set Extensions
196
+ ### Set Extensions
257
197
 
258
198
  - [`adds`](docs/extensions.md#adds) - Add multiple values at once
259
199
  - [`toggle`](docs/extensions.md#toggle-1) - Toggle value (add/remove)
260
200
 
201
+ ## Types
202
+
203
+ - [`Bytes`](docs/types.md#bytes) - Alias for `Uint8Array`
204
+ - [`PrimitiveTypeStr`](docs/types.md#primitivetypestr) - Primitive type string keys
205
+ - [`PrimitiveTypeMap`](docs/types.md#primitivetypemap) - Mapping from type string to type
206
+ - [`PrimitiveType`](docs/types.md#primitivetype) - Union of all primitive types
207
+ - [`DeepPartial`](docs/types.md#deeppartial) - Recursively convert properties to optional
208
+ - [`Type`](docs/types.md#type) - Constructor type
209
+ - [`ObjUndefToOptional`](docs/types.md#objundeftooptional) - Convert `undefined` properties to optional
210
+ - [`ObjOptionalToUndef`](docs/types.md#objoptionaltoundef) - Convert optional properties to `required + undefined`
211
+ - [`ArrayDiffsResult`](docs/types.md#arraydiffsresult) - Result type of `Array.diffs()`
212
+ - [`ArrayDiffs2Result`](docs/types.md#arraydiffs2result) - Result type of `Array.oneWayDiffs()`
213
+ - [`TreeArray`](docs/types.md#treearray) - Result type of `Array.toTree()`
214
+
215
+ ## Caveats
216
+
217
+ ### Prototype Extension Conflicts
218
+
219
+ This package extends Array, Map, and Set prototypes.
220
+ Conflicts may occur when used with other libraries that extend the same method names.
221
+ In case of conflict, the last defined implementation is applied based on load order.
222
+
223
+ ### Timezone Handling
224
+
225
+ When using `DateOnly.parse()`, `DateTime.parse()`:
226
+ - `yyyy-MM-dd`, `yyyyMMdd` format: parse directly from string (no timezone influence)
227
+ - ISO 8601 format (`2024-01-15T00:00:00Z`): interpret as UTC then convert to local
228
+
229
+ When server and client timezones differ, actively use `yyyy-MM-dd` format.
230
+
231
+ ### Memory Management (LazyGcMap)
232
+
233
+ `LazyGcMap` has an internal GC timer, so it must be cleaned up.
234
+
235
+ ```typescript
236
+ // using statement (recommended)
237
+ // gcInterval: GC execution interval (ms), expireTime: item expiration time (ms)
238
+ using map = new LazyGcMap({ gcInterval: 10000, expireTime: 60000 }); // GC every 10 seconds, expire after 60 seconds
239
+
240
+ // Or explicit dispose() call
241
+ const map = new LazyGcMap({ gcInterval: 10000, expireTime: 60000 }); // GC every 10 seconds, expire after 60 seconds
242
+ try {
243
+ // ... use
244
+ } finally {
245
+ map.dispose();
246
+ }
247
+ ```
248
+
249
+ ### jsonStringify's __type__ Reserved Word
250
+
251
+ `jsonStringify`/`jsonParse` uses objects with `__type__` and `data` keys for type restoration.
252
+ Be careful as user data in the form `{ __type__: "DateTime", data: "..." }` may be unintentionally type-converted.
253
+
254
+ ### Circular References
255
+
256
+ - `objClone`: supports circular references (tracked with WeakMap)
257
+ - `jsonStringify`: throws TypeError on circular reference
258
+ - `transferableEncode`: throws TypeError on circular reference (includes path information)
259
+
261
260
  ## License
262
261
 
263
262
  Apache-2.0
@@ -51,8 +51,8 @@ export type PrimitiveType = PrimitiveTypeMap[PrimitiveTypeStr] | undefined;
51
51
  * };
52
52
  * ```
53
53
  */
54
- export type DeepPartial<T> = Partial<{
55
- [K in keyof T]: T[K] extends PrimitiveType ? T[K] : DeepPartial<T[K]>;
54
+ export type DeepPartial<TObject> = Partial<{
55
+ [K in keyof TObject]: TObject[K] extends PrimitiveType ? TObject[K] : DeepPartial<TObject[K]>;
56
56
  }>;
57
57
  /**
58
58
  * 생성자 타입
@@ -68,7 +68,7 @@ export type DeepPartial<T> = Partial<{
68
68
  * class MyClass { name = "test"; }
69
69
  * const instance = create(MyClass); // MyClass 인스턴스
70
70
  */
71
- export interface Type<T> extends Function {
72
- new (...args: unknown[]): T;
71
+ export interface Type<TInstance> extends Function {
72
+ new (...args: unknown[]): TInstance;
73
73
  }
74
74
  //# sourceMappingURL=common.types.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"common.types.d.ts","sourceRoot":"","sources":["../src/common.types.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7C,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7C,OAAO,EAAE,IAAI,EAAE,MAAM,cAAc,CAAC;AACpC,OAAO,EAAE,IAAI,EAAE,MAAM,cAAc,CAAC;AAIpC;;GAEG;AACH,MAAM,MAAM,KAAK,GAAG,UAAU,CAAC;AAM/B;;;GAGG;AACH,MAAM,MAAM,gBAAgB,GAAG;IAC7B,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,OAAO,CAAC;IACjB,QAAQ,EAAE,QAAQ,CAAC;IACnB,QAAQ,EAAE,QAAQ,CAAC;IACnB,IAAI,EAAE,IAAI,CAAC;IACX,IAAI,EAAE,IAAI,CAAC;IACX,KAAK,EAAE,KAAK,CAAC;CACd,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,gBAAgB,GAAG,MAAM,gBAAgB,CAAC;AAEtD;;GAEG;AACH,MAAM,MAAM,aAAa,GAAG,gBAAgB,CAAC,gBAAgB,CAAC,GAAG,SAAS,CAAC;AAM3E;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,MAAM,MAAM,WAAW,CAAC,CAAC,IAAI,OAAO,CAAC;KAClC,CAAC,IAAI,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,SAAS,aAAa,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,WAAW,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;CACtE,CAAC,CAAC;AAEH;;;;;;;;;;;;;GAaG;AACH,MAAM,WAAW,IAAI,CAAC,CAAC,CAAE,SAAQ,QAAQ;IACvC,KAAK,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,CAAC,CAAC;CAC7B"}
1
+ {"version":3,"file":"common.types.d.ts","sourceRoot":"","sources":["../src/common.types.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7C,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAC7C,OAAO,EAAE,IAAI,EAAE,MAAM,cAAc,CAAC;AACpC,OAAO,EAAE,IAAI,EAAE,MAAM,cAAc,CAAC;AAIpC;;GAEG;AACH,MAAM,MAAM,KAAK,GAAG,UAAU,CAAC;AAM/B;;;GAGG;AACH,MAAM,MAAM,gBAAgB,GAAG;IAC7B,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,OAAO,CAAC;IACjB,QAAQ,EAAE,QAAQ,CAAC;IACnB,QAAQ,EAAE,QAAQ,CAAC;IACnB,IAAI,EAAE,IAAI,CAAC;IACX,IAAI,EAAE,IAAI,CAAC;IACX,KAAK,EAAE,KAAK,CAAC;CACd,CAAC;AAEF;;GAEG;AACH,MAAM,MAAM,gBAAgB,GAAG,MAAM,gBAAgB,CAAC;AAEtD;;GAEG;AACH,MAAM,MAAM,aAAa,GAAG,gBAAgB,CAAC,gBAAgB,CAAC,GAAG,SAAS,CAAC;AAM3E;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,MAAM,MAAM,WAAW,CAAC,OAAO,IAAI,OAAO,CAAC;KACxC,CAAC,IAAI,MAAM,OAAO,GAAG,OAAO,CAAC,CAAC,CAAC,SAAS,aAAa,GAAG,OAAO,CAAC,CAAC,CAAC,GAAG,WAAW,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;CAC9F,CAAC,CAAC;AAEH;;;;;;;;;;;;;GAaG;AACH,MAAM,WAAW,IAAI,CAAC,SAAS,CAAE,SAAQ,QAAQ;IAC/C,KAAK,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,SAAS,CAAC;CACrC"}
@@ -5,54 +5,54 @@ import type { PrimitiveTypeMap, PrimitiveTypeStr, Type } from "../common.types";
5
5
  import type { DateTime } from "../types/date-time";
6
6
  import type { DateOnly } from "../types/date-only";
7
7
  import type { Time } from "../types/time";
8
- export interface ReadonlyArrayExt<T> {
8
+ export interface ReadonlyArrayExt<TItem> {
9
9
  /**
10
10
  * 조건에 맞는 단일 요소 반환
11
11
  * @param predicate 필터 조건 (생략 시 배열 전체 대상)
12
12
  * @returns 요소가 없으면 undefined
13
13
  * @throws ArgumentError 조건에 맞는 요소가 2개 이상이면 발생
14
14
  */
15
- single(predicate?: (item: T, index: number) => boolean): T | undefined;
15
+ single(predicate?: (item: TItem, index: number) => boolean): TItem | undefined;
16
16
  /**
17
17
  * 첫 번째 요소 반환
18
18
  * @param predicate 필터 조건 (생략 시 첫 번째 요소 반환)
19
19
  * @returns 요소가 없으면 undefined
20
20
  */
21
- first(predicate?: (item: T, index: number) => boolean): T | undefined;
21
+ first(predicate?: (item: TItem, index: number) => boolean): TItem | undefined;
22
22
  /** 비동기 필터 (순차 실행) */
23
- filterAsync(predicate: (item: T, index: number) => Promise<boolean>): Promise<T[]>;
23
+ filterAsync(predicate: (item: TItem, index: number) => Promise<boolean>): Promise<TItem[]>;
24
24
  /**
25
25
  * 마지막 요소 반환
26
26
  * @param predicate 필터 조건 (생략 시 마지막 요소 반환)
27
27
  * @returns 요소가 없으면 undefined
28
28
  */
29
- last(predicate?: (item: T, index: number) => boolean): T | undefined;
29
+ last(predicate?: (item: TItem, index: number) => boolean): TItem | undefined;
30
30
  /** null/undefined 제거 */
31
- filterExists(): NonNullable<T>[];
31
+ filterExists(): NonNullable<TItem>[];
32
32
  /** 특정 타입의 요소만 필터링 (PrimitiveTypeStr 또는 생성자 타입) */
33
- ofType<K extends PrimitiveTypeStr>(type: K): Extract<T, PrimitiveTypeMap[K]>[];
34
- ofType<N extends T>(type: Type<N>): N[];
33
+ ofType<K extends PrimitiveTypeStr>(type: K): Extract<TItem, PrimitiveTypeMap[K]>[];
34
+ ofType<N extends TItem>(type: Type<N>): N[];
35
35
  /** 비동기 매핑 (순차 실행) */
36
- mapAsync<R>(selector: (item: T, index: number) => Promise<R>): Promise<R[]>;
36
+ mapAsync<R>(selector: (item: TItem, index: number) => Promise<R>): Promise<R[]>;
37
37
  /** 중첩 배열 평탄화 */
38
- mapMany(): T extends readonly (infer U)[] ? U[] : T;
38
+ mapMany(): TItem extends readonly (infer U)[] ? U[] : TItem;
39
39
  /** 매핑 후 평탄화 */
40
- mapMany<R>(selector: (item: T, index: number) => R[]): R[];
40
+ mapMany<R>(selector: (item: TItem, index: number) => R[]): R[];
41
41
  /** 비동기 매핑 후 평탄화 (순차 실행) */
42
- mapManyAsync<R>(selector: (item: T, index: number) => Promise<R[]>): Promise<R[]>;
42
+ mapManyAsync<R>(selector: (item: TItem, index: number) => Promise<R[]>): Promise<R[]>;
43
43
  /**
44
44
  * 비동기 병렬 처리 (Promise.all 사용)
45
45
  * @note 하나라도 reject되면 전체가 fail-fast로 reject됨 (Promise.all 동작)
46
46
  */
47
- parallelAsync<R>(fn: (item: T, index: number) => Promise<R>): Promise<R[]>;
47
+ parallelAsync<R>(fn: (item: TItem, index: number) => Promise<R>): Promise<R[]>;
48
48
  /**
49
49
  * 키 기준 그룹화
50
50
  * @param keySelector 그룹 키 선택 함수
51
51
  * @note O(n²) 복잡도 (객체 키 지원을 위해 깊은 비교 사용). primitive 키만 필요하면 toArrayMap()이 O(n)으로 더 효율적
52
52
  */
53
- groupBy<K>(keySelector: (item: T, index: number) => K): {
53
+ groupBy<K>(keySelector: (item: TItem, index: number) => K): {
54
54
  key: K;
55
- values: T[];
55
+ values: TItem[];
56
56
  }[];
57
57
  /**
58
58
  * 키 기준 그룹화 (값 변환 포함)
@@ -60,21 +60,21 @@ export interface ReadonlyArrayExt<T> {
60
60
  * @param valueSelector 값 변환 함수
61
61
  * @note O(n²) 복잡도 (객체 키 지원을 위해 깊은 비교 사용). primitive 키만 필요하면 toArrayMap()이 O(n)으로 더 효율적
62
62
  */
63
- groupBy<K, V>(keySelector: (item: T, index: number) => K, valueSelector: (item: T, index: number) => V): {
63
+ groupBy<K, V>(keySelector: (item: TItem, index: number) => K, valueSelector: (item: TItem, index: number) => V): {
64
64
  key: K;
65
65
  values: V[];
66
66
  }[];
67
- toMap<K>(keySelector: (item: T, index: number) => K): Map<K, T>;
68
- toMap<K, V>(keySelector: (item: T, index: number) => K, valueSelector: (item: T, index: number) => V): Map<K, V>;
69
- toMapAsync<K>(keySelector: (item: T, index: number) => Promise<K>): Promise<Map<K, T>>;
70
- toMapAsync<K, V>(keySelector: (item: T, index: number) => Promise<K> | K, valueSelector: (item: T, index: number) => Promise<V> | V): Promise<Map<K, V>>;
71
- toArrayMap<K>(keySelector: (item: T, index: number) => K): Map<K, T[]>;
72
- toArrayMap<K, V>(keySelector: (item: T, index: number) => K, valueSelector: (item: T, index: number) => V): Map<K, V[]>;
73
- toSetMap<K>(keySelector: (item: T, index: number) => K): Map<K, Set<T>>;
74
- toSetMap<K, V>(keySelector: (item: T, index: number) => K, valueSelector: (item: T, index: number) => V): Map<K, Set<V>>;
75
- toMapValues<K, V>(keySelector: (item: T, index: number) => K, valueSelector: (items: T[]) => V): Map<K, V>;
76
- toObject(keySelector: (item: T, index: number) => string): Record<string, T>;
77
- toObject<V>(keySelector: (item: T, index: number) => string, valueSelector: (item: T, index: number) => V): Record<string, V>;
67
+ toMap<K>(keySelector: (item: TItem, index: number) => K): Map<K, TItem>;
68
+ toMap<K, V>(keySelector: (item: TItem, index: number) => K, valueSelector: (item: TItem, index: number) => V): Map<K, V>;
69
+ toMapAsync<K>(keySelector: (item: TItem, index: number) => Promise<K>): Promise<Map<K, TItem>>;
70
+ toMapAsync<K, V>(keySelector: (item: TItem, index: number) => Promise<K> | K, valueSelector: (item: TItem, index: number) => Promise<V> | V): Promise<Map<K, V>>;
71
+ toArrayMap<K>(keySelector: (item: TItem, index: number) => K): Map<K, TItem[]>;
72
+ toArrayMap<K, V>(keySelector: (item: TItem, index: number) => K, valueSelector: (item: TItem, index: number) => V): Map<K, V[]>;
73
+ toSetMap<K>(keySelector: (item: TItem, index: number) => K): Map<K, Set<TItem>>;
74
+ toSetMap<K, V>(keySelector: (item: TItem, index: number) => K, valueSelector: (item: TItem, index: number) => V): Map<K, Set<V>>;
75
+ toMapValues<K, V>(keySelector: (item: TItem, index: number) => K, valueSelector: (items: TItem[]) => V): Map<K, V>;
76
+ toObject(keySelector: (item: TItem, index: number) => string): Record<string, TItem>;
77
+ toObject<V>(keySelector: (item: TItem, index: number) => string, valueSelector: (item: TItem, index: number) => V): Record<string, V>;
78
78
  /**
79
79
  * 평탄한 배열을 트리 구조로 변환한다
80
80
  *
@@ -111,7 +111,7 @@ export interface ReadonlyArrayExt<T> {
111
111
  * // ]}]
112
112
  * ```
113
113
  */
114
- toTree<K extends keyof T, P extends keyof T>(keyProp: K, parentKey: P): TreeArray<T>[];
114
+ toTree<K extends keyof TItem, P extends keyof TItem>(keyProp: K, parentKey: P): TreeArray<TItem>[];
115
115
  /**
116
116
  * 중복 제거
117
117
  * @param options matchAddress: 주소 비교 (true면 Set 사용), keyFn: 커스텀 키 함수 (O(n) 성능)
@@ -119,46 +119,46 @@ export interface ReadonlyArrayExt<T> {
119
119
  */
120
120
  distinct(options?: boolean | {
121
121
  matchAddress?: boolean;
122
- keyFn?: (item: T) => string | number;
123
- }): T[];
124
- orderBy(selector?: (item: T) => string | number | DateOnly | DateTime | Time | undefined): T[];
125
- orderByDesc(selector?: (item: T) => string | number | DateOnly | DateTime | Time | undefined): T[];
122
+ keyFn?: (item: TItem) => string | number;
123
+ }): TItem[];
124
+ orderBy(selector?: (item: TItem) => string | number | DateOnly | DateTime | Time | undefined): TItem[];
125
+ orderByDesc(selector?: (item: TItem) => string | number | DateOnly | DateTime | Time | undefined): TItem[];
126
126
  /**
127
127
  * 두 배열 비교 (INSERT/DELETE/UPDATE)
128
128
  * @param target 비교 대상 배열
129
129
  * @param options keys: 키 비교용, excludes: 비교 제외 속성
130
130
  * @note target에 중복 키가 있으면 첫 번째 매칭만 사용됨
131
131
  */
132
- diffs<P>(target: P[], options?: {
132
+ diffs<TOtherItem>(target: TOtherItem[], options?: {
133
133
  keys?: string[];
134
134
  excludes?: string[];
135
- }): ArrayDiffsResult<T, P>[];
136
- oneWayDiffs<K extends keyof T>(orgItems: T[] | Map<T[K], T>, keyPropNameOrFn: K | ((item: T) => K), options?: {
135
+ }): ArrayDiffsResult<TItem, TOtherItem>[];
136
+ oneWayDiffs<K extends keyof TItem>(orgItems: TItem[] | Map<TItem[K], TItem>, keyPropNameOrFn: K | ((item: TItem) => K), options?: {
137
137
  includeSame?: boolean;
138
138
  excludes?: string[];
139
139
  includes?: string[];
140
- }): ArrayDiffs2Result<T>[];
141
- merge<P>(target: P[], options?: {
140
+ }): ArrayDiffs2Result<TItem>[];
141
+ merge<TOtherItem>(target: TOtherItem[], options?: {
142
142
  keys?: string[];
143
143
  excludes?: string[];
144
- }): (T | P | (T & P))[];
144
+ }): (TItem | TOtherItem | (TItem & TOtherItem))[];
145
145
  /**
146
146
  * 요소의 합계 반환
147
147
  * @param selector 값 선택 함수 (생략 시 요소 자체를 number로 사용)
148
148
  * @returns 빈 배열인 경우 0 반환
149
149
  */
150
- sum(selector?: (item: T, index: number) => number): number;
151
- min(): T extends number | string ? T | undefined : never;
152
- min<P extends number | string>(selector?: (item: T, index: number) => P): P | undefined;
153
- max(): T extends number | string ? T | undefined : never;
154
- max<P extends number | string>(selector?: (item: T, index: number) => P): P | undefined;
155
- shuffle(): T[];
150
+ sum(selector?: (item: TItem, index: number) => number): number;
151
+ min(): TItem extends number | string ? TItem | undefined : never;
152
+ min<P extends number | string>(selector?: (item: TItem, index: number) => P): P | undefined;
153
+ max(): TItem extends number | string ? TItem | undefined : never;
154
+ max<P extends number | string>(selector?: (item: TItem, index: number) => P): P | undefined;
155
+ shuffle(): TItem[];
156
156
  }
157
157
  /**
158
158
  * 원본 배열을 변경하는 확장 메서드
159
159
  * @mutates 모든 메서드가 원본 배열을 직접 변경합니다
160
160
  */
161
- export interface MutableArrayExt<T> {
161
+ export interface MutableArrayExt<TItem> {
162
162
  /**
163
163
  * 원본 배열에서 중복 제거
164
164
  * @param options matchAddress: 주소 비교 (true면 Set 사용), keyFn: 커스텀 키 함수 (O(n) 성능)
@@ -167,48 +167,48 @@ export interface MutableArrayExt<T> {
167
167
  */
168
168
  distinctThis(options?: boolean | {
169
169
  matchAddress?: boolean;
170
- keyFn?: (item: T) => string | number;
171
- }): T[];
170
+ keyFn?: (item: TItem) => string | number;
171
+ }): TItem[];
172
172
  /** 원본 배열 오름차순 정렬 @mutates */
173
- orderByThis(selector?: (item: T) => string | number | DateOnly | DateTime | Time | undefined): T[];
173
+ orderByThis(selector?: (item: TItem) => string | number | DateOnly | DateTime | Time | undefined): TItem[];
174
174
  /** 원본 배열 내림차순 정렬 @mutates */
175
- orderByDescThis(selector?: (item: T) => string | number | DateOnly | DateTime | Time | undefined): T[];
175
+ orderByDescThis(selector?: (item: TItem) => string | number | DateOnly | DateTime | Time | undefined): TItem[];
176
176
  /** 원본 배열에 항목 삽입 @mutates */
177
- insert(index: number, ...items: T[]): this;
177
+ insert(index: number, ...items: TItem[]): this;
178
178
  /** 원본 배열에서 항목 제거 @mutates */
179
- remove(item: T): this;
179
+ remove(item: TItem): this;
180
180
  /** 원본 배열에서 조건에 맞는 항목 제거 @mutates */
181
- remove(selector: (item: T, index: number) => boolean): this;
181
+ remove(selector: (item: TItem, index: number) => boolean): this;
182
182
  /** 원본 배열에서 항목 토글 (있으면 제거, 없으면 추가) @mutates */
183
- toggle(item: T): this;
183
+ toggle(item: TItem): this;
184
184
  /** 원본 배열 비우기 @mutates */
185
185
  clear(): this;
186
186
  }
187
- export type ArrayDiffsResult<T, P> = {
187
+ export type ArrayDiffsResult<TOriginal, TOther> = {
188
188
  source: undefined;
189
- target: P;
189
+ target: TOther;
190
190
  } | {
191
- source: T;
191
+ source: TOriginal;
192
192
  target: undefined;
193
193
  } | {
194
- source: T;
195
- target: P;
194
+ source: TOriginal;
195
+ target: TOther;
196
196
  };
197
- export type ArrayDiffs2Result<T> = {
197
+ export type ArrayDiffs2Result<TItem> = {
198
198
  type: "create";
199
- item: T;
199
+ item: TItem;
200
200
  orgItem: undefined;
201
201
  } | {
202
202
  type: "update";
203
- item: T;
204
- orgItem: T;
203
+ item: TItem;
204
+ orgItem: TItem;
205
205
  } | {
206
206
  type: "same";
207
- item: T;
208
- orgItem: T;
207
+ item: TItem;
208
+ orgItem: TItem;
209
209
  };
210
- export type TreeArray<T> = T & {
211
- children: TreeArray<T>[];
210
+ export type TreeArray<TNode> = TNode & {
211
+ children: TreeArray<TNode>[];
212
212
  };
213
213
  /** 정렬/비교 가능한 타입 */
214
214
  export type ComparableType = string | number | boolean | DateTime | DateOnly | Time | undefined;