@toon-protocol/townhouse 0.1.0-rc5 → 0.1.1

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
@@ -230,6 +230,119 @@ The package-local `packages/townhouse/compose/townhouse-dev.yml` is the canonica
230
230
 
231
231
  For backward compatibility, `docker-compose-townhouse-dev.yml` at the repo root is preserved and continues to be used by `scripts/townhouse-dev-infra.sh`. A follow-up story will route the script through the package-local copy.
232
232
 
233
+ ## DockerOrchestrator Profiles
234
+
235
+ The `DockerOrchestrator` class drives both the contributor dev stack and
236
+ the operator HS-mode apex stack via a single `profile: 'dev' | 'hs'`
237
+ parameter:
238
+
239
+ - **`profile: 'dev'`** (default) — uses `dockerode` for fine-grained
240
+ programmatic control. Matches the lifecycle the existing `townhouse up`
241
+ CLI has shipped since Epic 21. No `composePath` required.
242
+ - **`profile: 'hs'`** — shells out to `docker compose -f <composePath> up -d`
243
+ with `--profile <type>` flags for each enabled peer. Waits on the
244
+ connector's `GET /admin/hs-hostname` endpoint (connector v3.5.0+) until
245
+ the `.anyone` hostname is published. Requires `composePath` (typically
246
+ the path returned by `materializeComposeTemplate('hs')`).
247
+
248
+ Example (HS-mode caller, as Story 45.4's `townhouse hs up` will use):
249
+ ```typescript
250
+ import { materializeComposeTemplate, DockerOrchestrator } from '@toon-protocol/townhouse';
251
+ import Docker from 'dockerode';
252
+
253
+ const { composePath } = materializeComposeTemplate('hs');
254
+ const docker = new Docker();
255
+ const orch = new DockerOrchestrator(docker, config, walletManager, {
256
+ profile: 'hs',
257
+ composePath,
258
+ });
259
+ await orch.up([]); // apex-only (connector + townhouse-api)
260
+ ```
261
+
262
+ ### Connector Anon Requirement (HS Profile)
263
+
264
+ The HS profile's readiness gate calls `GET /admin/hs-hostname`. The
265
+ connector container MUST be configured with `anon.enabled: true` —
266
+ if anon is disabled, the endpoint returns 503 and the orchestrator
267
+ throws `OrchestratorError("connector is anon-disabled — set
268
+ anon.enabled: true in the connector config")`. Story 45.4's
269
+ `townhouse hs up` generates the connector config with `anon.enabled: true`
270
+ by default; manual configurations should mirror that setting.
271
+
272
+ ## HS Mode (Apex Install)
273
+
274
+ `townhouse hs up` is the one-command install for homelab operators. It boots the
275
+ apex stack (connector + townhouse-api) and publishes a `.anyone` hidden-service
276
+ address, writing the address to `~/.townhouse/host.json` as the final step.
277
+
278
+ ### First-run flow
279
+
280
+ ```bash
281
+ npx @toon-protocol/townhouse init # initialise config + wallet (one-time)
282
+ npx @toon-protocol/townhouse hs up # boot apex — prints "Apex live at <hostname>.anyone"
283
+ ```
284
+
285
+ On a cold image cache the command takes up to 5 minutes (image pull + anon
286
+ bootstrap). On subsequent runs with a warm cache, the HS bootstrap phase
287
+ (30–90 s) dominates.
288
+
289
+ ### Files written by `hs up`
290
+
291
+ | File | Mode | Purpose |
292
+ |------|------|---------|
293
+ | `~/.townhouse/config.yaml` | 0o600 | Townhouse config (written by `init`) |
294
+ | `~/.townhouse/wallet.enc` | 0o600 | Encrypted BIP-39 wallet (written by `init`) |
295
+ | `~/.townhouse/compose/townhouse-hs.yml` | 0o600 | Materialised HS compose template |
296
+ | `~/.townhouse/image-manifest.json` | 0o600 | Digest-pinned image manifest |
297
+ | `~/.townhouse/connector.yaml` | 0o600 | Connector config with `anon.enabled: true` |
298
+ | `~/.townhouse/host.json` | 0o600 | Published hostname + metadata |
299
+
300
+ `host.json` schema:
301
+ ```json
302
+ {
303
+ "hostname": "<onion>.anyone",
304
+ "publishedAt": "<ISO-8601>",
305
+ "connectorAdminUrl": "http://127.0.0.1:9401",
306
+ "townhouseApiUrl": "http://127.0.0.1:28090",
307
+ "writtenAt": "<ISO-8601>"
308
+ }
309
+ ```
310
+
311
+ ### Idempotent re-run
312
+
313
+ Re-running `townhouse hs up` against an already-running apex detects the
314
+ running connector, re-prints the hostname, and exits 0 without pulling images
315
+ or restarting containers. `~/.townhouse/host.json` is refreshed.
316
+
317
+ ### `hs down` vs. `hs down --rotate-keys`
318
+
319
+ | Command | Volumes | `host.json` | Next `hs up` |
320
+ |---------|---------|-------------|--------------|
321
+ | `townhouse hs down` | **Preserved** (`townhouse-hs-anon`) | Kept | **Same** `.anyone` address |
322
+ | `townhouse hs down --rotate-keys` | **Deleted** | Deleted | **New** `.anyone` address |
323
+
324
+ `--rotate-keys` prompts for confirmation when stdin is a TTY. When stdin is not
325
+ a TTY (CI, scripted), it proceeds without prompting.
326
+
327
+ ### Password sourcing
328
+
329
+ Resolution order:
330
+ 1. `--password <pw>` flag
331
+ 2. `TOWNHOUSE_WALLET_PASSWORD` environment variable
332
+ 3. Interactive prompt (only when `process.stdin.isTTY === true`)
333
+ 4. Exit 1 with an error message (non-interactive, no password provided)
334
+
335
+ ### Failure-state copy (UX-DR5)
336
+
337
+ | Class | Detection | Next step shown |
338
+ |-------|-----------|-----------------|
339
+ | anon-timeout | `HS hostname publication timeout` in error | `Re-run with DEBUG=townhouse:*` |
340
+ | anon-disabled | `anon-disabled (HTTP 503)` from probe | Edit `connector.yaml`, set `anon.enabled: true` |
341
+ | image-pull-failure | `failed to pull` / `pull access denied` in stderr | Check your network |
342
+ | port-collision | `address already in use` / `port is already allocated` in stderr | Stop the conflicting service |
343
+ | missing-docker-sock | `Cannot connect to the Docker daemon` / `docker CLI not found` | Start Docker |
344
+ | generic | Any other error | `Run with DEBUG=townhouse:*` |
345
+
233
346
  ## Running the townhouse as a hidden service (laptop)
234
347
 
235
348
  `docker-compose-townhouse-hs.yml` brings up the full operator stack —
@@ -384,3 +497,7 @@ but the connector at 3.3.x reads a discriminated union keyed on `type`
384
497
  defaulting to direct — operators toggling ATOR got direct traffic anyway.
385
498
  The current generator emits the correct `type: 'socks5'` shape with
386
499
  `externalUrl`, `managed`, and `managedOptions` per the connector contract.
500
+
501
+ ## Notes
502
+
503
+ `townhouse status --units=sats` exists as an undocumented power-user flag for Bitcoin-native operators. It converts the earnings block to integer sats using a CLI-supplied rate (`--rate <sats-per-usdc>`) or the `TOWNHOUSE_SATS_PER_USDC` environment variable; if neither is set, the command exits 1. There is no built-in price oracle — this is intentionally a manual conversion. USDC remains the canonical denomination across every other Townhouse surface (TUI hero band, drill subcommands like `townhouse peer` and `townhouse channels`); this flag is absent from `townhouse --help` per design decision D44-002.
@@ -0,0 +1,538 @@
1
+ import { createRequire } from 'module'; const require = createRequire(import.meta.url);
2
+
3
+ // ../../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/cryptoNode.js
4
+ import * as nc from "crypto";
5
+ var crypto = nc && typeof nc === "object" && "webcrypto" in nc ? nc.webcrypto : nc && typeof nc === "object" && "randomBytes" in nc ? nc : void 0;
6
+
7
+ // ../../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/utils.js
8
+ function isBytes(a) {
9
+ return a instanceof Uint8Array || ArrayBuffer.isView(a) && a.constructor.name === "Uint8Array";
10
+ }
11
+ function anumber(n) {
12
+ if (!Number.isSafeInteger(n) || n < 0)
13
+ throw new Error("positive integer expected, got " + n);
14
+ }
15
+ function abytes(b, ...lengths) {
16
+ if (!isBytes(b))
17
+ throw new Error("Uint8Array expected");
18
+ if (lengths.length > 0 && !lengths.includes(b.length))
19
+ throw new Error("Uint8Array expected of length " + lengths + ", got length=" + b.length);
20
+ }
21
+ function ahash(h) {
22
+ if (typeof h !== "function" || typeof h.create !== "function")
23
+ throw new Error("Hash should be wrapped by utils.createHasher");
24
+ anumber(h.outputLen);
25
+ anumber(h.blockLen);
26
+ }
27
+ function aexists(instance, checkFinished = true) {
28
+ if (instance.destroyed)
29
+ throw new Error("Hash instance has been destroyed");
30
+ if (checkFinished && instance.finished)
31
+ throw new Error("Hash#digest() has already been called");
32
+ }
33
+ function aoutput(out, instance) {
34
+ abytes(out);
35
+ const min = instance.outputLen;
36
+ if (out.length < min) {
37
+ throw new Error("digestInto() expects output buffer of length at least " + min);
38
+ }
39
+ }
40
+ function u32(arr) {
41
+ return new Uint32Array(arr.buffer, arr.byteOffset, Math.floor(arr.byteLength / 4));
42
+ }
43
+ function clean(...arrays) {
44
+ for (let i = 0; i < arrays.length; i++) {
45
+ arrays[i].fill(0);
46
+ }
47
+ }
48
+ function createView(arr) {
49
+ return new DataView(arr.buffer, arr.byteOffset, arr.byteLength);
50
+ }
51
+ function rotr(word, shift) {
52
+ return word << 32 - shift | word >>> shift;
53
+ }
54
+ var isLE = /* @__PURE__ */ (() => new Uint8Array(new Uint32Array([287454020]).buffer)[0] === 68)();
55
+ function byteSwap(word) {
56
+ return word << 24 & 4278190080 | word << 8 & 16711680 | word >>> 8 & 65280 | word >>> 24 & 255;
57
+ }
58
+ function byteSwap32(arr) {
59
+ for (let i = 0; i < arr.length; i++) {
60
+ arr[i] = byteSwap(arr[i]);
61
+ }
62
+ return arr;
63
+ }
64
+ var swap32IfBE = isLE ? (u) => u : byteSwap32;
65
+ var hasHexBuiltin = /* @__PURE__ */ (() => (
66
+ // @ts-ignore
67
+ typeof Uint8Array.from([]).toHex === "function" && typeof Uint8Array.fromHex === "function"
68
+ ))();
69
+ var hexes = /* @__PURE__ */ Array.from({ length: 256 }, (_, i) => i.toString(16).padStart(2, "0"));
70
+ function bytesToHex(bytes) {
71
+ abytes(bytes);
72
+ if (hasHexBuiltin)
73
+ return bytes.toHex();
74
+ let hex = "";
75
+ for (let i = 0; i < bytes.length; i++) {
76
+ hex += hexes[bytes[i]];
77
+ }
78
+ return hex;
79
+ }
80
+ var asciis = { _0: 48, _9: 57, A: 65, F: 70, a: 97, f: 102 };
81
+ function asciiToBase16(ch) {
82
+ if (ch >= asciis._0 && ch <= asciis._9)
83
+ return ch - asciis._0;
84
+ if (ch >= asciis.A && ch <= asciis.F)
85
+ return ch - (asciis.A - 10);
86
+ if (ch >= asciis.a && ch <= asciis.f)
87
+ return ch - (asciis.a - 10);
88
+ return;
89
+ }
90
+ function hexToBytes(hex) {
91
+ if (typeof hex !== "string")
92
+ throw new Error("hex string expected, got " + typeof hex);
93
+ if (hasHexBuiltin)
94
+ return Uint8Array.fromHex(hex);
95
+ const hl = hex.length;
96
+ const al = hl / 2;
97
+ if (hl % 2)
98
+ throw new Error("hex string expected, got unpadded hex of length " + hl);
99
+ const array = new Uint8Array(al);
100
+ for (let ai = 0, hi = 0; ai < al; ai++, hi += 2) {
101
+ const n1 = asciiToBase16(hex.charCodeAt(hi));
102
+ const n2 = asciiToBase16(hex.charCodeAt(hi + 1));
103
+ if (n1 === void 0 || n2 === void 0) {
104
+ const char = hex[hi] + hex[hi + 1];
105
+ throw new Error('hex string expected, got non-hex character "' + char + '" at index ' + hi);
106
+ }
107
+ array[ai] = n1 * 16 + n2;
108
+ }
109
+ return array;
110
+ }
111
+ function utf8ToBytes(str) {
112
+ if (typeof str !== "string")
113
+ throw new Error("string expected");
114
+ return new Uint8Array(new TextEncoder().encode(str));
115
+ }
116
+ function toBytes(data) {
117
+ if (typeof data === "string")
118
+ data = utf8ToBytes(data);
119
+ abytes(data);
120
+ return data;
121
+ }
122
+ function concatBytes(...arrays) {
123
+ let sum = 0;
124
+ for (let i = 0; i < arrays.length; i++) {
125
+ const a = arrays[i];
126
+ abytes(a);
127
+ sum += a.length;
128
+ }
129
+ const res = new Uint8Array(sum);
130
+ for (let i = 0, pad = 0; i < arrays.length; i++) {
131
+ const a = arrays[i];
132
+ res.set(a, pad);
133
+ pad += a.length;
134
+ }
135
+ return res;
136
+ }
137
+ var Hash = class {
138
+ };
139
+ function createHasher(hashCons) {
140
+ const hashC = (msg) => hashCons().update(toBytes(msg)).digest();
141
+ const tmp = hashCons();
142
+ hashC.outputLen = tmp.outputLen;
143
+ hashC.blockLen = tmp.blockLen;
144
+ hashC.create = () => hashCons();
145
+ return hashC;
146
+ }
147
+ function randomBytes(bytesLength = 32) {
148
+ if (crypto && typeof crypto.getRandomValues === "function") {
149
+ return crypto.getRandomValues(new Uint8Array(bytesLength));
150
+ }
151
+ if (crypto && typeof crypto.randomBytes === "function") {
152
+ return Uint8Array.from(crypto.randomBytes(bytesLength));
153
+ }
154
+ throw new Error("crypto.getRandomValues must be defined");
155
+ }
156
+
157
+ // ../../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/hmac.js
158
+ var HMAC = class extends Hash {
159
+ constructor(hash, _key) {
160
+ super();
161
+ this.finished = false;
162
+ this.destroyed = false;
163
+ ahash(hash);
164
+ const key = toBytes(_key);
165
+ this.iHash = hash.create();
166
+ if (typeof this.iHash.update !== "function")
167
+ throw new Error("Expected instance of class which extends utils.Hash");
168
+ this.blockLen = this.iHash.blockLen;
169
+ this.outputLen = this.iHash.outputLen;
170
+ const blockLen = this.blockLen;
171
+ const pad = new Uint8Array(blockLen);
172
+ pad.set(key.length > blockLen ? hash.create().update(key).digest() : key);
173
+ for (let i = 0; i < pad.length; i++)
174
+ pad[i] ^= 54;
175
+ this.iHash.update(pad);
176
+ this.oHash = hash.create();
177
+ for (let i = 0; i < pad.length; i++)
178
+ pad[i] ^= 54 ^ 92;
179
+ this.oHash.update(pad);
180
+ clean(pad);
181
+ }
182
+ update(buf) {
183
+ aexists(this);
184
+ this.iHash.update(buf);
185
+ return this;
186
+ }
187
+ digestInto(out) {
188
+ aexists(this);
189
+ abytes(out, this.outputLen);
190
+ this.finished = true;
191
+ this.iHash.digestInto(out);
192
+ this.oHash.update(out);
193
+ this.oHash.digestInto(out);
194
+ this.destroy();
195
+ }
196
+ digest() {
197
+ const out = new Uint8Array(this.oHash.outputLen);
198
+ this.digestInto(out);
199
+ return out;
200
+ }
201
+ _cloneInto(to) {
202
+ to || (to = Object.create(Object.getPrototypeOf(this), {}));
203
+ const { oHash, iHash, finished, destroyed, blockLen, outputLen } = this;
204
+ to = to;
205
+ to.finished = finished;
206
+ to.destroyed = destroyed;
207
+ to.blockLen = blockLen;
208
+ to.outputLen = outputLen;
209
+ to.oHash = oHash._cloneInto(to.oHash);
210
+ to.iHash = iHash._cloneInto(to.iHash);
211
+ return to;
212
+ }
213
+ clone() {
214
+ return this._cloneInto();
215
+ }
216
+ destroy() {
217
+ this.destroyed = true;
218
+ this.oHash.destroy();
219
+ this.iHash.destroy();
220
+ }
221
+ };
222
+ var hmac = (hash, key, message) => new HMAC(hash, key).update(message).digest();
223
+ hmac.create = (hash, key) => new HMAC(hash, key);
224
+
225
+ // ../../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/_md.js
226
+ function setBigUint64(view, byteOffset, value, isLE2) {
227
+ if (typeof view.setBigUint64 === "function")
228
+ return view.setBigUint64(byteOffset, value, isLE2);
229
+ const _32n2 = BigInt(32);
230
+ const _u32_max = BigInt(4294967295);
231
+ const wh = Number(value >> _32n2 & _u32_max);
232
+ const wl = Number(value & _u32_max);
233
+ const h = isLE2 ? 4 : 0;
234
+ const l = isLE2 ? 0 : 4;
235
+ view.setUint32(byteOffset + h, wh, isLE2);
236
+ view.setUint32(byteOffset + l, wl, isLE2);
237
+ }
238
+ function Chi(a, b, c) {
239
+ return a & b ^ ~a & c;
240
+ }
241
+ function Maj(a, b, c) {
242
+ return a & b ^ a & c ^ b & c;
243
+ }
244
+ var HashMD = class extends Hash {
245
+ constructor(blockLen, outputLen, padOffset, isLE2) {
246
+ super();
247
+ this.finished = false;
248
+ this.length = 0;
249
+ this.pos = 0;
250
+ this.destroyed = false;
251
+ this.blockLen = blockLen;
252
+ this.outputLen = outputLen;
253
+ this.padOffset = padOffset;
254
+ this.isLE = isLE2;
255
+ this.buffer = new Uint8Array(blockLen);
256
+ this.view = createView(this.buffer);
257
+ }
258
+ update(data) {
259
+ aexists(this);
260
+ data = toBytes(data);
261
+ abytes(data);
262
+ const { view, buffer, blockLen } = this;
263
+ const len = data.length;
264
+ for (let pos = 0; pos < len; ) {
265
+ const take = Math.min(blockLen - this.pos, len - pos);
266
+ if (take === blockLen) {
267
+ const dataView = createView(data);
268
+ for (; blockLen <= len - pos; pos += blockLen)
269
+ this.process(dataView, pos);
270
+ continue;
271
+ }
272
+ buffer.set(data.subarray(pos, pos + take), this.pos);
273
+ this.pos += take;
274
+ pos += take;
275
+ if (this.pos === blockLen) {
276
+ this.process(view, 0);
277
+ this.pos = 0;
278
+ }
279
+ }
280
+ this.length += data.length;
281
+ this.roundClean();
282
+ return this;
283
+ }
284
+ digestInto(out) {
285
+ aexists(this);
286
+ aoutput(out, this);
287
+ this.finished = true;
288
+ const { buffer, view, blockLen, isLE: isLE2 } = this;
289
+ let { pos } = this;
290
+ buffer[pos++] = 128;
291
+ clean(this.buffer.subarray(pos));
292
+ if (this.padOffset > blockLen - pos) {
293
+ this.process(view, 0);
294
+ pos = 0;
295
+ }
296
+ for (let i = pos; i < blockLen; i++)
297
+ buffer[i] = 0;
298
+ setBigUint64(view, blockLen - 8, BigInt(this.length * 8), isLE2);
299
+ this.process(view, 0);
300
+ const oview = createView(out);
301
+ const len = this.outputLen;
302
+ if (len % 4)
303
+ throw new Error("_sha2: outputLen should be aligned to 32bit");
304
+ const outLen = len / 4;
305
+ const state = this.get();
306
+ if (outLen > state.length)
307
+ throw new Error("_sha2: outputLen bigger than state");
308
+ for (let i = 0; i < outLen; i++)
309
+ oview.setUint32(4 * i, state[i], isLE2);
310
+ }
311
+ digest() {
312
+ const { buffer, outputLen } = this;
313
+ this.digestInto(buffer);
314
+ const res = buffer.slice(0, outputLen);
315
+ this.destroy();
316
+ return res;
317
+ }
318
+ _cloneInto(to) {
319
+ to || (to = new this.constructor());
320
+ to.set(...this.get());
321
+ const { blockLen, buffer, length, finished, destroyed, pos } = this;
322
+ to.destroyed = destroyed;
323
+ to.finished = finished;
324
+ to.length = length;
325
+ to.pos = pos;
326
+ if (length % blockLen)
327
+ to.buffer.set(buffer);
328
+ return to;
329
+ }
330
+ clone() {
331
+ return this._cloneInto();
332
+ }
333
+ };
334
+ var SHA256_IV = /* @__PURE__ */ Uint32Array.from([
335
+ 1779033703,
336
+ 3144134277,
337
+ 1013904242,
338
+ 2773480762,
339
+ 1359893119,
340
+ 2600822924,
341
+ 528734635,
342
+ 1541459225
343
+ ]);
344
+
345
+ // ../../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/_u64.js
346
+ var U32_MASK64 = /* @__PURE__ */ BigInt(2 ** 32 - 1);
347
+ var _32n = /* @__PURE__ */ BigInt(32);
348
+ function fromBig(n, le = false) {
349
+ if (le)
350
+ return { h: Number(n & U32_MASK64), l: Number(n >> _32n & U32_MASK64) };
351
+ return { h: Number(n >> _32n & U32_MASK64) | 0, l: Number(n & U32_MASK64) | 0 };
352
+ }
353
+ function split(lst, le = false) {
354
+ const len = lst.length;
355
+ let Ah = new Uint32Array(len);
356
+ let Al = new Uint32Array(len);
357
+ for (let i = 0; i < len; i++) {
358
+ const { h, l } = fromBig(lst[i], le);
359
+ [Ah[i], Al[i]] = [h, l];
360
+ }
361
+ return [Ah, Al];
362
+ }
363
+ var rotlSH = (h, l, s) => h << s | l >>> 32 - s;
364
+ var rotlSL = (h, l, s) => l << s | h >>> 32 - s;
365
+ var rotlBH = (h, l, s) => l << s - 32 | h >>> 64 - s;
366
+ var rotlBL = (h, l, s) => h << s - 32 | l >>> 64 - s;
367
+
368
+ // ../../node_modules/.pnpm/@noble+hashes@1.8.0/node_modules/@noble/hashes/esm/sha2.js
369
+ var SHA256_K = /* @__PURE__ */ Uint32Array.from([
370
+ 1116352408,
371
+ 1899447441,
372
+ 3049323471,
373
+ 3921009573,
374
+ 961987163,
375
+ 1508970993,
376
+ 2453635748,
377
+ 2870763221,
378
+ 3624381080,
379
+ 310598401,
380
+ 607225278,
381
+ 1426881987,
382
+ 1925078388,
383
+ 2162078206,
384
+ 2614888103,
385
+ 3248222580,
386
+ 3835390401,
387
+ 4022224774,
388
+ 264347078,
389
+ 604807628,
390
+ 770255983,
391
+ 1249150122,
392
+ 1555081692,
393
+ 1996064986,
394
+ 2554220882,
395
+ 2821834349,
396
+ 2952996808,
397
+ 3210313671,
398
+ 3336571891,
399
+ 3584528711,
400
+ 113926993,
401
+ 338241895,
402
+ 666307205,
403
+ 773529912,
404
+ 1294757372,
405
+ 1396182291,
406
+ 1695183700,
407
+ 1986661051,
408
+ 2177026350,
409
+ 2456956037,
410
+ 2730485921,
411
+ 2820302411,
412
+ 3259730800,
413
+ 3345764771,
414
+ 3516065817,
415
+ 3600352804,
416
+ 4094571909,
417
+ 275423344,
418
+ 430227734,
419
+ 506948616,
420
+ 659060556,
421
+ 883997877,
422
+ 958139571,
423
+ 1322822218,
424
+ 1537002063,
425
+ 1747873779,
426
+ 1955562222,
427
+ 2024104815,
428
+ 2227730452,
429
+ 2361852424,
430
+ 2428436474,
431
+ 2756734187,
432
+ 3204031479,
433
+ 3329325298
434
+ ]);
435
+ var SHA256_W = /* @__PURE__ */ new Uint32Array(64);
436
+ var SHA256 = class extends HashMD {
437
+ constructor(outputLen = 32) {
438
+ super(64, outputLen, 8, false);
439
+ this.A = SHA256_IV[0] | 0;
440
+ this.B = SHA256_IV[1] | 0;
441
+ this.C = SHA256_IV[2] | 0;
442
+ this.D = SHA256_IV[3] | 0;
443
+ this.E = SHA256_IV[4] | 0;
444
+ this.F = SHA256_IV[5] | 0;
445
+ this.G = SHA256_IV[6] | 0;
446
+ this.H = SHA256_IV[7] | 0;
447
+ }
448
+ get() {
449
+ const { A, B, C, D, E, F, G, H } = this;
450
+ return [A, B, C, D, E, F, G, H];
451
+ }
452
+ // prettier-ignore
453
+ set(A, B, C, D, E, F, G, H) {
454
+ this.A = A | 0;
455
+ this.B = B | 0;
456
+ this.C = C | 0;
457
+ this.D = D | 0;
458
+ this.E = E | 0;
459
+ this.F = F | 0;
460
+ this.G = G | 0;
461
+ this.H = H | 0;
462
+ }
463
+ process(view, offset) {
464
+ for (let i = 0; i < 16; i++, offset += 4)
465
+ SHA256_W[i] = view.getUint32(offset, false);
466
+ for (let i = 16; i < 64; i++) {
467
+ const W15 = SHA256_W[i - 15];
468
+ const W2 = SHA256_W[i - 2];
469
+ const s0 = rotr(W15, 7) ^ rotr(W15, 18) ^ W15 >>> 3;
470
+ const s1 = rotr(W2, 17) ^ rotr(W2, 19) ^ W2 >>> 10;
471
+ SHA256_W[i] = s1 + SHA256_W[i - 7] + s0 + SHA256_W[i - 16] | 0;
472
+ }
473
+ let { A, B, C, D, E, F, G, H } = this;
474
+ for (let i = 0; i < 64; i++) {
475
+ const sigma1 = rotr(E, 6) ^ rotr(E, 11) ^ rotr(E, 25);
476
+ const T1 = H + sigma1 + Chi(E, F, G) + SHA256_K[i] + SHA256_W[i] | 0;
477
+ const sigma0 = rotr(A, 2) ^ rotr(A, 13) ^ rotr(A, 22);
478
+ const T2 = sigma0 + Maj(A, B, C) | 0;
479
+ H = G;
480
+ G = F;
481
+ F = E;
482
+ E = D + T1 | 0;
483
+ D = C;
484
+ C = B;
485
+ B = A;
486
+ A = T1 + T2 | 0;
487
+ }
488
+ A = A + this.A | 0;
489
+ B = B + this.B | 0;
490
+ C = C + this.C | 0;
491
+ D = D + this.D | 0;
492
+ E = E + this.E | 0;
493
+ F = F + this.F | 0;
494
+ G = G + this.G | 0;
495
+ H = H + this.H | 0;
496
+ this.set(A, B, C, D, E, F, G, H);
497
+ }
498
+ roundClean() {
499
+ clean(SHA256_W);
500
+ }
501
+ destroy() {
502
+ this.set(0, 0, 0, 0, 0, 0, 0, 0);
503
+ clean(this.buffer);
504
+ }
505
+ };
506
+ var sha256 = /* @__PURE__ */ createHasher(() => new SHA256());
507
+
508
+ export {
509
+ isBytes,
510
+ anumber,
511
+ abytes,
512
+ ahash,
513
+ aexists,
514
+ aoutput,
515
+ u32,
516
+ clean,
517
+ swap32IfBE,
518
+ bytesToHex,
519
+ hexToBytes,
520
+ toBytes,
521
+ concatBytes,
522
+ Hash,
523
+ createHasher,
524
+ randomBytes,
525
+ split,
526
+ rotlSH,
527
+ rotlSL,
528
+ rotlBH,
529
+ rotlBL,
530
+ sha256,
531
+ hmac
532
+ };
533
+ /*! Bundled license information:
534
+
535
+ @noble/hashes/esm/utils.js:
536
+ (*! noble-hashes - MIT License (c) 2022 Paul Miller (paulmillr.com) *)
537
+ */
538
+ //# sourceMappingURL=chunk-5O4SBV5O.js.map