@ddunigma/node 3.0.1 → 3.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,217 @@
1
+ import { P as PlatformAdapter, K as KeyDerivationOptions, D as Ddu64Core, b as DduOptions, O as ObfuscationLayer } from './core-BccIjoLZ.cjs';
2
+ export { C as CharSetConfig, c as CharSetInfo, d as CharsetBuilder, a as DduConstructorOptions, e as DduEncodeStats, f as DduProgressInfo, g as DduSetSymbol, E as EncoderConfig, h as KeyDerivationAlgorithm, W as WasmCodec, i as WorkerPool, j as getWasmCodec, k as getWasmCodecSync, p as preloadWasm } from './core-BccIjoLZ.cjs';
3
+
4
+ /**
5
+ * 브라우저 플랫폼 어댑터 구현.
6
+ * 암호화 연산에 Web Crypto API(SubtleCrypto)를 사용하고
7
+ * 압축에 CompressionStream/DecompressionStream을 사용합니다.
8
+ *
9
+ * 이 어댑터는 동기 암호화 또는 압축 연산을 지원하지 않습니다.
10
+ * Brotli도 브라우저 환경에서는 사용할 수 없습니다.
11
+ *
12
+ * @module adapters/BrowserAdapter
13
+ */
14
+
15
+ /**
16
+ * Web API를 사용하여 PlatformAdapter를 구현하는 BrowserAdapter:
17
+ * - AES-256-GCM 및 SHA-256을 위한 Web Crypto API(SubtleCrypto)
18
+ * - 안전한 랜덤 바이트를 위한 crypto.getRandomValues
19
+ * - deflate 압축을 위한 CompressionStream/DecompressionStream
20
+ */
21
+ declare class BrowserAdapter implements PlatformAdapter {
22
+ readonly supportsSyncCrypto = false;
23
+ readonly supportsSyncCompression = false;
24
+ readonly supportsBrotli = false;
25
+ readonly runtime: "browser";
26
+ /**
27
+ * UTF-8 키 문자열에서 SHA-256을 통해 256비트 키를 파생합니다.
28
+ * UTF-8 인코딩된 키에 SubtleCrypto.digest('SHA-256', ...)를 사용합니다.
29
+ */
30
+ deriveKey(key: string, options?: KeyDerivationOptions): Promise<Uint8Array>;
31
+ /**
32
+ * 12바이트 IV를 사용하여 AES-256-GCM으로 데이터를 암호화합니다.
33
+ * 와이어 포맷 반환: IV(12바이트) + authTag(16바이트) + 암호문.
34
+ *
35
+ * 참고: Web Crypto는 authTag를 암호문에 추가하므로,
36
+ * 마지막 16바이트를 authTag로 추출하고 와이어 포맷에 맞게 재배치합니다.
37
+ */
38
+ encrypt(data: Uint8Array, keyHash: Uint8Array): Promise<Uint8Array>;
39
+ /**
40
+ * AES-256-GCM 페이로드를 복호화합니다.
41
+ * 와이어 포맷 기대: IV(12바이트) + authTag(16바이트) + 암호문.
42
+ * 복호화 전에 Web Crypto 형식(암호문 + authTag)으로 재구성합니다.
43
+ */
44
+ decrypt(data: Uint8Array, keyHash: Uint8Array): Promise<Uint8Array>;
45
+ /**
46
+ * 암호학적으로 안전한 랜덤 바이트를 생성합니다.
47
+ */
48
+ randomBytes(length: number): Uint8Array;
49
+ /**
50
+ * CompressionStream을 통해 deflate로 데이터를 압축합니다.
51
+ * 가능하면 'deflate-raw' 형식을 사용하고, 그렇지 않으면 'deflate'를 사용합니다.
52
+ */
53
+ deflate(data: Uint8Array, _level?: number): Promise<Uint8Array>;
54
+ /**
55
+ * DecompressionStream을 통해 deflate 데이터를 압축 해제합니다.
56
+ * 가능하면 'deflate-raw' 형식을 사용하고, 그렇지 않으면 'deflate'를 사용합니다.
57
+ * maxBytes가 지정되면 제한을 적용합니다.
58
+ */
59
+ inflate(data: Uint8Array, maxBytes?: number): Promise<Uint8Array>;
60
+ /**
61
+ * CompressionStream에 적합한 deflate 형식을 결정합니다.
62
+ * Node.js zlib.deflateRaw와의 상호운용성을 위해 'deflate-raw'를 선호합니다.
63
+ */
64
+ private getDeflateFormat;
65
+ }
66
+
67
+ /**
68
+ * 런타임 자동 감지 모듈.
69
+ * 현재 JavaScript 런타임 환경을 감지하고 적절한 PlatformAdapter를 반환합니다.
70
+ *
71
+ * 중요: 이 모듈은 Node.js 내장 모듈을 임포트하지 않습니다.
72
+ * 감지는 순수하게 globalThis 검사에 기반합니다.
73
+ *
74
+ * @module adapters/detect
75
+ */
76
+
77
+ /** 감지된 런타임 환경 식별자 */
78
+ type RuntimeId = "node" | "browser" | "edge" | "deno" | "bun" | "unknown";
79
+ /**
80
+ * 현재 JavaScript 런타임 환경을 감지합니다.
81
+ *
82
+ * 감지 순서:
83
+ * 1. Node.js: `globalThis.process?.versions?.node` 존재
84
+ * 2. Deno: `(globalThis as any).Deno?.version?.deno` 존재
85
+ * 3. Bun: `(globalThis as any).Bun?.version` 존재
86
+ * 4. Web Crypto (브라우저/엣지): `globalThis.crypto?.subtle` 존재
87
+ * 5. 그 외: 에러 throw
88
+ *
89
+ * @returns 감지된 런타임 식별자
90
+ * @throws 적합한 crypto 제공자를 찾지 못한 경우 에러
91
+ */
92
+ declare function detectRuntime(): RuntimeId;
93
+ /**
94
+ * 현재 런타임에 적합한 PlatformAdapter를 가져옵니다.
95
+ *
96
+ * 실제로 필요할 때까지 플랫폼별 모듈을 임포트하지 않는
97
+ * 지연 로딩을 사용합니다.
98
+ *
99
+ * @returns 적절한 PlatformAdapter로 resolve되는 Promise
100
+ * @throws 적합한 런타임이 감지되지 않은 경우 에러
101
+ */
102
+ declare function getAdapter(): Promise<PlatformAdapter>;
103
+
104
+ /**
105
+ * ddunigma Web Streams API 구현.
106
+ *
107
+ * Web Streams API(globalThis.TransformStream)를 사용하는
108
+ * TransformStream 기반 인코딩/디코딩 파이프라인을 제공합니다.
109
+ * 모든 최신 브라우저와 Node.js에서 사용 가능합니다.
110
+ *
111
+ * 스트리밍 모드:
112
+ * - 압축/암호화 비활성화 시: 진정한 청크 단위 스트리밍 (메모리 효율적)
113
+ * - 압축/암호화 활성화 시: 전체 축적 후 일괄 처리 (알고리즘 제약)
114
+ *
115
+ * 스트림 헤더 형식: [pad]DDS1[D|B|N][1|0][pad]
116
+ * D=deflate, B=brotli, N=없음 (압축), 1/0 (암호화).
117
+ *
118
+ * @module streams/WebStreams
119
+ */
120
+
121
+ /**
122
+ * 바이너리 데이터를 charset 인코딩 문자열로 변환하는
123
+ * Web Streams API TransformStream을 생성합니다.
124
+ *
125
+ * 압축/암호화가 비활성화된 경우, 각 청크를 즉시 인코딩하여 출력합니다.
126
+ * 압축/암호화가 활성화된 경우, 전체 데이터를 축적한 후 flush에서 처리합니다.
127
+ *
128
+ * @param encoder - 인코딩에 사용할 Ddu64Core 인스턴스
129
+ * @param options - 인코딩 옵션 (compress, encrypt, compressionAlgorithm 등)
130
+ * @returns TransformStream<Uint8Array, string>
131
+ */
132
+ declare function createReadableEncodeStream(encoder: Ddu64Core, options?: DduOptions): TransformStream<Uint8Array, string>;
133
+ /**
134
+ * charset 인코딩 문자열을 바이너리 데이터로 역변환하는
135
+ * Web Streams API TransformStream을 생성합니다.
136
+ *
137
+ * 스트림은 DDS1 스트림 헤더를 파싱하여 압축 및 암호화 설정을 감지한 후
138
+ * 페이로드를 그에 맞게 디코딩합니다.
139
+ *
140
+ * 압축/암호화가 없는 스트림의 경우, 헤더 파싱 후 각 청크를 즉시 디코딩합니다.
141
+ * 압축/암호화가 있는 스트림의 경우, 전체 페이로드를 축적 후 일괄 디코딩합니다.
142
+ *
143
+ * @param encoder - 디코딩에 사용할 Ddu64Core 인스턴스
144
+ * @param options - 디코딩 옵션
145
+ * @returns TransformStream<string, Uint8Array>
146
+ */
147
+ declare function createReadableDecodeStream(encoder: Ddu64Core, options?: DduOptions): TransformStream<string, Uint8Array>;
148
+
149
+ /**
150
+ * 한글 음절 난독화 레이어 구현.
151
+ *
152
+ * 암호화된 charset 인코딩 문자열을 결정론적 전단사 매핑을 사용하여
153
+ * 자연스러운 한국어 음절 블록으로 변환합니다. 매핑은 다음을 보장합니다:
154
+ * - 모든 출력 문자가 유효한 한국어 음절 블록 (U+AC00–U+D7A3)
155
+ * - 단일 문자 빈도가 기대 균등 빈도의 3배를 초과하지 않음
156
+ * - 출력 길이 <= 입력 길이의 1.5배 (실제로는 1:1 매핑)
157
+ *
158
+ * 플랫폼 독립적: Node.js 임포트 없음.
159
+ *
160
+ * @module obfuscation/ObfuscationLayer
161
+ */
162
+
163
+ /**
164
+ * 한글 음절 매핑을 사용하여 ObfuscationLayer 인터페이스를 구현합니다.
165
+ *
166
+ * 입력 알파벳(인코더가 사용하는 charset 문자)이 주어지면,
167
+ * 이 레이어는 각 문자를 결정론적으로 한글 음절에 매핑합니다.
168
+ * 매핑은 전단사(가역적)이며 위치에 따라 각 문자의 할당된 음절 범위를
169
+ * 순환하여 출력 빈도를 균등하게 분배합니다.
170
+ */
171
+ declare class HangulObfuscationLayer implements ObfuscationLayer {
172
+ private readonly config;
173
+ /**
174
+ * 새 HangulObfuscationLayer를 생성합니다.
175
+ *
176
+ * @param alphabet - 완전한 입력 알파벳 (charset 문자 + 패딩 문자).
177
+ * 인코딩된 문자열에 나타날 수 있는 모든 고유 문자.
178
+ */
179
+ constructor(alphabet: string[]);
180
+ /**
181
+ * 암호화된 charset 인코딩 문자열을 한글 음절로 변환합니다.
182
+ *
183
+ * 각 입력 문자는 할당된 범위의 한글 음절에 매핑됩니다.
184
+ * 문자열 내 위치가 범위 내 어떤 음절을 사용할지 결정하여
185
+ * 균등한 빈도 분포를 보장합니다.
186
+ *
187
+ * @param input - 암호화된 charset 인코딩 문자열
188
+ * @returns 한글 음절 블록 문자열 (U+AC00–U+D7A3)
189
+ * @throws 입력에 알파벳에 없는 문자가 포함된 경우 에러
190
+ */
191
+ obfuscate(input: string): string;
192
+ /**
193
+ * 난독화를 역변환하여 원본 charset 인코딩 문자열을 복원합니다.
194
+ *
195
+ * 각 한글 음절이 어떤 문자의 범위에 속하는지 판별하여
196
+ * 원래 문자로 매핑합니다.
197
+ *
198
+ * @param input - 난독화된 한글 음절 문자열
199
+ * @returns 원본 charset 인코딩 문자열
200
+ * @throws 입력에 유효한 한글 음절 범위 밖의 문자가 포함되거나
201
+ * 알파벳 문자에 매핑되지 않는 문자가 포함된 경우 에러
202
+ */
203
+ deobfuscate(input: string): string;
204
+ }
205
+ /**
206
+ * 주어진 charset 설정에 대한 ObfuscationLayer를 생성합니다.
207
+ *
208
+ * charset 문자와 패딩 문자로부터 완전한 알파벳을 구성한 후
209
+ * 한글 난독화 레이어를 생성합니다.
210
+ *
211
+ * @param charSet - 인코딩에 사용되는 charset 문자
212
+ * @param paddingChar - 패딩 문자
213
+ * @returns ObfuscationLayer 인스턴스
214
+ */
215
+ declare function createObfuscationLayer(charSet: string[], paddingChar: string): ObfuscationLayer;
216
+
217
+ export { BrowserAdapter, Ddu64Core as Ddu64, Ddu64Core, DduOptions, HangulObfuscationLayer, KeyDerivationOptions, ObfuscationLayer, PlatformAdapter, createObfuscationLayer, createReadableDecodeStream, createReadableEncodeStream, detectRuntime, getAdapter };
@@ -0,0 +1,217 @@
1
+ import { P as PlatformAdapter, K as KeyDerivationOptions, D as Ddu64Core, b as DduOptions, O as ObfuscationLayer } from './core-BccIjoLZ.js';
2
+ export { C as CharSetConfig, c as CharSetInfo, d as CharsetBuilder, a as DduConstructorOptions, e as DduEncodeStats, f as DduProgressInfo, g as DduSetSymbol, E as EncoderConfig, h as KeyDerivationAlgorithm, W as WasmCodec, i as WorkerPool, j as getWasmCodec, k as getWasmCodecSync, p as preloadWasm } from './core-BccIjoLZ.js';
3
+
4
+ /**
5
+ * 브라우저 플랫폼 어댑터 구현.
6
+ * 암호화 연산에 Web Crypto API(SubtleCrypto)를 사용하고
7
+ * 압축에 CompressionStream/DecompressionStream을 사용합니다.
8
+ *
9
+ * 이 어댑터는 동기 암호화 또는 압축 연산을 지원하지 않습니다.
10
+ * Brotli도 브라우저 환경에서는 사용할 수 없습니다.
11
+ *
12
+ * @module adapters/BrowserAdapter
13
+ */
14
+
15
+ /**
16
+ * Web API를 사용하여 PlatformAdapter를 구현하는 BrowserAdapter:
17
+ * - AES-256-GCM 및 SHA-256을 위한 Web Crypto API(SubtleCrypto)
18
+ * - 안전한 랜덤 바이트를 위한 crypto.getRandomValues
19
+ * - deflate 압축을 위한 CompressionStream/DecompressionStream
20
+ */
21
+ declare class BrowserAdapter implements PlatformAdapter {
22
+ readonly supportsSyncCrypto = false;
23
+ readonly supportsSyncCompression = false;
24
+ readonly supportsBrotli = false;
25
+ readonly runtime: "browser";
26
+ /**
27
+ * UTF-8 키 문자열에서 SHA-256을 통해 256비트 키를 파생합니다.
28
+ * UTF-8 인코딩된 키에 SubtleCrypto.digest('SHA-256', ...)를 사용합니다.
29
+ */
30
+ deriveKey(key: string, options?: KeyDerivationOptions): Promise<Uint8Array>;
31
+ /**
32
+ * 12바이트 IV를 사용하여 AES-256-GCM으로 데이터를 암호화합니다.
33
+ * 와이어 포맷 반환: IV(12바이트) + authTag(16바이트) + 암호문.
34
+ *
35
+ * 참고: Web Crypto는 authTag를 암호문에 추가하므로,
36
+ * 마지막 16바이트를 authTag로 추출하고 와이어 포맷에 맞게 재배치합니다.
37
+ */
38
+ encrypt(data: Uint8Array, keyHash: Uint8Array): Promise<Uint8Array>;
39
+ /**
40
+ * AES-256-GCM 페이로드를 복호화합니다.
41
+ * 와이어 포맷 기대: IV(12바이트) + authTag(16바이트) + 암호문.
42
+ * 복호화 전에 Web Crypto 형식(암호문 + authTag)으로 재구성합니다.
43
+ */
44
+ decrypt(data: Uint8Array, keyHash: Uint8Array): Promise<Uint8Array>;
45
+ /**
46
+ * 암호학적으로 안전한 랜덤 바이트를 생성합니다.
47
+ */
48
+ randomBytes(length: number): Uint8Array;
49
+ /**
50
+ * CompressionStream을 통해 deflate로 데이터를 압축합니다.
51
+ * 가능하면 'deflate-raw' 형식을 사용하고, 그렇지 않으면 'deflate'를 사용합니다.
52
+ */
53
+ deflate(data: Uint8Array, _level?: number): Promise<Uint8Array>;
54
+ /**
55
+ * DecompressionStream을 통해 deflate 데이터를 압축 해제합니다.
56
+ * 가능하면 'deflate-raw' 형식을 사용하고, 그렇지 않으면 'deflate'를 사용합니다.
57
+ * maxBytes가 지정되면 제한을 적용합니다.
58
+ */
59
+ inflate(data: Uint8Array, maxBytes?: number): Promise<Uint8Array>;
60
+ /**
61
+ * CompressionStream에 적합한 deflate 형식을 결정합니다.
62
+ * Node.js zlib.deflateRaw와의 상호운용성을 위해 'deflate-raw'를 선호합니다.
63
+ */
64
+ private getDeflateFormat;
65
+ }
66
+
67
+ /**
68
+ * 런타임 자동 감지 모듈.
69
+ * 현재 JavaScript 런타임 환경을 감지하고 적절한 PlatformAdapter를 반환합니다.
70
+ *
71
+ * 중요: 이 모듈은 Node.js 내장 모듈을 임포트하지 않습니다.
72
+ * 감지는 순수하게 globalThis 검사에 기반합니다.
73
+ *
74
+ * @module adapters/detect
75
+ */
76
+
77
+ /** 감지된 런타임 환경 식별자 */
78
+ type RuntimeId = "node" | "browser" | "edge" | "deno" | "bun" | "unknown";
79
+ /**
80
+ * 현재 JavaScript 런타임 환경을 감지합니다.
81
+ *
82
+ * 감지 순서:
83
+ * 1. Node.js: `globalThis.process?.versions?.node` 존재
84
+ * 2. Deno: `(globalThis as any).Deno?.version?.deno` 존재
85
+ * 3. Bun: `(globalThis as any).Bun?.version` 존재
86
+ * 4. Web Crypto (브라우저/엣지): `globalThis.crypto?.subtle` 존재
87
+ * 5. 그 외: 에러 throw
88
+ *
89
+ * @returns 감지된 런타임 식별자
90
+ * @throws 적합한 crypto 제공자를 찾지 못한 경우 에러
91
+ */
92
+ declare function detectRuntime(): RuntimeId;
93
+ /**
94
+ * 현재 런타임에 적합한 PlatformAdapter를 가져옵니다.
95
+ *
96
+ * 실제로 필요할 때까지 플랫폼별 모듈을 임포트하지 않는
97
+ * 지연 로딩을 사용합니다.
98
+ *
99
+ * @returns 적절한 PlatformAdapter로 resolve되는 Promise
100
+ * @throws 적합한 런타임이 감지되지 않은 경우 에러
101
+ */
102
+ declare function getAdapter(): Promise<PlatformAdapter>;
103
+
104
+ /**
105
+ * ddunigma Web Streams API 구현.
106
+ *
107
+ * Web Streams API(globalThis.TransformStream)를 사용하는
108
+ * TransformStream 기반 인코딩/디코딩 파이프라인을 제공합니다.
109
+ * 모든 최신 브라우저와 Node.js에서 사용 가능합니다.
110
+ *
111
+ * 스트리밍 모드:
112
+ * - 압축/암호화 비활성화 시: 진정한 청크 단위 스트리밍 (메모리 효율적)
113
+ * - 압축/암호화 활성화 시: 전체 축적 후 일괄 처리 (알고리즘 제약)
114
+ *
115
+ * 스트림 헤더 형식: [pad]DDS1[D|B|N][1|0][pad]
116
+ * D=deflate, B=brotli, N=없음 (압축), 1/0 (암호화).
117
+ *
118
+ * @module streams/WebStreams
119
+ */
120
+
121
+ /**
122
+ * 바이너리 데이터를 charset 인코딩 문자열로 변환하는
123
+ * Web Streams API TransformStream을 생성합니다.
124
+ *
125
+ * 압축/암호화가 비활성화된 경우, 각 청크를 즉시 인코딩하여 출력합니다.
126
+ * 압축/암호화가 활성화된 경우, 전체 데이터를 축적한 후 flush에서 처리합니다.
127
+ *
128
+ * @param encoder - 인코딩에 사용할 Ddu64Core 인스턴스
129
+ * @param options - 인코딩 옵션 (compress, encrypt, compressionAlgorithm 등)
130
+ * @returns TransformStream<Uint8Array, string>
131
+ */
132
+ declare function createReadableEncodeStream(encoder: Ddu64Core, options?: DduOptions): TransformStream<Uint8Array, string>;
133
+ /**
134
+ * charset 인코딩 문자열을 바이너리 데이터로 역변환하는
135
+ * Web Streams API TransformStream을 생성합니다.
136
+ *
137
+ * 스트림은 DDS1 스트림 헤더를 파싱하여 압축 및 암호화 설정을 감지한 후
138
+ * 페이로드를 그에 맞게 디코딩합니다.
139
+ *
140
+ * 압축/암호화가 없는 스트림의 경우, 헤더 파싱 후 각 청크를 즉시 디코딩합니다.
141
+ * 압축/암호화가 있는 스트림의 경우, 전체 페이로드를 축적 후 일괄 디코딩합니다.
142
+ *
143
+ * @param encoder - 디코딩에 사용할 Ddu64Core 인스턴스
144
+ * @param options - 디코딩 옵션
145
+ * @returns TransformStream<string, Uint8Array>
146
+ */
147
+ declare function createReadableDecodeStream(encoder: Ddu64Core, options?: DduOptions): TransformStream<string, Uint8Array>;
148
+
149
+ /**
150
+ * 한글 음절 난독화 레이어 구현.
151
+ *
152
+ * 암호화된 charset 인코딩 문자열을 결정론적 전단사 매핑을 사용하여
153
+ * 자연스러운 한국어 음절 블록으로 변환합니다. 매핑은 다음을 보장합니다:
154
+ * - 모든 출력 문자가 유효한 한국어 음절 블록 (U+AC00–U+D7A3)
155
+ * - 단일 문자 빈도가 기대 균등 빈도의 3배를 초과하지 않음
156
+ * - 출력 길이 <= 입력 길이의 1.5배 (실제로는 1:1 매핑)
157
+ *
158
+ * 플랫폼 독립적: Node.js 임포트 없음.
159
+ *
160
+ * @module obfuscation/ObfuscationLayer
161
+ */
162
+
163
+ /**
164
+ * 한글 음절 매핑을 사용하여 ObfuscationLayer 인터페이스를 구현합니다.
165
+ *
166
+ * 입력 알파벳(인코더가 사용하는 charset 문자)이 주어지면,
167
+ * 이 레이어는 각 문자를 결정론적으로 한글 음절에 매핑합니다.
168
+ * 매핑은 전단사(가역적)이며 위치에 따라 각 문자의 할당된 음절 범위를
169
+ * 순환하여 출력 빈도를 균등하게 분배합니다.
170
+ */
171
+ declare class HangulObfuscationLayer implements ObfuscationLayer {
172
+ private readonly config;
173
+ /**
174
+ * 새 HangulObfuscationLayer를 생성합니다.
175
+ *
176
+ * @param alphabet - 완전한 입력 알파벳 (charset 문자 + 패딩 문자).
177
+ * 인코딩된 문자열에 나타날 수 있는 모든 고유 문자.
178
+ */
179
+ constructor(alphabet: string[]);
180
+ /**
181
+ * 암호화된 charset 인코딩 문자열을 한글 음절로 변환합니다.
182
+ *
183
+ * 각 입력 문자는 할당된 범위의 한글 음절에 매핑됩니다.
184
+ * 문자열 내 위치가 범위 내 어떤 음절을 사용할지 결정하여
185
+ * 균등한 빈도 분포를 보장합니다.
186
+ *
187
+ * @param input - 암호화된 charset 인코딩 문자열
188
+ * @returns 한글 음절 블록 문자열 (U+AC00–U+D7A3)
189
+ * @throws 입력에 알파벳에 없는 문자가 포함된 경우 에러
190
+ */
191
+ obfuscate(input: string): string;
192
+ /**
193
+ * 난독화를 역변환하여 원본 charset 인코딩 문자열을 복원합니다.
194
+ *
195
+ * 각 한글 음절이 어떤 문자의 범위에 속하는지 판별하여
196
+ * 원래 문자로 매핑합니다.
197
+ *
198
+ * @param input - 난독화된 한글 음절 문자열
199
+ * @returns 원본 charset 인코딩 문자열
200
+ * @throws 입력에 유효한 한글 음절 범위 밖의 문자가 포함되거나
201
+ * 알파벳 문자에 매핑되지 않는 문자가 포함된 경우 에러
202
+ */
203
+ deobfuscate(input: string): string;
204
+ }
205
+ /**
206
+ * 주어진 charset 설정에 대한 ObfuscationLayer를 생성합니다.
207
+ *
208
+ * charset 문자와 패딩 문자로부터 완전한 알파벳을 구성한 후
209
+ * 한글 난독화 레이어를 생성합니다.
210
+ *
211
+ * @param charSet - 인코딩에 사용되는 charset 문자
212
+ * @param paddingChar - 패딩 문자
213
+ * @returns ObfuscationLayer 인스턴스
214
+ */
215
+ declare function createObfuscationLayer(charSet: string[], paddingChar: string): ObfuscationLayer;
216
+
217
+ export { BrowserAdapter, Ddu64Core as Ddu64, Ddu64Core, DduOptions, HangulObfuscationLayer, KeyDerivationOptions, ObfuscationLayer, PlatformAdapter, createObfuscationLayer, createReadableDecodeStream, createReadableEncodeStream, detectRuntime, getAdapter };
@@ -0,0 +1,7 @@
1
+ import {pbkdf2,pbkdf2Sync,createHash,randomBytes,createCipheriv,createDecipheriv}from'crypto';import {deflateRaw,inflateRaw,brotliCompress,brotliDecompress,deflateRawSync,inflateRawSync,constants,brotliCompressSync,brotliDecompressSync}from'zlib';import {promisify}from'util';var Ne=Object.defineProperty;var Ke=(n=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(n,{get:(e,t)=>(typeof require<"u"?require:e)[t]}):n)(function(n){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+n+'" is not supported')});var O=(n,e)=>()=>(n&&(e=n(n=0)),e);var N=(n,e)=>{for(var t in e)Ne(n,t,{get:e[t],enumerable:true});};var xe={};N(xe,{NodeAdapter:()=>Q});function ke(n){return (n??"SHA-256").toLowerCase().replace("-","")}function ve(n){return n===void 0||!Number.isFinite(n)||n<=0?Ue:Math.max(Bt,Math.floor(n))}function Le(n){return n===void 0?Buffer.from(Pt,"utf-8"):typeof n=="string"?Buffer.from(n,"utf-8"):Buffer.from(n.buffer,n.byteOffset,n.byteLength)}var At,Pe,Ct,De,Et,Ue,Bt,Pt,Q,Te=O(()=>{At=promisify(deflateRaw),Pe=promisify(inflateRaw),Ct=promisify(brotliCompress),De=promisify(brotliDecompress),Et=promisify(pbkdf2),Ue=21e4,Bt=1e4,Pt="ddunigma:pbkdf2:v1";Q=class{supportsSyncCrypto=true;supportsSyncCompression=true;supportsBrotli=true;runtime="node";async deriveKey(e,t){if(t?.algorithm==="pbkdf2"){let r=await Et(e,Le(t.salt),ve(t.iterations),32,ke(t.hash));return new Uint8Array(r)}return this.deriveKeySync(e,t)}deriveKeySync(e,t){return t?.algorithm==="pbkdf2"?new Uint8Array(pbkdf2Sync(e,Le(t.salt),ve(t.iterations),32,ke(t.hash))):new Uint8Array(createHash("sha256").update(e).digest())}async encrypt(e,t){return this.encryptSync(e,t)}encryptSync(e,t){let r=randomBytes(12),o=createCipheriv("aes-256-gcm",t,r),s=Buffer.concat([o.update(e),o.final()]),i=o.getAuthTag(),a=new Uint8Array(28+s.length);return a.set(r,0),a.set(i,12),a.set(s,28),a}async decrypt(e,t){return this.decryptSync(e,t)}decryptSync(e,t){if(e.length<28)throw new Error("[Ddu64 decrypt] Invalid encrypted data: too short");let r=e.subarray(0,12),o=e.subarray(12,28),s=e.subarray(28),i=createDecipheriv("aes-256-gcm",t,r);i.setAuthTag(o);let a=Buffer.concat([i.update(s),i.final()]);return new Uint8Array(a)}randomBytes(e){return new Uint8Array(randomBytes(e))}async deflate(e,t){let r={};t!==void 0&&(r.level=t);let o=await At(Buffer.from(e),r);return new Uint8Array(o)}deflateSync(e,t){let r={};return t!==void 0&&(r.level=t),new Uint8Array(deflateRawSync(Buffer.from(e),r))}async inflate(e,t){if(t===void 0||t===Number.POSITIVE_INFINITY){let o=await Pe(Buffer.from(e));return new Uint8Array(o)}let r={maxOutputLength:t};try{let o=await Pe(Buffer.from(e),r);return new Uint8Array(o)}catch(o){let s=o,i=String(s?.message??"").toLowerCase();throw String(s?.code??"")==="ERR_BUFFER_TOO_LARGE"||i.includes("output length")||i.includes("buffer too large")?new Error(`[Ddu64 inflate] Decompressed data exceeds limit. Limit: ${t} bytes`,{cause:o}):o}}inflateSync(e,t){if(t===void 0||t===Number.POSITIVE_INFINITY)return new Uint8Array(inflateRawSync(Buffer.from(e)));try{return new Uint8Array(inflateRawSync(Buffer.from(e),{maxOutputLength:t}))}catch(r){let o=r,s=String(o?.message??"").toLowerCase();throw String(o?.code??"")==="ERR_BUFFER_TOO_LARGE"||s.includes("output length")||s.includes("buffer too large")?new Error(`[Ddu64 inflate] Decompressed data exceeds limit. Limit: ${t} bytes`,{cause:r}):r}}async brotliCompress(e,t){let r={};t!==void 0&&(r.params={[constants.BROTLI_PARAM_QUALITY]:Math.max(0,Math.min(11,t))});let o=await Ct(Buffer.from(e),r);return new Uint8Array(o)}brotliCompressSync(e,t){let r={};return t!==void 0&&(r.params={[constants.BROTLI_PARAM_QUALITY]:Math.max(0,Math.min(11,t))}),new Uint8Array(brotliCompressSync(Buffer.from(e),r))}async brotliDecompress(e,t){if(t===void 0||t===Number.POSITIVE_INFINITY){let r=await De(Buffer.from(e));return new Uint8Array(r)}try{let r=await De(Buffer.from(e),{maxOutputLength:t});return new Uint8Array(r)}catch(r){let o=r,s=String(o?.message??"").toLowerCase();throw String(o?.code??"")==="ERR_BUFFER_TOO_LARGE"||s.includes("output length")||s.includes("buffer too large")||s.includes("cannot create a buffer larger")?new Error(`[Ddu64 brotli] Decompressed data exceeds limit. Limit: ${t} bytes`,{cause:r}):r}}brotliDecompressSync(e,t){if(t===void 0||t===Number.POSITIVE_INFINITY)return new Uint8Array(brotliDecompressSync(Buffer.from(e)));try{return new Uint8Array(brotliDecompressSync(Buffer.from(e),{maxOutputLength:t}))}catch(r){let o=r,s=String(o?.message??"").toLowerCase();throw String(o?.code??"")==="ERR_BUFFER_TOO_LARGE"||s.includes("output length")||s.includes("buffer too large")||s.includes("cannot create a buffer larger")?new Error(`[Ddu64 brotli] Decompressed data exceeds limit. Limit: ${t} bytes`,{cause:r}):r}}};});var Re={};N(Re,{BrowserAdapter:()=>I});function Ut(n){return n===void 0||!Number.isFinite(n)||n<=0?21e4:Math.max(1e4,Math.floor(n))}function kt(n){return n===void 0?new TextEncoder().encode(Dt):typeof n=="string"?new TextEncoder().encode(n):n}var Dt,I,J=O(()=>{Dt="ddunigma:pbkdf2:v1";I=class{supportsSyncCrypto=false;supportsSyncCompression=false;supportsBrotli=false;runtime="browser";async deriveKey(e,t){let o=new TextEncoder().encode(e);if(t?.algorithm==="pbkdf2"){let i=await crypto.subtle.importKey("raw",o,"PBKDF2",false,["deriveBits"]),a=await crypto.subtle.deriveBits({name:"PBKDF2",salt:kt(t.salt),iterations:Ut(t.iterations),hash:t.hash??"SHA-256"},i,256);return new Uint8Array(a)}let s=await crypto.subtle.digest("SHA-256",o);return new Uint8Array(s)}async encrypt(e,t){let r=crypto.getRandomValues(new Uint8Array(12)),o=await crypto.subtle.importKey("raw",t,{name:"AES-GCM"},false,["encrypt"]),s=await crypto.subtle.encrypt({name:"AES-GCM",iv:r,tagLength:128},o,e),i=new Uint8Array(s),a=i.slice(0,i.length-16),c=i.slice(i.length-16),d=new Uint8Array(28+a.length);return d.set(r,0),d.set(c,12),d.set(a,28),d}async decrypt(e,t){if(e.length<28)throw new Error("[Ddu64 decrypt] Encrypted data is invalid. Payload must be at least 28 bytes (12 IV + 16 authTag + ciphertext).");let r=e.slice(0,12),o=e.slice(12,28),s=e.slice(28),i=new Uint8Array(s.length+16);i.set(s,0),i.set(o,s.length);let a=await crypto.subtle.importKey("raw",t,{name:"AES-GCM"},false,["decrypt"]);try{let c=await crypto.subtle.decrypt({name:"AES-GCM",iv:r,tagLength:128},a,i);return new Uint8Array(c)}catch{throw new Error("[Ddu64 decrypt] Decryption failed: data tampering or incorrect key.")}}randomBytes(e){return crypto.getRandomValues(new Uint8Array(e))}async deflate(e,t){if(typeof CompressionStream>"u")throw new Error("[Ddu64 compress] Deflate compression is unsupported in the current runtime. CompressionStream API is not available.");let r=this.getDeflateFormat(),o=new CompressionStream(r),s=o.writable.getWriter(),i=o.readable.getReader();s.write(e),s.close();let a=[],c=0;for(;;){let{done:h,value:f}=await i.read();if(h)break;a.push(f),c+=f.length;}let d=new Uint8Array(c),l=0;for(let h of a)d.set(h,l),l+=h.length;return d}async inflate(e,t){if(typeof DecompressionStream>"u")throw new Error("[Ddu64 decompress] Deflate decompression is unsupported in the current runtime. DecompressionStream API is not available.");let r=this.getDeflateFormat(),o=new DecompressionStream(r),s=o.writable.getWriter(),i=o.readable.getReader();s.write(e),s.close();let a=[],c=0;for(;;){let{done:h,value:f}=await i.read();if(h)break;if(c+=f.length,t!==void 0&&c>t)throw new Error(`[Ddu64 decompress] Decompressed size exceeds limit. Estimated ${c}+ bytes exceeds maximum of ${t} bytes.`);a.push(f);}let d=new Uint8Array(c),l=0;for(let h of a)d.set(h,l),l+=h.length;return d}getDeflateFormat(){return "deflate-raw"}};});var Ie={};N(Ie,{detectRuntime:()=>ee,getAdapter:()=>_e});function ee(){if(typeof globalThis.process<"u"&&globalThis.process?.versions?.node)return "node";if(globalThis.Deno?.version?.deno)return "deno";if(globalThis.Bun?.version)return "bun";if(typeof globalThis.crypto<"u"&&globalThis.crypto?.subtle)return "browser";throw new Error("[ddunigma] No suitable crypto provider found. Detected runtime lacks both Node.js crypto module and Web Crypto API (SubtleCrypto).")}async function _e(){switch(ee()){case "node":{let{NodeAdapter:e}=await Promise.resolve().then(()=>(Te(),xe));return new e}case "deno":case "bun":case "browser":case "edge":{let{BrowserAdapter:e}=await Promise.resolve().then(()=>(J(),Re));return new e}default:throw new Error("[ddunigma] No suitable crypto provider found. Detected runtime lacks both Node.js crypto module and Web Crypto API (SubtleCrypto).")}}var te=O(()=>{});function oe(n,e){let{bitLength:t,usePowerOfTwo:r,charsetSize:o}=e,s=n.length;if(s===0)return {indices:[],paddingBits:0};let i=s*8,a=Math.ceil(i/t),c=r?a:a*2,d=new Array(c),l=0,h=0,f=0;if(r){let m=(1<<t)-1;for(let g=0;g<s;g++)for(h=h<<8|n[g],f+=8;f>=t;)f-=t,d[l++]=h>>f&m,h&=(1<<f)-1;}else for(let m=0;m<s;m++)for(h=h<<8|n[m],f+=8;f>=t;){f-=t;let g=h>>f,p=g/o|0;d[l++]=p,d[l++]=g-p*o,h&=(1<<f)-1;}let u=0;if(f>0){u=t-f;let m=h<<u;if(r)d[l++]=m;else {let g=m/o|0;d[l++]=g,d[l++]=m-g*o;}}return d.length=l,{indices:d,paddingBits:u}}function se(n,e,t){let{bitLength:r,usePowerOfTwo:o,charsetSize:s}=t,i=n.length;if(i===0)return new Uint8Array(0);let a=o?1:2,c=Math.ceil(i/a),d=r<31?1<<r:Math.pow(2,r),l=Math.ceil((c*r-e)/8),h=new Uint8Array(l+1),f=0,u=0,m=0;if(o)for(let g=0;g<i;g+=a){let p=n[g];if(p<0||p>=s)throw new Error(`[BitPack decode] Invalid index ${p} at position ${g}`);for(u=u<<r|p,m+=r,g+a>=i&&e>0&&(u>>=e,m-=e);m>=8;)m-=8,h[f++]=u>>m&255,u&=(1<<m)-1;}else for(let g=0;g<i;g+=a){let p=n[g],y=n[g+1];if(p<0||p>=s)throw new Error(`[BitPack decode] Invalid index ${p} at position ${g}`);if(y===void 0||y<0||y>=s)throw new Error(`[BitPack decode] Invalid index ${y} at position ${g+1}`);let b=p*s+y;if(b>=d)throw new Error(`[BitPack decode] Value ${b} exceeds range at position ${g}`);for(u=u<<r|b,m+=r,g+a>=i&&e>0&&(u>>=e,m-=e);m>=8;)m-=8,h[f++]=u>>m&255,u&=(1<<m)-1;}return h.subarray(0,f)}function We(n,e){return n<=1?0:e?Math.floor(Math.log2(n)):Math.ceil(Math.log2(n))}function He(n){return n>0&&(n&n-1)===0}function ie(n){let e=He(n);return {bitLength:We(n,e),usePowerOfTwo:e,charsetSize:n}}var A="DDS1",B="ELYSIA",P="GRISEO";function K(n,e,t){let r=n.length,o=e.length,s={cleanedInput:n,paddingBits:0,isEncrypted:false,pipelineVersion:2};if(r<o)return s;let a=Math.max(0,t-1).toString().length;for(let c=Math.min(a,r);c>=1;c--){let d=r-c,l=true;for(let b=d;b<r;b++){let k=n.charCodeAt(b);if(k<48||k>57){l=false;break}}if(!l)continue;let h=n.substring(d),f=parseInt(h,10);if(Number.isNaN(f)||f<0||f>=t||h!==f.toString())continue;let u=d,m=false,g,p=2;u>=2&&n.substring(u-2,u)==="V3"&&(p=3,u-=2),u>=3&&n.substring(u-3,u)==="ENC"&&(m=true,u-=3),u>=B.length&&n.substring(u-B.length,u)===B?(g="deflate",u-=B.length):u>=P.length&&n.substring(u-P.length,u)===P&&(g="brotli",u-=P.length);let y=u-o;if(y>=0&&n.substring(y,u)===e)return {cleanedInput:n.substring(0,y),paddingBits:f,compressionAlgorithm:g,isEncrypted:m,pipelineVersion:p}}if(n.endsWith(e)){let c=0,d=r;for(;d>=o&&n.substring(d-o,d)===e;)c++,d-=o;if(c>0){let l=c*2;if(l<t)return {cleanedInput:n.substring(0,d),paddingBits:l,isEncrypted:false,pipelineVersion:2}}}return s}function W(n){let e=n.lastIndexOf("CHK");if(e===-1)return {data:n,checksum:null};let t=n.slice(e+3);return t.length!==8||!/^[0-9a-f]+$/i.test(t)?{data:n,checksum:null}:{data:n.slice(0,e),checksum:t.toLowerCase()}}function H(n){return n.length*2+A.length+2}function v(n,e){let t=e.compressionAlgorithm==="brotli"?"B":e.compressionAlgorithm==="deflate"?"D":"N",r=e.encrypted?"1":"0";return `${n}${A}${t}${r}${n}`}function ae(n,e){let t=H(e);if(n.length<t||!n.startsWith(e))return null;let r=e.length;if(n.slice(r,r+A.length)!==A)throw new Error("[wireFormat] Invalid stream header magic");let s=n[r+A.length],i=n[r+A.length+1];if(n.slice(t-e.length,t)!==e)throw new Error("[wireFormat] Invalid stream header terminator");let c=s==="B"?"brotli":s==="D"?"deflate":s==="N"?void 0:null;if(c===null)throw new Error("[wireFormat] Invalid stream header compression flag");if(i!=="0"&&i!=="1")throw new Error("[wireFormat] Invalid stream header encryption flag");return {compressionAlgorithm:c,encrypted:i==="1"}}function ce(n){let{paddingBits:e,compressionAlgorithm:t,isEncrypted:r,paddingChar:o,useRepeatPadding:s,pipelineVersion:i=2}=n;if(e===0&&!t&&!r&&i===2)return "";if(s&&!t&&!r&&i===2&&e>0&&e%2===0){let c=e>>1;return o.repeat(c)}return o+(t==="deflate"?B:t==="brotli"?P:"")+(r?"ENC":"")+(i===3?"V3":"")+e.toString()}var ze=(()=>{let n=new Uint32Array(256);for(let e=0;e<256;e++){let t=e;for(let r=0;r<8;r++)t=t>>>1^(t&1?3988292384:0);n[e]=t;}return n})();function D(n){let e=4294967295;for(let t=0;t<n.length;t++)e=e>>>8^ze[(e^n[t])&255];return ((e^4294967295)>>>0).toString(16).padStart(8,"0")}function de(n){return n.length===0?n:n.replaceAll("+","-").replaceAll("/","_").replaceAll("=",".")}function z(n){return n.length===0?n:n.replaceAll("-","+").replaceAll("_","/").replaceAll(".","=")}function le(n,e,t){if(e<=0||n.length<=e)return n;let r=Math.ceil(n.length/e),o=new Array(r*2-1),s=0;for(let i=0;i<n.length;i+=e)o[s++]=n.slice(i,i+e),i+e<n.length&&(o[s++]=t);return o.join("")}function F(n,e){if(n.length===0)return n;let t=n.replace(/[\r\n]/g,""),r=e&&e!==`
2
+ `&&e!==`\r
3
+ `&&e!=="\r"?e:"";return r.length>0&&t.includes(r)&&(t=t.replaceAll(r,"")),t}var Fe={"":0,\u3131:1,\u3132:2,\u3133:3,\u3134:4,\u3135:5,\u3136:6,\u3137:7,\u3139:8,\u313A:9,\u313B:10,\u313C:11,\u313D:12,\u313E:13,\u313F:14,\u3140:15,\u3141:16,\u3142:17,\u3144:18,\u3145:19,\u3146:20,\u3147:21,\u3148:22,\u314A:23,\u314B:24,\u314C:25,\u314D:26,\u314E:27};function $e(n,e){let t=n.charCodeAt(0);if(t<44032||t>55203)return n;let r=t-(t-44032)%28,o=Fe[e]??0;return String.fromCharCode(r+o)}function L(n,e){let t=new Array(n.length*e.length),r=0;for(let o of n)for(let s of e)t[r++]=$e(o,s);return t}function x(n,e){let r=n===void 0||!Number.isFinite(n)?6:Math.floor(n);return Math.min(e==="brotli"?11:9,Math.max(0,r))}var qe=new TextEncoder,Ye=new TextDecoder;function T(n){return qe.encode(n)}function $(n){return Ye.decode(n)}var q=(r=>(r.DDU="ddu",r.DDU_V1="ddu_v1",r.ONECHARSET="oneCharSet",r))(q||{}),Y={dduSetSymbol:"ddu",usePowerOfTwo:true,requiredLength:64,bitLength:6};var Ve={symbol:"ddu",charSet:["\uB70C","\uB568","\uC774","\uC6B0","\uC57C","\uB4C0","\uB31C","\uB3A8"],codaChar:["","\u3131","\u3132","\u3137","\u3148","\u3147","\u3145","\u3146"],maxRequiredLength:64,bitLength:6,paddingChar:"\uBB50",useRepeatPadding:true},je={symbol:"ddu_v1",charSet:["\uB70C","\uB568","\uC774","\uC6B0","\uC57C","!","?","."],maxRequiredLength:8,bitLength:3,paddingChar:"\uBB50",useRepeatPadding:true},Ge={symbol:"oneCharSet",charSet:["A","s","q","r","0","z","3","t","y","1","5","2","4","E","B","C","Q","F","R","T","U","W","V","X","Y","Z","b","a","c","d","D","G","L","H","I","-","J","K","M","O","N","f","e","h","g","P","i","S","k","l","m","u","j","v","n","o","p","9","w","6","7","8","x","_"],paddingChar:"=",maxRequiredLength:64,bitLength:6};function R(n){switch(n){case "ddu":return Ve;case "ddu_v1":return je;case "oneCharSet":return Ge;default:return}}var Ze=65536,Xe=["-","_","."];function ue(n,e,t,r){let o=(s,i,a,c,d)=>{if(Qe(a,t?.usePowerOfTwo)&&a>0){let f=Math.floor(Math.log2(a)),u=1<<f;return {charSet:s.length===u?s:s.slice(0,u),padding:i,requiredLength:u,bitLength:f,isPredefined:c,useRepeatPadding:d}}return {charSet:s.length===a?s:s.slice(0,a),padding:i,requiredLength:a,bitLength:a>0?Math.ceil(Math.log2(a)):0,isPredefined:c,useRepeatPadding:d}};try{let s=n??t?.dduChar,i=e??t?.paddingChar;if(s){if(!i)throw new Error("[Ddu64 Constructor] paddingChar is required when dduChar is provided.");let l=typeof s=="string"?[...s]:[...s],h=t?.codaChar,f=h?!0:t?.useRepeatPadding??!1;if(h&&h.length>0&&(l=L(l,h)),r&&new Set(l).size!==l.length){let g=l.filter((p,y)=>l.indexOf(p)!==y);throw new Error(`[Ddu64 Constructor] Character set contains duplicate characters: [${[...new Set(g)].join(", ")}]`)}let u=t?.requiredLength??l.length;if(l.length<u)throw new Error("[Ddu64 Constructor] Insufficient characters.");return o(l,i,u,!1,f)}let a=t?.dduSetSymbol??Y.dduSetSymbol??"ddu",c=Je(a),d=c.codaChar?L(c.charSet,c.codaChar):c.charSet;return o(d,c.paddingChar,c.maxRequiredLength,!0,c.useRepeatPadding)}catch(s){if(r)throw s;return V(t)}}function he(n,e,t){let r=[n,null];for(let s of r){let i=s?{...s}:V(t);try{let a=i.charSet,c=i.requiredLength,d=Array.from(new Set(a));if(d.length!==a.length){if(e){let f=a.filter((u,m)=>a.indexOf(u)!==m);throw new Error(`[Ddu64 normalizeCharSet] Character set contains duplicate characters: [${[...new Set(f)].join(", ")}]`)}a=d,i.isPredefined||(c=a.length);}if(a.length<c)throw new Error(`[Ddu64 normalizeCharSet] Insufficient characters. Required: ${c}, Has: ${a.length}`);if(c<2)throw new Error("[Ddu64 normalizeCharSet] At least 2 unique characters required.");if(a.length===0)throw new Error("[Ddu64 normalizeCharSet] Empty charset.");if(a.find(f=>f.length!==1)){if(e)throw new Error("[Ddu64 normalizeCharSet] Multi-character symbols are not supported.");continue}if(a.length>Ze){if(e)throw new Error("[Ddu64 normalizeCharSet] Charset size exceeds maximum supported size of 65536.");continue}if(i.padding.length!==1)throw new Error(`[Ddu64 normalizeCharSet] Padding length mismatch. Expected 1, got ${i.padding.length}`);if(a.includes(i.padding)){if(e)throw new Error(`[Ddu64 normalizeCharSet] Padding character "${i.padding}" conflicts with charset.`);a=a.filter(f=>f!==i.padding);}for(let f of a)if(f.includes(`
4
+ `)||f.includes("\r"))throw new Error("[Ddu64 normalizeCharSet] Newline and carriage return characters are reserved.");if(i.padding.includes(`
5
+ `)||i.padding.includes("\r"))throw new Error("[Ddu64 normalizeCharSet] Newline and carriage return characters are reserved.");return {charSet:a.length===c?a:a.slice(0,c),padding:i.padding,isPredefined:i.isPredefined}}catch(a){if(e)throw a}}let o=V(t);return {charSet:o.charSet.slice(0,o.requiredLength),padding:o.padding,isPredefined:true}}function fe(n,e,t){for(let r of Xe){for(let o of n)if(o.includes(r)){let s=`[Ddu64 Constructor] URL-Safe mode conflict: charset character "${o}" contains "${r}".`;if(t)throw new Error(s);return false}if(e.includes(r)){let o=`[Ddu64 Constructor] URL-Safe mode conflict: padding character "${e}" contains "${r}".`;if(t)throw new Error(o);return false}}return true}function me(n,e,t){if(t>256)return;let r=Math.min(n.length,t),o=n.slice(0,r),s=new Set;for(let a=0;a<o.length;a++)s.add(o[a]);s.add(e);for(let a=0;a<o.length;a++){let c=o[a];for(let h=0;h<o.length;h++){let f=c+o[h];if(s.has(f))throw new Error(`Combination conflict: "${c}" + "${o[h]}"`);s.add(f);}let d=c+e;if(s.has(d))throw new Error(`Combination conflict: "${c}" + padding`);s.add(d);let l=e+c;if(s.has(l))throw new Error(`Combination conflict: padding + "${c}"`);s.add(l);}let i=e+e;if(s.has(i))throw new Error("Combination conflict: double padding");s.add(i);}function Qe(n,e){return e!==void 0?e?n>0:false:n>0&&(n&n-1)===0}function Je(n){let e=R(n);if(!e)throw new Error(`CharSet with symbol ${n} not found`);return e}function V(n){let e=n?.dduSetSymbol??Y.dduSetSymbol??"oneCharSet",t=R(e)??R("oneCharSet");if(!t)throw new Error("Critical: No fallback CharSet available");return {charSet:t.codaChar?L(t.charSet,t.codaChar):t.charSet,padding:t.paddingChar,requiredLength:t.maxRequiredLength,bitLength:t.bitLength,isPredefined:true,useRepeatPadding:t.useRepeatPadding}}function et(){let n=1;return typeof globalThis.navigator<"u"&&globalThis.navigator.hardwareConcurrency?n=globalThis.navigator.hardwareConcurrency:typeof globalThis.process<"u"&&globalThis.process.versions?.node&&(typeof globalThis.process.availableParallelism=="function"?n=globalThis.process.availableParallelism():n=4),Math.max(1,Math.min(64,n-1))}function tt(){try{let{Worker:n}=Ke("worker_threads"),e=new URL("./nodeWorker.js",import.meta.url).pathname,t=new n(e);return {postMessage(r){t.postMessage(r);},async terminate(){await t.terminate();},onMessage(r){t.on("message",r);},onError(r){t.on("error",r);}}}catch{return null}}function rt(){try{if(typeof globalThis.Worker>"u")return null;let n=new URL("./webWorker.js",import.meta.url),e=new globalThis.Worker(n,{type:"module"});return {postMessage(t){e.postMessage(t);},async terminate(){e.terminate();},onMessage(t){e.addEventListener("message",r=>{t(r.data);});},onError(t){e.addEventListener("error",r=>{t(new Error(r.message||"Worker error"));});}}}catch{return null}}var G=class{poolSize;workers=[];pendingTasks=new Map;nextTaskId=0;roundRobinIndex=0;initialized=false;terminated=false;constructor(e){this.poolSize=e??et();}async encode(e,t){return await this.dispatch("encode",e,t)}async decode(e,t){return await this.dispatch("decode",e,t)}setPoolSize(e){if(!Number.isInteger(e))throw new Error(`[WorkerPool] Pool size must be an integer. Got: ${e}. Valid range: [1, 64]`);if(e<1||e>64)throw new Error(`[WorkerPool] Pool size must be between 1 and 64. Got: ${e}`);let t=this.poolSize;this.poolSize=e,this.initialized&&t!==e&&(this.terminateWorkers(),this.initialized=false);}async terminate(){this.terminated=true,await this.terminateWorkers();for(let[,e]of this.pendingTasks)e.reject(new Error("[WorkerPool] Pool terminated"));this.pendingTasks.clear();}async dispatch(e,t,r){if(this.terminated)throw new Error("[WorkerPool] Pool has been terminated");if(this.ensureInitialized(),this.workers.length===0)throw new Error("[WorkerPool] No workers available. Workers may not be supported in this runtime.");let o=this.nextTaskId++,s=this.roundRobinIndex%this.workers.length;this.roundRobinIndex=(this.roundRobinIndex+1)%this.workers.length;let i=this.workers[s];return new Promise((a,c)=>{this.pendingTasks.set(o,{resolve:a,reject:c});let d={id:o,type:e,data:t,config:r};i.postMessage(d);})}ensureInitialized(){if(this.initialized)return;let e=typeof globalThis.process<"u"&&!!globalThis.process.versions?.node;for(let t=0;t<this.poolSize;t++){let r=e?tt():rt();if(!r)break;r.onMessage(o=>{let s=this.pendingTasks.get(o.id);s&&(this.pendingTasks.delete(o.id),o.type==="error"?s.reject(new Error(o.error??"Worker error")):s.resolve(o.result));}),r.onError(o=>{console.error("[WorkerPool] Worker error:",o.message);}),this.workers.push(r);}this.initialized=true;}async terminateWorkers(){let e=this.workers.map(t=>t.terminate());await Promise.all(e),this.workers=[];}},j=null;function nt(){return j||(j=new G),j}function pe(n){nt().setPoolSize(n);}function ye(n){if(n.length===0)throw new Error("[Ddu64 obfuscation] Alphabet must not be empty.");if(n.length>11172)throw new Error(`[Ddu64 obfuscation] Alphabet size (${n.length}) exceeds available Hangul syllables (11172).`);let e=Math.floor(11172/n.length),t=new Map;for(let r=0;r<n.length;r++)t.set(n[r],r);return {alphabet:n,syllablesPerChar:e,charToIndex:t}}function ge(n,e,t){let r=44032+n*t.syllablesPerChar,o=e%t.syllablesPerChar;return r+o}function be(n,e){if(n<44032||n>55203)return -1;let t=n-44032,r=Math.floor(t/e.syllablesPerChar);return r>=e.alphabet.length?-1:r}var C=class{config;constructor(e){this.config=ye(e);}obfuscate(e){if(e.length===0)return "";let t=new Array(e.length);for(let r=0;r<e.length;r++){let o=e[r],s=this.config.charToIndex.get(o);if(s===void 0)throw new Error(`[Ddu64 obfuscation] Character "${o}" (U+${o.charCodeAt(0).toString(16).padStart(4,"0").toUpperCase()}) not found in obfuscation alphabet.`);let i=ge(s,r,this.config);t[r]=String.fromCharCode(i);}return t.join("")}deobfuscate(e){if(e.length===0)return "";let t=new Array(e.length);for(let r=0;r<e.length;r++){let o=e.charCodeAt(r),s=be(o,this.config);if(s===-1)throw new Error(`[Ddu64 obfuscation] Invalid syllable at position ${r}: U+${o.toString(16).padStart(4,"0").toUpperCase()} is not in the mapped range.`);t[r]=this.config.alphabet[s];}return t.join("")}};function ot(n,e){let t=new Set(n);t.add(e);let r=[...t];return new C(r)}var E=null,Z=false,S=false,w=null,X=class{exports;_ready=true;constructor(e){this.exports=e;}get ready(){return this._ready}encode(e,t){let{exports:r}=this;if(e.length===0)return {indices:new Uint16Array(0),paddingBits:0};let o=r.alloc(e.length);new Uint8Array(r.memory.buffer).set(e,o);let i=1<<t,a=1;try{let c=r.encode(o,e.length,t,i,a),d=r.get_result_ptr(),l=new Uint16Array(r.memory.buffer,d,c),h=new Uint16Array(c);return h.set(l),{indices:h,paddingBits:r.get_padding_bits()}}finally{r.dealloc(o,e.length);}}decode(e,t,r){let{exports:o}=this;if(e.length===0)return new Uint8Array(0);let s=e.length*2,i=o.alloc(s);new Uint16Array(o.memory.buffer,i,e.length).set(e);let c=1<<t,d=1;try{let l=o.decode(i,e.length,t,c,d,r);if(l===4294967295)throw new Error("[WasmCodec decode] Invalid index in input");let h=o.get_result_ptr(),f=new Uint8Array(o.memory.buffer,h,l),u=new Uint8Array(l);return u.set(f),u}finally{o.dealloc(i,s);}}};async function st(){try{if(typeof globalThis.process<"u"&&globalThis.process.versions?.node){let{readFile:n}=await import('fs/promises'),{fileURLToPath:e}=await import('url'),{dirname:t,join:r}=await import('path'),o=t(e(import.meta.url)),s=r(o,"wasm","codec.wasm");try{let i=await n(s);return i.buffer.slice(i.byteOffset,i.byteOffset+i.byteLength)}catch{let i=r(o,"codec.wasm");try{let a=await n(i);return a.buffer.slice(a.byteOffset,a.byteOffset+a.byteLength)}catch{let a=r(o,"..","wasm","codec.wasm");try{let c=await n(a);return c.buffer.slice(c.byteOffset,c.byteOffset+c.byteLength)}catch{return null}}}}if(typeof fetch=="function"){let n=await fetch(new URL("./wasm/codec.wasm",import.meta.url));return n.ok?await n.arrayBuffer():null}return null}catch{return null}}async function it(n){try{if(n.byteLength<16)return null;let e=new Uint8Array(n,0,4);if(e[0]!==0||e[1]!==97||e[2]!==115||e[3]!==109)return null;let t;try{t=await WebAssembly.compile(n);}catch{return null}let o=(await WebAssembly.instantiate(t,{})).exports;return typeof o.alloc!="function"||typeof o.dealloc!="function"||typeof o.encode!="function"||typeof o.decode!="function"||typeof o.get_result_ptr!="function"||typeof o.get_result_len!="function"||typeof o.get_padding_bits!="function"||!o.memory?null:o}catch{return null}}async function we(){try{if(E)return !0;if(S)return !1;let n=await st();if(!n)return S=!0,!1;let e=await it(n);return e?(E=new X(e),!0):(S=!0,!1)}catch{return S=true,false}}function at(n,e){let t;return {promise:new Promise((s,i)=>{t=setTimeout(()=>i(new Error(e)),n);}),clear:()=>clearTimeout(t)}}async function ct(){if(E)return;if(w)return w;let n=at(1e4,"[Ddu64 wasm] WASM initialization timed out (10s)"),e=async()=>{try{if(!await we())throw new Error("[Ddu64 wasm] WASM initialization failed")}finally{n.clear();}};return w=Promise.race([e(),n.promise]).finally(()=>{w=null,Z=true;}),w}function dt(){if(E)return E;if(S)return null;if(!Z&&!w){Z=true;let n;w=new Promise(e=>{n=setTimeout(()=>{S=true,e();},5e3),we().then(t=>{t||(S=true);}).catch(()=>{S=true;}).finally(()=>{n!==void 0&&clearTimeout(n),e();});}).finally(()=>{w=null;});}return null}function _(){return E}function Se(n){if(!Number.isFinite(n))throw new Error(`[Ddu64 config] wasmThreshold must be a finite number, got ${n}`);return Math.max(1024,Math.min(1048576,Math.round(n)))}var Lt=8,xt=64*1024*1024,Tt=64*1024*1024,re="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",Me="=",Rt=Object.fromEntries([...re].map((n,e)=>[n,e])),M=class{dduChar;paddingChar;bitLength;usePowerOfTwo;effectiveBitLength;dduBinaryLookup=new Map;isPredefinedCharSet;defaultCompress;defaultMaxDecodedBytes;defaultMaxDecompressedBytes;urlSafe;encryptionKey;keyDerivation;encryptionKeyHash;defaultChecksum;defaultChunkSize;defaultChunkSeparator;defaultCompressionLevel;defaultCompressionAlgorithm;useRepeatPadding;bitPackConfig;wasmThreshold;canUseNativeBase64;nativeDecodeMap;adapter;defaultObfuscate;_obfuscationLayer;constructor(e,t,r){let o=r?.throwOnError??r?.useBuildErrorReturn??false;r?.adapter?this.adapter=r.adapter:this.adapter=void 0;let s=ue(e,t,r,o),i=he(s,o,r);this.dduChar=i.charSet,this.paddingChar=i.padding,this.isPredefinedCharSet=i.isPredefined,this.defaultCompress=r?.compress??false,this.defaultMaxDecodedBytes=this.normalizeLimit(r?.maxDecodedBytes,xt,o,"maxDecodedBytes"),this.defaultMaxDecompressedBytes=this.normalizeLimit(r?.maxDecompressedBytes,Tt,o,"maxDecompressedBytes");let a=this.dduChar.length;this.usePowerOfTwo=a>0&&(a&a-1)===0;let c=Math.ceil(Math.log2(a));this.bitLength=this.usePowerOfTwo?Math.floor(Math.log2(a)):c,this.effectiveBitLength=this.usePowerOfTwo?this.bitLength:c;for(let l=0;l<a;l++)this.dduBinaryLookup.set(this.dduChar[l],l);this.isPredefinedCharSet||me(this.dduChar,this.paddingChar,a);let d=r?.urlSafe??false;if(this.urlSafe=d?fe(this.dduChar,this.paddingChar,o):false,this.encryptionKey=r?.encryptionKey,this.keyDerivation=r?.keyDerivation,this.encryptionKey&&this.adapter?.deriveKeySync&&(this.encryptionKeyHash=this.adapter.deriveKeySync(this.encryptionKey,this.keyDerivation)),this.defaultChecksum=r?.checksum??false,this.defaultChunkSize=r?.chunkSize,this.defaultChunkSeparator=r?.chunkSeparator??`
6
+ `,this.defaultCompressionAlgorithm=r?.compressionAlgorithm??"deflate",this.defaultCompressionLevel=x(r?.compressionLevel,this.defaultCompressionAlgorithm),this.useRepeatPadding=r?.useRepeatPadding??s.useRepeatPadding??false,this.defaultObfuscate=r?.obfuscate??false,this.defaultObfuscate&&!this.encryptionKey)throw new Error("[Ddu64 obfuscation] Obfuscation requires encryption to be enabled.");if(this.bitPackConfig=ie(a),this.wasmThreshold=Se(r?.wasmThreshold??4096),this.canUseNativeBase64=this.usePowerOfTwo&&this.dduChar.length===64,this.canUseNativeBase64){this.nativeDecodeMap=new Map;for(let l=0;l<re.length;l++){let h=this.dduChar[l];this.nativeDecodeMap.set(h,re[l]);}}}encode(e,t){return this.encodeInternal(e,t).encoded}decode(e,t){let r=this.decodeToUint8Array(e,t);return $(r)}decodeToUint8Array(e,t){let r=t?.checksum??this.defaultChecksum,o=t?.compress!==false,s=t?.encrypt!==false,i=e;this.reportProgress(t,{processedBytes:0,totalBytes:e.length,percent:0,stage:"start"});let a=t?.chunkSeparator??this.defaultChunkSeparator;i=F(i,a),this.urlSafe&&(i=z(i));let c=null;if(r){let y=W(i);c=y.checksum,i=y.data;}this.shouldObfuscate(t)&&(i=this.getObfuscationLayer().deobfuscate(i));let{cleanedInput:d,paddingBits:l,compressionAlgorithm:h,isEncrypted:f,pipelineVersion:u}=K(i,this.paddingChar,this.effectiveBitLength);if(f&&s&&!this.encryptionKey)throw new Error("[Ddu64 decode] Encrypted payload requires an encryptionKey");this.assertEncodedInputAligned(d);let m=this.normalizeLimit(t?.maxDecodedBytes,this.defaultMaxDecodedBytes,true,"maxDecodedBytes"),g=this.estimateDecodedBytes(d.length,l);if(g>m)throw new Error(`[Ddu64 decode] Decoded output exceeds limit. Estimated: ${g} bytes, Limit: ${m} bytes`);this.reportProgress(t,{processedBytes:d.length,totalBytes:e.length,percent:30,stage:"decode"});let p=this.decodeChars(d,l);if(u===3&&f&&this.encryptionKey&&s&&(this.reportProgress(t,{processedBytes:p.length,totalBytes:p.length,percent:55,stage:"decrypt"}),p=this.decryptSync(p)),h&&o&&(u===2||!f||s)){let y=this.normalizeLimit(t?.maxDecompressedBytes,this.defaultMaxDecompressedBytes,true,"maxDecompressedBytes");this.reportProgress(t,{processedBytes:p.length,totalBytes:p.length,percent:70,stage:"decompress"}),p=this.decompressSync(p,h,y);}if(c&&(u===2||!f||s)){this.reportProgress(t,{processedBytes:p.length,totalBytes:p.length,percent:85,stage:"checksum"});let y=D(p);if(y!==c)throw new Error(`[Ddu64 decode] Checksum mismatch. Expected: ${c}, Got: ${y}`)}return u===2&&f&&this.encryptionKey&&s&&(this.reportProgress(t,{processedBytes:p.length,totalBytes:p.length,percent:90,stage:"decrypt"}),p=this.decryptSync(p)),this.reportProgress(t,{processedBytes:p.length,totalBytes:p.length,percent:100,stage:"done"}),p}async encodeAsync(e,t){let r=await this.getAdapterAsync(),o=t?.compress??this.defaultCompress,s=t?.checksum??this.defaultChecksum,i=(t?.encrypt??true)&&!!this.encryptionKey,a=t?.chunkSize??this.defaultChunkSize,c=t?.chunkSeparator??this.defaultChunkSeparator,d=typeof e=="string"?T(e):e;this.reportProgress(t,{processedBytes:0,totalBytes:d.length,percent:0,stage:"start"});let l="";s&&(l=D(d));let h;if(o){let m=t?.compressionAlgorithm??this.defaultCompressionAlgorithm,g=x(t?.compressionLevel??this.defaultCompressionLevel,m);this.reportProgress(t,{processedBytes:d.length,totalBytes:d.length,percent:20,stage:"compress"});let p;if(m==="brotli"){if(!r.brotliCompress)throw new Error("[Ddu64 compress] Brotli compression is unavailable in the current runtime.");p=await r.brotliCompress(d,g);}else p=await r.deflate(d,g);p.length<d.length&&(d=p,h=m);}let f=false;if(i){let m=await this.getKeyHashAsync(r);this.reportProgress(t,{processedBytes:d.length,totalBytes:d.length,percent:45,stage:"encrypt"}),d=await r.encrypt(d,m),f=true;}this.reportProgress(t,{processedBytes:d.length,totalBytes:d.length,percent:70,stage:"encode"});let u=this.encodeBytes(d,h,f,t);return u=this.applyPostEncoding(u,t,l,s,a,c),this.reportProgress(t,{processedBytes:d.length,totalBytes:d.length,percent:100,stage:"done"}),u}async decodeAsync(e,t){let r=await this.decodeToUint8ArrayAsync(e,t);return $(r)}async decodeToUint8ArrayAsync(e,t){let r=await this.getAdapterAsync(),o=t?.checksum??this.defaultChecksum,s=t?.compress!==false,i=t?.encrypt!==false,a=e;this.reportProgress(t,{processedBytes:0,totalBytes:e.length,percent:0,stage:"start"});let c=t?.chunkSeparator??this.defaultChunkSeparator;a=F(a,c),this.urlSafe&&(a=z(a));let d=null;if(o){let b=W(a);d=b.checksum,a=b.data;}this.shouldObfuscate(t)&&(a=this.getObfuscationLayer().deobfuscate(a));let{cleanedInput:l,paddingBits:h,compressionAlgorithm:f,isEncrypted:u,pipelineVersion:m}=K(a,this.paddingChar,this.effectiveBitLength);if(u&&i&&!this.encryptionKey)throw new Error("[Ddu64 decode] Encrypted payload requires an encryptionKey");this.assertEncodedInputAligned(l);let g=this.normalizeLimit(t?.maxDecodedBytes,this.defaultMaxDecodedBytes,true,"maxDecodedBytes"),p=this.estimateDecodedBytes(l.length,h);if(p>g)throw new Error(`[Ddu64 decode] Decoded output exceeds limit. Estimated: ${p} bytes, Limit: ${g} bytes`);this.reportProgress(t,{processedBytes:l.length,totalBytes:e.length,percent:30,stage:"decode"});let y=this.decodeChars(l,h);if(m===3&&u&&this.encryptionKey&&i){let b=await this.getKeyHashAsync(r);this.reportProgress(t,{processedBytes:y.length,totalBytes:y.length,percent:55,stage:"decrypt"}),y=await r.decrypt(y,b);}if(f&&s&&(m===2||!u||i)){let b=this.normalizeLimit(t?.maxDecompressedBytes,this.defaultMaxDecompressedBytes,true,"maxDecompressedBytes");if(f==="brotli"){if(!r.brotliDecompress)throw new Error("[Ddu64 decompress] Brotli decompression is unavailable in the current runtime.");this.reportProgress(t,{processedBytes:y.length,totalBytes:y.length,percent:70,stage:"decompress"}),y=await r.brotliDecompress(y,b);}else this.reportProgress(t,{processedBytes:y.length,totalBytes:y.length,percent:70,stage:"decompress"}),y=await r.inflate(y,b);}if(d&&(m===2||!u||i)){this.reportProgress(t,{processedBytes:y.length,totalBytes:y.length,percent:85,stage:"checksum"});let b=D(y);if(b!==d)throw new Error(`[Ddu64 decode] Checksum mismatch. Expected: ${d}, Got: ${b}`)}if(m===2&&u&&this.encryptionKey&&i){let b=await this.getKeyHashAsync(r);this.reportProgress(t,{processedBytes:y.length,totalBytes:y.length,percent:90,stage:"decrypt"}),y=await r.decrypt(y,b);}return this.reportProgress(t,{processedBytes:y.length,totalBytes:y.length,percent:100,stage:"done"}),y}getCharSetInfo(){return {charSet:[...this.dduChar],paddingChar:this.paddingChar,bitLength:this.bitLength,usePowerOfTwo:this.usePowerOfTwo,encoding:"utf-8",defaultCompress:this.defaultCompress,defaultMaxDecodedBytes:this.defaultMaxDecodedBytes,defaultMaxDecompressedBytes:this.defaultMaxDecompressedBytes,urlSafe:this.urlSafe,hasEncryptionKey:!!this.encryptionKey,defaultChecksum:this.defaultChecksum,defaultChunkSize:this.defaultChunkSize,defaultChunkSeparator:this.defaultChunkSeparator,defaultCompressionLevel:this.defaultCompressionLevel,defaultCompressionAlgorithm:this.defaultCompressionAlgorithm}}getStats(e,t){let o=(typeof e=="string"?T(e):e).length,{encoded:s,compressedSize:i}=this.encodeInternal(e,t),a=s.length,c=o>0?a/o:0,l=(t?.compress??this.defaultCompress)&&i!==void 0&&o>0?i/o:void 0;return {originalSize:o,encodedSize:a,compressedSize:i,compressionRatio:l,expansionRatio:c,charsetSize:this.dduChar.length,bitLength:this.bitLength}}static setWorkerPoolSize(e){pe(e);}encodeInternal(e,t){let r=t?.compress??this.defaultCompress,o=t?.checksum??this.defaultChecksum,s=(t?.encrypt??true)&&!!this.encryptionKey,i=t?.chunkSize??this.defaultChunkSize,a=t?.chunkSeparator??this.defaultChunkSeparator,c=typeof e=="string"?T(e):e;this.reportProgress(t,{processedBytes:0,totalBytes:c.length,percent:0,stage:"start"});let d="";o&&(d=D(c));let l,h;if(r){let m=t?.compressionAlgorithm??this.defaultCompressionAlgorithm,g=x(t?.compressionLevel??this.defaultCompressionLevel,m);this.reportProgress(t,{processedBytes:c.length,totalBytes:c.length,percent:20,stage:"compress"});let p=this.compressSync(c,m,g);h=p.length,p.length<c.length&&(c=p,l=m);}let f=false;s&&(this.reportProgress(t,{processedBytes:c.length,totalBytes:c.length,percent:45,stage:"encrypt"}),c=this.encryptSync(c),f=true),this.reportProgress(t,{processedBytes:c.length,totalBytes:c.length,percent:70,stage:"encode"});let u=this.encodeBytes(c,l,f,t);return u=this.applyPostEncoding(u,t,d,o,i,a),this.reportProgress(t,{processedBytes:c.length,totalBytes:c.length,percent:100,stage:"done"}),{encoded:u,compressedSize:h}}applyPostEncoding(e,t,r,o,s,i){let a=e;return this.shouldObfuscate(t)&&(a=this.getObfuscationLayer().obfuscate(a)),o&&r&&(a=a+"CHK"+r),this.urlSafe&&(a=de(a)),s&&s>0&&(a=le(a,s,i)),a}encodeBytes(e,t,r,o){if(e.length===0)return "";let s=this.encodeBytesWithNativeBase64(e),i,a;if(s)i=s.indices,a=s.paddingBits;else {let l=this.shouldUseWasm(e.length)?_():null;if(l?.ready&&this.usePowerOfTwo){let h=l.encode(e,this.bitLength);i=h.indices,a=h.paddingBits;}else {let h=oe(e,this.bitPackConfig);i=h.indices,a=h.paddingBits;}}let c=new Array(i.length);for(let l=0;l<i.length;l++)c[l]=this.dduChar[i[l]];let d=o?.omitFooter?"":ce({paddingBits:a,compressionAlgorithm:t,isEncrypted:!!r,paddingChar:this.paddingChar,useRepeatPadding:this.useRepeatPadding&&!t&&!r,pipelineVersion:r?3:2});return c.join("")+d}decodeChars(e,t){let r=e.length;if(r===0)return new Uint8Array(0);let o=this.decodeCharsWithNativeBase64(e,t);if(o)return o;let s=r>=this.wasmThreshold||r>=4096?new Uint16Array(r):new Array(r);for(let a=0;a<r;a++){let c=e[a],d=this.dduBinaryLookup.get(c);if(d===void 0)throw new Error(`[Ddu64 decode] Invalid character "${c}" at ${a}`);s[a]=d;}let i=this.shouldUseWasm(r)?_():null;if(i?.ready&&this.usePowerOfTwo){let a=s instanceof Uint16Array?s:Uint16Array.from(s);return i.decode(a,this.bitLength,t)}return se(s,t,this.bitPackConfig)}encodeBytesWithNativeBase64(e){if(!this.canUseNativeBase64)return null;let t=this.bytesToBase64(e);if(t===null)return null;let r=0,o=t.length;for(;o>0&&t[o-1]===Me;)r++,o--;let s=o>=4096?new Uint16Array(o):new Array(o);for(let i=0;i<o;i++)s[i]=Rt[t[i]];return {indices:s,paddingBits:r===2?4:r===1?2:0}}decodeCharsWithNativeBase64(e,t){if(!this.canUseNativeBase64||!this.nativeDecodeMap)return null;let r=t===4?2:t===2?1:t===0?0:-1;if(r<0)return null;let o=new Array(e.length+r);for(let s=0;s<e.length;s++){let i=this.nativeDecodeMap.get(e[s]);if(i===void 0)return null;o[s]=i;}for(let s=0;s<r;s++)o[e.length+s]=Me;return this.base64ToBytes(o.join(""))}bytesToBase64(e){let t=e.toBase64;if(typeof t=="function")return t.call(e);let r=globalThis.Buffer;return r?.from?r.from(e.buffer,e.byteOffset,e.byteLength).toString("base64"):null}base64ToBytes(e){let t=Uint8Array;if(typeof t.fromBase64=="function")return t.fromBase64(e);let r=globalThis.Buffer;if(r?.from){let o=r.from(e,"base64");return new Uint8Array(o.buffer,o.byteOffset,o.byteLength)}return null}shouldUseWasm(e){return e>=this.wasmThreshold}reportProgress(e,t){e?.onProgress?.(t);}requireSyncAdapter(){if(!this.adapter)throw new Error("[Ddu64 adapter] No platform adapter available. Use encodeAsync()/decodeAsync() in browser environments, or provide an adapter via options.adapter.");return this.adapter}encryptSync(e){let t=this.requireSyncAdapter();if(!t.encryptSync)throw new Error("[Ddu64 encrypt] Sync encryption unavailable. Use encodeAsync() in browser environments.");if(!this.encryptionKeyHash){if(!t.deriveKeySync)throw new Error("[Ddu64 encrypt] Sync key derivation unavailable. Use encodeAsync() in browser environments.");this.encryptionKeyHash=t.deriveKeySync(this.encryptionKey,this.keyDerivation);}return t.encryptSync(e,this.encryptionKeyHash)}decryptSync(e){let t=this.requireSyncAdapter();if(!t.decryptSync)throw new Error("[Ddu64 decrypt] Sync decryption unavailable. Use decodeAsync() in browser environments.");if(!this.encryptionKeyHash){if(!t.deriveKeySync)throw new Error("[Ddu64 decrypt] Sync key derivation unavailable. Use decodeAsync() in browser environments.");this.encryptionKeyHash=t.deriveKeySync(this.encryptionKey,this.keyDerivation);}return t.decryptSync(e,this.encryptionKeyHash)}compressSync(e,t,r){let o=this.requireSyncAdapter();if(t==="brotli"){if(!o.brotliCompressSync)throw new Error("[Ddu64 compress] Brotli compression is unavailable in the current runtime.");return o.brotliCompressSync(e,r)}if(!o.deflateSync)throw new Error("[Ddu64 compress] Sync compression unavailable. Use encodeAsync() in browser environments.");return o.deflateSync(e,r)}decompressSync(e,t,r){let o=this.requireSyncAdapter();if(t==="brotli"){if(!o.brotliDecompressSync)throw new Error("[Ddu64 decompress] Brotli decompression is unavailable in the current runtime.");return o.brotliDecompressSync(e,r)}if(!o.inflateSync)throw new Error("[Ddu64 decompress] Sync decompression unavailable. Use decodeAsync() in browser environments.");return o.inflateSync(e,r)}async getAdapterAsync(){if(this.adapter)return this.adapter;let{getAdapter:e}=await Promise.resolve().then(()=>(te(),Ie));return this.adapter=await e(),this.adapter}async getKeyHashAsync(e){return this.encryptionKeyHash?this.encryptionKeyHash:(this.encryptionKeyHash=await e.deriveKey(this.encryptionKey,this.keyDerivation),this.encryptionKeyHash)}getObfuscationLayer(){if(!this._obfuscationLayer){let e=new Set(this.dduChar);e.add(this.paddingChar);let t="ELYSIAGRONCV01234567";for(let o of t)e.add(o);let r=[...e];this._obfuscationLayer=new C(r);}return this._obfuscationLayer}shouldObfuscate(e){let t=e?.obfuscate??this.defaultObfuscate;if(t&&!this.encryptionKey)throw new Error("[Ddu64 obfuscation] Obfuscation requires encryption to be enabled.");return t}normalizeLimit(e,t,r,o){if(e===void 0)return t;if(e===Number.POSITIVE_INFINITY)return Number.POSITIVE_INFINITY;if(!Number.isFinite(e)||e<=0){if(r)throw new Error(`[Ddu64 options] Invalid ${o}. Must be a positive finite number or Infinity.`);return t}return Math.floor(e)}estimateDecodedBytes(e,t){if(e===0)return 0;if(t<0||t>=this.effectiveBitLength)throw new Error(`[Ddu64 decode] Invalid padding bits: ${t}`);let r=this.usePowerOfTwo?1:2,s=Math.ceil(e/r)*this.effectiveBitLength-t;if(s<0)throw new Error("[Ddu64 decode] Invalid decoded bit length");return Math.ceil(s/Lt)}assertEncodedInputAligned(e){if(!this.usePowerOfTwo&&e.length%2!==0)throw new Error(`[Ddu64 decode] Invalid encoded length for variable charset. Expected multiple of 2, got ${e.length}`)}};var ne=class n{chars=[];constructor(){}static create(){return new n}static fromUnicodeRange(e,t){return new n().addUnicodeRange(e,t)}static fromString(e){return new n().addString(e)}static base64(){return new n().addString("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/")}static base32(){return new n().addString("ABCDEFGHIJKLMNOPQRSTUVWXYZ234567")}static uppercase(){return n.fromUnicodeRange(65,90)}static lowercase(){return n.fromUnicodeRange(97,122)}static digits(){return n.fromUnicodeRange(48,57)}static hangulJamo(){return new n().addUnicodeRange(4352,4370).addUnicodeRange(4449,4469).addUnicodeRange(4520,4546)}addUnicodeRange(e,t){for(let r=e;r<=t;r++)this.chars.push(String.fromCodePoint(r));return this}addString(e){return typeof e=="string"?this.chars.push(...e):this.chars.push(...e),this}add(...e){return this.chars.push(...e),this}excludeConfusing(){let e=new Set(["0","O","o","1","l","I","i","|","L"]);return this.chars=this.chars.filter(t=>!e.has(t)),this}exclude(...e){let t=new Set(e);return this.chars=this.chars.filter(r=>!t.has(r)),this}excludeUrlUnsafe(){let e=new Set(["+","/","=","?","&","#","%"," "]);return this.chars=this.chars.filter(t=>!e.has(t)),this}unique(){return this.chars=[...new Set(this.chars)],this}shuffle(e){let t=e!==void 0?this.seededRandom(e):Math.random;for(let r=this.chars.length-1;r>0;r--){let o=Math.floor(t()*(r+1));[this.chars[r],this.chars[o]]=[this.chars[o],this.chars[r]];}return this}seededRandom(e){let t=e|0||1;return ()=>(t^=t<<13,t^=t>>17,t^=t<<5,(t>>>0)/4294967296)}limit(e){return this.chars=this.chars.slice(0,e),this}limitToPowerOfTwo(){let e=this.chars.length;if(e===0)return this;let t=1<<Math.floor(Math.log2(e));return this.chars=this.chars.slice(0,t),this}sort(){return this.chars.sort(),this}reverse(){return this.chars.reverse(),this}get length(){return this.chars.length}buildString(){return this.chars.join("")}build(){return [...this.chars]}buildWithPadding(e){let t=[...this.chars],r=e;if(!r){let o=["=",".","_","-","~","!"];for(let s of o)if(!t.includes(s)){r=s;break}if(!r)throw new Error("Cannot find suitable padding character")}return {charset:t,padding:r}}};J();te();function _t(n,e){let t=n.getCharSetInfo(),r=e?.compress??t.defaultCompress,o=(e?.encrypt??true)&&t.hasEncryptionKey,s=r?e?.compressionAlgorithm??t.defaultCompressionAlgorithm:void 0,i=t.paddingChar,a=!r&&!o,c=false,d=[],l=0,h=null;return new TransformStream({async transform(f,u){if(a){if(!c){let b=v(i,{compressionAlgorithm:void 0,encrypted:false});u.enqueue(b),c=true;}let m;h&&h.length>0?(m=new Uint8Array(h.length+f.length),m.set(h,0),m.set(f,h.length)):m=f;let g=t.bitLength,p=Oe(g,8)/8,y=Math.floor(m.length/p)*p;if(y>0){let b=m.subarray(0,y),k=await n.encodeAsync(b,{compress:false,encrypt:false,checksum:false,chunkSize:void 0,chunkSeparator:void 0,omitFooter:true});u.enqueue(k);}y<m.length?h=m.slice(y):h=null;}else d.push(f),l+=f.length;},async flush(f){try{if(a){if(!c){let u=v(i,{compressionAlgorithm:void 0,encrypted:!1});f.enqueue(u);}if(h&&h.length>0){let u=await n.encodeAsync(h,{compress:!1,encrypt:!1,checksum:!1,chunkSize:void 0,chunkSeparator:void 0});f.enqueue(u);}h=null;}else {let u=v(i,{compressionAlgorithm:s,encrypted:o});if(f.enqueue(u),l>0){let m=new Uint8Array(l),g=0;for(let y of d)m.set(y,g),g+=y.length;let p=await n.encodeAsync(m,{...e,compress:r,encrypt:o,checksum:!1,chunkSize:void 0,chunkSeparator:void 0});f.enqueue(p);}d=[],l=0;}}catch(u){f.error(u instanceof Error?u:new Error(String(u)));}}})}function It(n,e){let t=n.getCharSetInfo(),r=t.paddingChar,o=H(r),s="",i=false,a=null,c=false;return new TransformStream({async transform(d,l){if(s+=d,!i&&s.length>=o){if(!s.startsWith(r)){l.error(new Error("[WebStreams decode] Invalid or missing stream header"));return}if(a=ae(s,r),a===null){l.error(new Error("[WebStreams decode] Invalid or missing stream header"));return}if(a.encrypted&&!t.hasEncryptionKey){l.error(new Error("[WebStreams decode] Encrypted stream requires an encryptionKey"));return}i=true,c=!a.compressionAlgorithm&&!a.encrypted,s=s.slice(o);}if(i&&c&&s.length>0){let h=t.bitLength,f=Oe(h,8)/h,u=Math.floor(s.length/f)*f;if(u>0){let m=s.slice(0,u);s=s.slice(u);try{let g=await n.decodeToUint8ArrayAsync(m,{compress:!1,encrypt:!1,checksum:!1,chunkSize:void 0,chunkSeparator:void 0});g.length>0&&l.enqueue(g);}catch{s=m+s;}}}},async flush(d){try{if(!i){if(s.length===0)return;d.error(new Error("[WebStreams decode] Incomplete stream header"));return}if(s.length===0)return;let l=a.compressionAlgorithm,h=a.encrypted,f=await n.decodeToUint8ArrayAsync(s,{...e,compress:!!l,compressionAlgorithm:l,encrypt:h,checksum:!1,chunkSize:void 0,chunkSeparator:void 0});f.length>0&&d.enqueue(f),s="";}catch(l){d.error(l instanceof Error?l:new Error(String(l)));}}})}function Oe(n,e){return n*e/Mt(n,e)}function Mt(n,e){for(;e!==0;){let t=e;e=n%e,n=t;}return n}export{I as BrowserAdapter,ne as CharsetBuilder,M as Ddu64,M as Ddu64Core,q as DduSetSymbol,C as HangulObfuscationLayer,ot as createObfuscationLayer,It as createReadableDecodeStream,_t as createReadableEncodeStream,ee as detectRuntime,_e as getAdapter,dt as getWasmCodec,_ as getWasmCodecSync,ct as preloadWasm};//# sourceMappingURL=browser.js.map
7
+ //# sourceMappingURL=browser.js.map