@inversealtruism/csd-codec 0.1.1 → 0.1.3

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 ADDED
@@ -0,0 +1,11 @@
1
+ # @inversealtruism/csd-codec
2
+
3
+ bincode codec (serialize/deserialize), txid, sighash (CSD_SIG_V1), header serialize/hash, compact-bits↔target, merkle proofs, content-addressing. Byte-identical to the Rust node (golden-vector + live-chain gated).
4
+
5
+ Part of the [Compute Substrate SDK](https://github.com/InverseAltruism/csd-sdk) (L0). Zero `Buffer` — runs in Node, browsers, and MV3 service workers. Deps: `@noble/*` only.
6
+
7
+ ```
8
+ npm i @inversealtruism/csd-codec
9
+ ```
10
+
11
+ See the [repo README](https://github.com/InverseAltruism/csd-sdk#readme) and [examples/quickstart.mjs](https://github.com/InverseAltruism/csd-sdk/blob/master/examples/quickstart.mjs) for usage. MIT.
package/dist/index.cjs CHANGED
@@ -91,8 +91,20 @@ function u32(n) {
91
91
  return b;
92
92
  }
93
93
  function u64(n) {
94
+ let v;
95
+ if (typeof n === "bigint") {
96
+ v = n;
97
+ } else {
98
+ if (!Number.isSafeInteger(n)) {
99
+ throw new Error(`u64: unsafe number ${n} \u2014 pass values \u2265 2^53 (or negatives) as bigint`);
100
+ }
101
+ v = BigInt(n);
102
+ }
103
+ if (v < 0n || v > 0xffffffffffffffffn) {
104
+ throw new Error(`u64: value ${v} out of range [0, 2^64)`);
105
+ }
94
106
  const b = new Uint8Array(8);
95
- new DataView(b.buffer).setBigUint64(0, BigInt(n), true);
107
+ new DataView(b.buffer).setBigUint64(0, v, true);
96
108
  return b;
97
109
  }
98
110
  var lenBytes = (b) => (0, import_utils.concatBytes)(u64(b.length), b);
@@ -344,7 +356,7 @@ function verifyMerkleProof(txidHex, pos, branchHex, merkleRootHex) {
344
356
  cur = sha256d(buf);
345
357
  idx >>= 1;
346
358
  }
347
- return hx(cur).toLowerCase() === merkleRootHex.toLowerCase();
359
+ return hx(cur) === hx(hb(merkleRootHex));
348
360
  }
349
361
  function merkleBranch(txidsHex, pos) {
350
362
  let layer = txidsHex.map(hb);
@@ -372,11 +384,16 @@ function merkleBranch(txidsHex, pos) {
372
384
  // src/content.ts
373
385
  var import_sha2563 = require("@noble/hashes/sha256");
374
386
  var import_utils4 = require("@noble/hashes/utils");
375
- function canonicalJson(v) {
376
- if (v === null || typeof v !== "object") return JSON.stringify(v);
377
- if (Array.isArray(v)) return "[" + v.map(canonicalJson).join(",") + "]";
387
+ var MAX_DEPTH = 256;
388
+ function canonicalJson(v, depth = 0) {
389
+ if (depth > MAX_DEPTH) throw new Error("canonicalJson: max nesting depth exceeded");
390
+ if (v === null || typeof v !== "object") {
391
+ if (v === void 0) return "null";
392
+ return JSON.stringify(v);
393
+ }
394
+ if (Array.isArray(v)) return "[" + v.map((x) => canonicalJson(x, depth + 1)).join(",") + "]";
378
395
  const o = v;
379
- return "{" + Object.keys(o).sort().map((k) => JSON.stringify(k) + ":" + canonicalJson(o[k])).join(",") + "}";
396
+ return "{" + Object.keys(o).sort().filter((k) => o[k] !== void 0).map((k) => JSON.stringify(k) + ":" + canonicalJson(o[k], depth + 1)).join(",") + "}";
380
397
  }
381
398
  function payloadHash(content) {
382
399
  return "0x" + (0, import_utils4.bytesToHex)((0, import_sha2563.sha256)((0, import_utils4.utf8ToBytes)(canonicalJson(content))));
package/dist/index.d.cts CHANGED
@@ -124,7 +124,7 @@ declare function verifyMerkleProof(txidHex: string, pos: number, branchHex: stri
124
124
  /** Build the merkle branch for tx at index `pos` from the full ordered txid list. */
125
125
  declare function merkleBranch(txidsHex: string[], pos: number): string[];
126
126
 
127
- declare function canonicalJson(v: unknown): string;
127
+ declare function canonicalJson(v: unknown, depth?: number): string;
128
128
  /** payload_hash for a content record (0x-hex sha256 of its canonical JSON). */
129
129
  declare function payloadHash(content: unknown): string;
130
130
  /** Verify served bytes match an on-chain payload_hash (self-certification). */
package/dist/index.d.ts CHANGED
@@ -124,7 +124,7 @@ declare function verifyMerkleProof(txidHex: string, pos: number, branchHex: stri
124
124
  /** Build the merkle branch for tx at index `pos` from the full ordered txid list. */
125
125
  declare function merkleBranch(txidsHex: string[], pos: number): string[];
126
126
 
127
- declare function canonicalJson(v: unknown): string;
127
+ declare function canonicalJson(v: unknown, depth?: number): string;
128
128
  /** payload_hash for a content record (0x-hex sha256 of its canonical JSON). */
129
129
  declare function payloadHash(content: unknown): string;
130
130
  /** Verify served bytes match an on-chain payload_hash (self-certification). */
package/dist/index.js CHANGED
@@ -11,8 +11,20 @@ function u32(n) {
11
11
  return b;
12
12
  }
13
13
  function u64(n) {
14
+ let v;
15
+ if (typeof n === "bigint") {
16
+ v = n;
17
+ } else {
18
+ if (!Number.isSafeInteger(n)) {
19
+ throw new Error(`u64: unsafe number ${n} \u2014 pass values \u2265 2^53 (or negatives) as bigint`);
20
+ }
21
+ v = BigInt(n);
22
+ }
23
+ if (v < 0n || v > 0xffffffffffffffffn) {
24
+ throw new Error(`u64: value ${v} out of range [0, 2^64)`);
25
+ }
14
26
  const b = new Uint8Array(8);
15
- new DataView(b.buffer).setBigUint64(0, BigInt(n), true);
27
+ new DataView(b.buffer).setBigUint64(0, v, true);
16
28
  return b;
17
29
  }
18
30
  var lenBytes = (b) => concatBytes(u64(b.length), b);
@@ -264,7 +276,7 @@ function verifyMerkleProof(txidHex, pos, branchHex, merkleRootHex) {
264
276
  cur = sha256d(buf);
265
277
  idx >>= 1;
266
278
  }
267
- return hx(cur).toLowerCase() === merkleRootHex.toLowerCase();
279
+ return hx(cur) === hx(hb(merkleRootHex));
268
280
  }
269
281
  function merkleBranch(txidsHex, pos) {
270
282
  let layer = txidsHex.map(hb);
@@ -292,11 +304,16 @@ function merkleBranch(txidsHex, pos) {
292
304
  // src/content.ts
293
305
  import { sha256 as sha2563 } from "@noble/hashes/sha256";
294
306
  import { bytesToHex as bytesToHex2, utf8ToBytes as utf8ToBytes3 } from "@noble/hashes/utils";
295
- function canonicalJson(v) {
296
- if (v === null || typeof v !== "object") return JSON.stringify(v);
297
- if (Array.isArray(v)) return "[" + v.map(canonicalJson).join(",") + "]";
307
+ var MAX_DEPTH = 256;
308
+ function canonicalJson(v, depth = 0) {
309
+ if (depth > MAX_DEPTH) throw new Error("canonicalJson: max nesting depth exceeded");
310
+ if (v === null || typeof v !== "object") {
311
+ if (v === void 0) return "null";
312
+ return JSON.stringify(v);
313
+ }
314
+ if (Array.isArray(v)) return "[" + v.map((x) => canonicalJson(x, depth + 1)).join(",") + "]";
298
315
  const o = v;
299
- return "{" + Object.keys(o).sort().map((k) => JSON.stringify(k) + ":" + canonicalJson(o[k])).join(",") + "}";
316
+ return "{" + Object.keys(o).sort().filter((k) => o[k] !== void 0).map((k) => JSON.stringify(k) + ":" + canonicalJson(o[k], depth + 1)).join(",") + "}";
300
317
  }
301
318
  function payloadHash(content) {
302
319
  return "0x" + bytesToHex2(sha2563(utf8ToBytes3(canonicalJson(content))));
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@inversealtruism/csd-codec",
3
- "version": "0.1.1",
3
+ "version": "0.1.3",
4
4
  "description": "Compute Substrate consensus codec — bincode (fixint-LE) serialize/deserialize, txid, sighash (CSD_SIG_V1), header serialize/hash, compact-bits→target, merkle. Byte-identical to the Rust node (golden-vector-gated).",
5
5
  "type": "module",
6
6
  "main": "./dist/index.cjs",
@@ -15,13 +15,14 @@
15
15
  },
16
16
  "files": [
17
17
  "dist",
18
- "LICENSE"
18
+ "LICENSE",
19
+ "README.md"
19
20
  ],
20
21
  "dependencies": {
21
22
  "@noble/hashes": "1.8.0"
22
23
  },
23
24
  "devDependencies": {
24
- "@inversealtruism/csd-vectors": "0.1.1"
25
+ "@inversealtruism/csd-vectors": "0.1.3"
25
26
  },
26
27
  "license": "MIT",
27
28
  "sideEffects": false,