@vultisig/core-chain 1.2.2 → 1.3.0

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.
Files changed (57) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/dist/chains/cardano/cip30/buildCardanoValue.d.ts +18 -0
  3. package/dist/chains/cardano/cip30/buildCardanoValue.d.ts.map +1 -0
  4. package/dist/chains/cardano/cip30/buildCardanoValue.js +72 -0
  5. package/dist/chains/cardano/cip30/buildCardanoValue.js.map +1 -0
  6. package/dist/chains/cardano/cip30/buildCardanoWitnessSet.d.ts +10 -0
  7. package/dist/chains/cardano/cip30/buildCardanoWitnessSet.d.ts.map +1 -0
  8. package/dist/chains/cardano/cip30/buildCardanoWitnessSet.js +15 -0
  9. package/dist/chains/cardano/cip30/buildCardanoWitnessSet.js.map +1 -0
  10. package/dist/chains/cardano/cip30/buildCoseStructures.d.ts +45 -0
  11. package/dist/chains/cardano/cip30/buildCoseStructures.d.ts.map +1 -0
  12. package/dist/chains/cardano/cip30/buildCoseStructures.js +70 -0
  13. package/dist/chains/cardano/cip30/buildCoseStructures.js.map +1 -0
  14. package/dist/chains/cardano/cip30/cardanoAddressBytes.d.ts +6 -0
  15. package/dist/chains/cardano/cip30/cardanoAddressBytes.d.ts.map +1 -0
  16. package/dist/chains/cardano/cip30/cardanoAddressBytes.js +12 -0
  17. package/dist/chains/cardano/cip30/cardanoAddressBytes.js.map +1 -0
  18. package/dist/chains/cardano/cip30/cardanoCborPrimitives.d.ts +53 -0
  19. package/dist/chains/cardano/cip30/cardanoCborPrimitives.d.ts.map +1 -0
  20. package/dist/chains/cardano/cip30/cardanoCborPrimitives.js +91 -0
  21. package/dist/chains/cardano/cip30/cardanoCborPrimitives.js.map +1 -0
  22. package/dist/chains/cardano/cip30/cardanoTxBodyHash.d.ts +6 -0
  23. package/dist/chains/cardano/cip30/cardanoTxBodyHash.d.ts.map +1 -0
  24. package/dist/chains/cardano/cip30/cardanoTxBodyHash.js +55 -0
  25. package/dist/chains/cardano/cip30/cardanoTxBodyHash.js.map +1 -0
  26. package/dist/chains/cardano/cip30/cborEncoder.d.ts +11 -0
  27. package/dist/chains/cardano/cip30/cborEncoder.d.ts.map +1 -0
  28. package/dist/chains/cardano/cip30/cborEncoder.js +14 -0
  29. package/dist/chains/cardano/cip30/cborEncoder.js.map +1 -0
  30. package/dist/chains/cardano/cip30/cborSkip.d.ts +13 -0
  31. package/dist/chains/cardano/cip30/cborSkip.d.ts.map +1 -0
  32. package/dist/chains/cardano/cip30/cborSkip.js +108 -0
  33. package/dist/chains/cardano/cip30/cborSkip.js.map +1 -0
  34. package/dist/chains/cardano/cip30/decodeCardanoAmountValue.d.ts +16 -0
  35. package/dist/chains/cardano/cip30/decodeCardanoAmountValue.d.ts.map +1 -0
  36. package/dist/chains/cardano/cip30/decodeCardanoAmountValue.js +72 -0
  37. package/dist/chains/cardano/cip30/decodeCardanoAmountValue.js.map +1 -0
  38. package/dist/chains/cardano/cip30/encodeCardanoUnspentOutput.d.ts +16 -0
  39. package/dist/chains/cardano/cip30/encodeCardanoUnspentOutput.d.ts.map +1 -0
  40. package/dist/chains/cardano/cip30/encodeCardanoUnspentOutput.js +23 -0
  41. package/dist/chains/cardano/cip30/encodeCardanoUnspentOutput.js.map +1 -0
  42. package/dist/chains/cardano/cip30/encodeCardanoValue.d.ts +4 -0
  43. package/dist/chains/cardano/cip30/encodeCardanoValue.d.ts.map +1 -0
  44. package/dist/chains/cardano/cip30/encodeCardanoValue.js +5 -0
  45. package/dist/chains/cardano/cip30/encodeCardanoValue.js.map +1 -0
  46. package/dist/chains/cardano/cip30/selectCardanoUtxosByLovelace.d.ts +24 -0
  47. package/dist/chains/cardano/cip30/selectCardanoUtxosByLovelace.d.ts.map +1 -0
  48. package/dist/chains/cardano/cip30/selectCardanoUtxosByLovelace.js +23 -0
  49. package/dist/chains/cardano/cip30/selectCardanoUtxosByLovelace.js.map +1 -0
  50. package/dist/chains/cardano/submit/submitCardanoCbor.d.ts +18 -0
  51. package/dist/chains/cardano/submit/submitCardanoCbor.d.ts.map +1 -0
  52. package/dist/chains/cardano/submit/submitCardanoCbor.js +71 -0
  53. package/dist/chains/cardano/submit/submitCardanoCbor.js.map +1 -0
  54. package/dist/tx/broadcast/resolvers/cardano.d.ts.map +1 -1
  55. package/dist/tx/broadcast/resolvers/cardano.js +11 -63
  56. package/dist/tx/broadcast/resolvers/cardano.js.map +1 -1
  57. package/package.json +66 -1
package/CHANGELOG.md CHANGED
@@ -1,5 +1,25 @@
1
1
  # @vultisig/core-chain
2
2
 
3
+ ## 1.3.0
4
+
5
+ ### Minor Changes
6
+
7
+ - [#291](https://github.com/vultisig/vultisig-sdk/pull/291) [`824e58c`](https://github.com/vultisig/vultisig-sdk/commit/824e58cded1ca80e29a2e19e2bda6957f2da71ad) Thanks [@Ehsan-saradar](https://github.com/Ehsan-saradar)! - feat(chain/cardano): CIP-30 CBOR helpers and a reusable submit helper
8
+
9
+ Adds primitives needed by CIP-30 dApp-wallet bridges on top of `@vultisig/core-chain`:
10
+ - `chains/cardano/cip30/cardanoAddressBytes` — decode a Cardano bech32 address into raw bytes (CIP-30 carries addresses as hex of these bytes, not bech32).
11
+ - `chains/cardano/cip30/cardanoTxBodyHash` — blake2b-256 of the transaction body, extracted from the full tx CBOR **without re-encoding** so the txid matches what dApps sign off on.
12
+ - `chains/cardano/cip30/buildCardanoValue` / `encodeCardanoValue` — build and CBOR-encode a Cardano `value` (coin + multiasset) for `getBalance()`.
13
+ - `chains/cardano/cip30/encodeCardanoUnspentOutput` — CBOR-encode a `transaction_unspent_output` for `getUtxos()`.
14
+ - `chains/cardano/cip30/decodeCardanoAmountValue` — decode the CBOR `value` argument passed to `getUtxos(amount)` into `{ lovelace, hasAssets }`. Returns `null` on malformed input so callers can fall back to returning all UTXOs.
15
+ - `chains/cardano/cip30/selectCardanoUtxosByLovelace` — greedy largest-first coin selection by lovelace; returns `null` when the full set is insufficient. Used by CIP-30 `getUtxos` coin selection.
16
+ - `chains/cardano/cip30/buildCardanoWitnessSet` — CBOR witness set returned by CIP-30 `signTx`.
17
+ - `chains/cardano/cip30/buildCoseStructures` — CIP-8 / COSE_Sign1 + COSE_Key builders for `signData`.
18
+ - `chains/cardano/cip30/cardanoCborPrimitives`, `cborEncoder`, `cborSkip` — minimal, Cardano-correct CBOR primitives (hand-rolled for the integer/bytes-keyed maps that `cbor-x` can't produce, and a byte-range walker used by `cardanoTxBodyHash`).
19
+ - `chains/cardano/submit/submitCardanoCbor` — low-level Cardano broadcast helper that exposes `{ txHash, errorMessage, rpcErrorCode, rawResponse }` so callers can distinguish already-committed (Ogmios code 3117), mempool conflicts, etc.
20
+
21
+ The existing `broadcastCardanoTx` resolver is refactored to delegate to `submitCardanoCbor`, preserving the already-committed fallback behavior.
22
+
3
23
  ## 1.2.2
4
24
 
5
25
  ### Patch Changes
@@ -0,0 +1,18 @@
1
+ /** Minimal shape of a native-token holding, as returned by Koios. */
2
+ export type CardanoNativeAsset = {
3
+ policy_id: string;
4
+ asset_name: string;
5
+ quantity: string;
6
+ };
7
+ /**
8
+ * Build the in-memory tree representing a Cardano `value` per the CDDL:
9
+ *
10
+ * value = coin / [coin, multiasset<uint>]
11
+ * multiasset<a> = { * policy_id => { * asset_name => a } }
12
+ *
13
+ * The returned structure is fed to the shared `cardanoCborEncoder`; when
14
+ * the UTXO carries no native tokens the result is the lovelace uint itself.
15
+ * Duplicated (policy, asset_name) entries are summed.
16
+ */
17
+ export declare const buildCardanoValue: (lovelace: bigint, assets: readonly CardanoNativeAsset[]) => bigint | [bigint, Map<Uint8Array, Map<Uint8Array, bigint>>];
18
+ //# sourceMappingURL=buildCardanoValue.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"buildCardanoValue.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/buildCardanoValue.ts"],"names":[],"mappings":"AAEA,qEAAqE;AACrE,MAAM,MAAM,kBAAkB,GAAG;IAC/B,SAAS,EAAE,MAAM,CAAA;IACjB,UAAU,EAAE,MAAM,CAAA;IAClB,QAAQ,EAAE,MAAM,CAAA;CACjB,CAAA;AAkCD;;;;;;;;;GASG;AACH,eAAO,MAAM,iBAAiB,GAC5B,UAAU,MAAM,EAChB,QAAQ,SAAS,kBAAkB,EAAE,KACpC,MAAM,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,UAAU,EAAE,GAAG,CAAC,UAAU,EAAE,MAAM,CAAC,CAAC,CA4C5D,CAAA"}
@@ -0,0 +1,72 @@
1
+ import { stripHexPrefix } from '@vultisig/lib-utils/hex/stripHexPrefix';
2
+ const hexPattern = /^[0-9a-fA-F]*$/;
3
+ const hexToBytes = (hex) => Uint8Array.from(Buffer.from(stripHexPrefix(hex), 'hex'));
4
+ const assertEvenHex = (field, value) => {
5
+ const stripped = stripHexPrefix(value);
6
+ if (stripped.length === 0 || stripped.length % 2 !== 0 || !hexPattern.test(stripped)) {
7
+ throw new Error(`buildCardanoValue: ${field} must be non-empty even-length hex, got ${JSON.stringify(value)}`);
8
+ }
9
+ };
10
+ const assertNonNegativeQuantity = (value) => {
11
+ const parsed = attemptBigInt(value);
12
+ if (parsed === null || parsed < 0n) {
13
+ throw new Error(`buildCardanoValue: quantity must be a non-negative integer, got ${JSON.stringify(value)}`);
14
+ }
15
+ return parsed;
16
+ };
17
+ const attemptBigInt = (value) => {
18
+ try {
19
+ return BigInt(value);
20
+ }
21
+ catch {
22
+ return null;
23
+ }
24
+ };
25
+ /**
26
+ * Build the in-memory tree representing a Cardano `value` per the CDDL:
27
+ *
28
+ * value = coin / [coin, multiasset<uint>]
29
+ * multiasset<a> = { * policy_id => { * asset_name => a } }
30
+ *
31
+ * The returned structure is fed to the shared `cardanoCborEncoder`; when
32
+ * the UTXO carries no native tokens the result is the lovelace uint itself.
33
+ * Duplicated (policy, asset_name) entries are summed.
34
+ */
35
+ export const buildCardanoValue = (lovelace, assets) => {
36
+ if (assets.length === 0)
37
+ return lovelace;
38
+ const byPolicy = new Map();
39
+ for (const a of assets) {
40
+ assertEvenHex('policy_id', a.policy_id);
41
+ // asset_name may legitimately be empty (per-policy "default" asset), so
42
+ // only validate the hex shape when a name is provided.
43
+ if (a.asset_name.length > 0) {
44
+ const stripped = stripHexPrefix(a.asset_name);
45
+ if (stripped.length % 2 !== 0 || !hexPattern.test(stripped)) {
46
+ throw new Error(`buildCardanoValue: asset_name must be even-length hex, got ${JSON.stringify(a.asset_name)}`);
47
+ }
48
+ }
49
+ const quantity = assertNonNegativeQuantity(a.quantity);
50
+ const policyKey = a.policy_id.toLowerCase();
51
+ let bucket = byPolicy.get(policyKey);
52
+ if (!bucket) {
53
+ bucket = { policy: hexToBytes(a.policy_id), byName: new Map() };
54
+ byPolicy.set(policyKey, bucket);
55
+ }
56
+ const nameKey = a.asset_name.toLowerCase();
57
+ const prior = bucket.byName.get(nameKey);
58
+ bucket.byName.set(nameKey, {
59
+ name: hexToBytes(a.asset_name),
60
+ qty: (prior?.qty ?? 0n) + quantity,
61
+ });
62
+ }
63
+ const multiasset = new Map();
64
+ for (const { policy, byName } of byPolicy.values()) {
65
+ const inner = new Map();
66
+ for (const { name, qty } of byName.values())
67
+ inner.set(name, qty);
68
+ multiasset.set(policy, inner);
69
+ }
70
+ return [lovelace, multiasset];
71
+ };
72
+ //# sourceMappingURL=buildCardanoValue.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"buildCardanoValue.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/buildCardanoValue.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,10 @@
1
+ type BuildCardanoWitnessSetInput = {
2
+ /** 32-byte Ed25519 public key (raw bytes, not hex). */
3
+ publicKey: Uint8Array;
4
+ /** 64-byte Ed25519 signature (raw bytes, not hex). */
5
+ signature: Uint8Array;
6
+ };
7
+ /** Return the witness set as CBOR bytes. */
8
+ export declare const buildCardanoWitnessSet: ({ publicKey, signature, }: BuildCardanoWitnessSetInput) => Uint8Array;
9
+ export {};
10
+ //# sourceMappingURL=buildCardanoWitnessSet.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"buildCardanoWitnessSet.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/buildCardanoWitnessSet.ts"],"names":[],"mappings":"AAaA,KAAK,2BAA2B,GAAG;IACjC,uDAAuD;IACvD,SAAS,EAAE,UAAU,CAAA;IACrB,sDAAsD;IACtD,SAAS,EAAE,UAAU,CAAA;CACtB,CAAA;AAED,4CAA4C;AAC5C,eAAO,MAAM,sBAAsB,GAAI,2BAGpC,2BAA2B,KAAG,UAM7B,CAAA"}
@@ -0,0 +1,15 @@
1
+ /**
2
+ * Build a CIP-30 witness set CBOR from a public key and signature.
3
+ *
4
+ * CIP-30 signTx returns just the witness set (not the full signed tx):
5
+ * { 0: [ [vkey_bytes(32), signature_bytes(64)] ] }
6
+ */
7
+ import { cborArray, cborBytes, cborMap, cborUint, } from './cardanoCborPrimitives.js';
8
+ /** Return the witness set as CBOR bytes. */
9
+ export const buildCardanoWitnessSet = ({ publicKey, signature, }) => cborMap([
10
+ [
11
+ cborUint(0),
12
+ cborArray([cborArray([cborBytes(publicKey), cborBytes(signature)])]),
13
+ ],
14
+ ]);
15
+ //# sourceMappingURL=buildCardanoWitnessSet.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"buildCardanoWitnessSet.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/buildCardanoWitnessSet.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EACL,SAAS,EACT,SAAS,EACT,OAAO,EACP,QAAQ,GACT,MAAM,yBAAyB,CAAA;AAShC,4CAA4C;AAC5C,MAAM,CAAC,MAAM,sBAAsB,GAAG,CAAC,EACrC,SAAS,EACT,SAAS,GACmB,EAAc,EAAE,CAC5C,OAAO,CAAC;IACN;QACE,QAAQ,CAAC,CAAC,CAAC;QACX,SAAS,CAAC,CAAC,SAAS,CAAC,CAAC,SAAS,CAAC,SAAS,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC;KACrE;CACF,CAAC,CAAA"}
@@ -0,0 +1,45 @@
1
+ /**
2
+ * Build the Sig_structure that is the input to Ed25519 signing:
3
+ *
4
+ * ["Signature1", protected_bytes, external_aad, payload]
5
+ */
6
+ export declare const buildSigStructure: (protectedBytes: Uint8Array, payload: Uint8Array) => Uint8Array;
7
+ type BuildCoseSign1Input = {
8
+ /** Raw address bytes (not hex). */
9
+ addressBytes: Uint8Array;
10
+ /** Payload bytes (the hex-decoded payload from the dApp). */
11
+ payload: Uint8Array;
12
+ /** 64-byte Ed25519 signature. */
13
+ signature: Uint8Array;
14
+ };
15
+ /**
16
+ * Build and return the full COSE_Sign1 CBOR:
17
+ *
18
+ * [protected: bstr, unprotected: {}, payload: bstr, signature: bstr]
19
+ *
20
+ * Also returns the `protectedSerialized` bytes needed to compute the
21
+ * Sig_structure before signing.
22
+ */
23
+ export declare const buildCoseSign1: ({ addressBytes, payload, signature, }: BuildCoseSign1Input) => Uint8Array;
24
+ /**
25
+ * Return the serialized protected headers for a given address.
26
+ * Used by the caller to build the Sig_structure before MPC signing.
27
+ */
28
+ export declare const buildProtectedHeaderBytes: (addressBytes: Uint8Array) => Uint8Array;
29
+ type BuildCoseKeyInput = {
30
+ /** 32-byte Ed25519 public key (raw bytes). */
31
+ publicKey: Uint8Array;
32
+ };
33
+ /**
34
+ * Build a COSE_Key for an Ed25519 public key:
35
+ *
36
+ * { 1: 1, 3: -8, -1: 6, -2: <pubkey> }
37
+ *
38
+ * - Key 1 (kty) = 1 (OKP)
39
+ * - Key 3 (alg) = -8 (EdDSA)
40
+ * - Key -1 (crv) = 6 (Ed25519)
41
+ * - Key -2 (x) = public key bytes
42
+ */
43
+ export declare const buildCoseKey: ({ publicKey }: BuildCoseKeyInput) => Uint8Array;
44
+ export {};
45
+ //# sourceMappingURL=buildCoseStructures.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"buildCoseStructures.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/buildCoseStructures.ts"],"names":[],"mappings":"AA+BA;;;;GAIG;AACH,eAAO,MAAM,iBAAiB,GAC5B,gBAAgB,UAAU,EAC1B,SAAS,UAAU,KAClB,UAMC,CAAA;AAEJ,KAAK,mBAAmB,GAAG;IACzB,mCAAmC;IACnC,YAAY,EAAE,UAAU,CAAA;IACxB,6DAA6D;IAC7D,OAAO,EAAE,UAAU,CAAA;IACnB,iCAAiC;IACjC,SAAS,EAAE,UAAU,CAAA;CACtB,CAAA;AAED;;;;;;;GAOG;AACH,eAAO,MAAM,cAAc,GAAI,uCAI5B,mBAAmB,KAAG,UAQxB,CAAA;AAED;;;GAGG;AACH,eAAO,MAAM,yBAAyB,GACpC,cAAc,UAAU,KACvB,UAAiD,CAAA;AAEpD,KAAK,iBAAiB,GAAG;IACvB,8CAA8C;IAC9C,SAAS,EAAE,UAAU,CAAA;CACtB,CAAA;AAED;;;;;;;;;GASG;AACH,eAAO,MAAM,YAAY,GAAI,eAAe,iBAAiB,KAAG,UAM5D,CAAA"}
@@ -0,0 +1,70 @@
1
+ /**
2
+ * CIP-8 / CIP-30 signData helpers.
3
+ *
4
+ * Builds the COSE_Sign1 and COSE_Key structures for Cardano message signing.
5
+ *
6
+ * @see https://datatracker.ietf.org/doc/html/rfc8152
7
+ * @see https://cips.cardano.org/cip/CIP-0008
8
+ */
9
+ import { cborArray, cborBytes, cborMap, cborNegint, cborText, cborUint, } from './cardanoCborPrimitives.js';
10
+ /**
11
+ * Build the protected headers for a CIP-8 COSE_Sign1:
12
+ *
13
+ * { 1: -8, "address": <address_bytes> }
14
+ *
15
+ * Key `1` = alg, value `-8` = EdDSA (IANA COSE algorithm).
16
+ */
17
+ const buildProtectedHeaders = (addressBytes) => cborMap([
18
+ [cborUint(1), cborNegint(7)],
19
+ [cborText('address'), cborBytes(addressBytes)],
20
+ ]);
21
+ /**
22
+ * Build the Sig_structure that is the input to Ed25519 signing:
23
+ *
24
+ * ["Signature1", protected_bytes, external_aad, payload]
25
+ */
26
+ export const buildSigStructure = (protectedBytes, payload) => cborArray([
27
+ cborText('Signature1'),
28
+ cborBytes(protectedBytes),
29
+ cborBytes(new Uint8Array(0)), // empty external_aad
30
+ cborBytes(payload),
31
+ ]);
32
+ /**
33
+ * Build and return the full COSE_Sign1 CBOR:
34
+ *
35
+ * [protected: bstr, unprotected: {}, payload: bstr, signature: bstr]
36
+ *
37
+ * Also returns the `protectedSerialized` bytes needed to compute the
38
+ * Sig_structure before signing.
39
+ */
40
+ export const buildCoseSign1 = ({ addressBytes, payload, signature, }) => {
41
+ const protectedSerialized = buildProtectedHeaders(addressBytes);
42
+ return cborArray([
43
+ cborBytes(protectedSerialized),
44
+ cborMap([]), // empty unprotected headers
45
+ cborBytes(payload),
46
+ cborBytes(signature),
47
+ ]);
48
+ };
49
+ /**
50
+ * Return the serialized protected headers for a given address.
51
+ * Used by the caller to build the Sig_structure before MPC signing.
52
+ */
53
+ export const buildProtectedHeaderBytes = (addressBytes) => buildProtectedHeaders(addressBytes);
54
+ /**
55
+ * Build a COSE_Key for an Ed25519 public key:
56
+ *
57
+ * { 1: 1, 3: -8, -1: 6, -2: <pubkey> }
58
+ *
59
+ * - Key 1 (kty) = 1 (OKP)
60
+ * - Key 3 (alg) = -8 (EdDSA)
61
+ * - Key -1 (crv) = 6 (Ed25519)
62
+ * - Key -2 (x) = public key bytes
63
+ */
64
+ export const buildCoseKey = ({ publicKey }) => cborMap([
65
+ [cborUint(1), cborUint(1)],
66
+ [cborUint(3), cborNegint(7)],
67
+ [cborNegint(0), cborUint(6)],
68
+ [cborNegint(1), cborBytes(publicKey)],
69
+ ]);
70
+ //# sourceMappingURL=buildCoseStructures.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"buildCoseStructures.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/buildCoseStructures.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EACL,SAAS,EACT,SAAS,EACT,OAAO,EACP,UAAU,EACV,QAAQ,EACR,QAAQ,GAET,MAAM,yBAAyB,CAAA;AAEhC;;;;;;GAMG;AACH,MAAM,qBAAqB,GAAG,CAAC,YAAwB,EAAc,EAAE,CACrE,OAAO,CAAC;IACN,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,UAAU,CAAC,CAAC,CAAC,CAAC;IAC5B,CAAC,QAAQ,CAAC,SAAS,CAAC,EAAE,SAAS,CAAC,YAAY,CAAC,CAAC;CAC/C,CAAC,CAAA;AAEJ;;;;GAIG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAAG,CAC/B,cAA0B,EAC1B,OAAmB,EACP,EAAE,CACd,SAAS,CAAC;IACR,QAAQ,CAAC,YAAY,CAAC;IACtB,SAAS,CAAC,cAAc,CAAC;IACzB,SAAS,CAAC,IAAI,UAAU,CAAC,CAAC,CAAC,CAAC,EAAE,qBAAqB;IACnD,SAAS,CAAC,OAAO,CAAC;CACnB,CAAC,CAAA;AAWJ;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,cAAc,GAAG,CAAC,EAC7B,YAAY,EACZ,OAAO,EACP,SAAS,GACW,EAAc,EAAE;IACpC,MAAM,mBAAmB,GAAG,qBAAqB,CAAC,YAAY,CAAC,CAAA;IAC/D,OAAO,SAAS,CAAC;QACf,SAAS,CAAC,mBAAmB,CAAC;QAC9B,OAAO,CAAC,EAAE,CAAC,EAAE,4BAA4B;QACzC,SAAS,CAAC,OAAO,CAAC;QAClB,SAAS,CAAC,SAAS,CAAC;KACrB,CAAC,CAAA;AACJ,CAAC,CAAA;AAED;;;GAGG;AACH,MAAM,CAAC,MAAM,yBAAyB,GAAG,CACvC,YAAwB,EACZ,EAAE,CAAC,qBAAqB,CAAC,YAAY,CAAC,CAAA;AAOpD;;;;;;;;;GASG;AACH,MAAM,CAAC,MAAM,YAAY,GAAG,CAAC,EAAE,SAAS,EAAqB,EAAc,EAAE,CAC3E,OAAO,CAAC;IACN,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAC;IAC1B,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,UAAU,CAAC,CAAC,CAAC,CAAC;IAC5B,CAAC,UAAU,CAAC,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC,CAAC,CAAC;IAC5B,CAAC,UAAU,CAAC,CAAC,CAAC,EAAE,SAAS,CAAC,SAAS,CAAC,CAAC;CACtC,CAAC,CAAA"}
@@ -0,0 +1,6 @@
1
+ /**
2
+ * Decode a Cardano bech32 address into its raw byte representation.
3
+ * CIP-30 addresses cross the dApp boundary as hex of these bytes.
4
+ */
5
+ export declare const cardanoAddressBytes: (bech32Address: string) => Uint8Array;
6
+ //# sourceMappingURL=cardanoAddressBytes.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cardanoAddressBytes.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cardanoAddressBytes.ts"],"names":[],"mappings":"AAQA;;;GAGG;AACH,eAAO,MAAM,mBAAmB,GAAI,eAAe,MAAM,KAAG,UACR,CAAA"}
@@ -0,0 +1,12 @@
1
+ import { fromBech32 } from '@cosmjs/encoding';
2
+ /**
3
+ * Cardano base/stake addresses exceed the BIP173 90-char bech32 limit.
4
+ * Their raw byte length tops out at 57 bytes, so 200 is a comfortable cap.
5
+ */
6
+ const cardanoBech32Limit = 200;
7
+ /**
8
+ * Decode a Cardano bech32 address into its raw byte representation.
9
+ * CIP-30 addresses cross the dApp boundary as hex of these bytes.
10
+ */
11
+ export const cardanoAddressBytes = (bech32Address) => fromBech32(bech32Address, cardanoBech32Limit).data;
12
+ //# sourceMappingURL=cardanoAddressBytes.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cardanoAddressBytes.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cardanoAddressBytes.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAE7C;;;GAGG;AACH,MAAM,kBAAkB,GAAG,GAAG,CAAA;AAE9B;;;GAGG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAAG,CAAC,aAAqB,EAAc,EAAE,CACvE,UAAU,CAAC,aAAa,EAAE,kBAAkB,CAAC,CAAC,IAAI,CAAA"}
@@ -0,0 +1,53 @@
1
+ /**
2
+ * Minimal hand-rolled CBOR primitives for Cardano CIP-8 / CIP-30 wire format.
3
+ *
4
+ * `cbor-x` tags `Uint8Array` and encodes `Map` with text keys by default,
5
+ * breaking Cardano's strict unsigned-integer-key maps (COSE headers, witness
6
+ * sets, multiasset). These helpers produce spec-conformant CBOR without the
7
+ * library shape collision.
8
+ *
9
+ * **Scope and limits.** Every `uint` / length argument these primitives emit
10
+ * fits in the CBOR `additional = 26` form (4-byte argument, max `2^32 - 1`).
11
+ * That is sufficient for all of our Cardano CIP-8 / CIP-30 call sites:
12
+ *
13
+ * - COSE header keys / algorithm identifiers: small ints (e.g. 1, 3, 6, −8).
14
+ * - Witness-set entry keys: small ints (0 for vkey witnesses).
15
+ * - Byte/text string lengths, array/map cardinalities: well under 2^32.
16
+ *
17
+ * Cardano `value` / `coin` — the one place a CBOR uint *could* exceed 2^32
18
+ * (lovelace) — is **not** encoded through these primitives; it goes through
19
+ * `cardanoCborEncoder` (cbor-x) which handles the 8-byte argument form.
20
+ *
21
+ * Anything outside that range is rejected by `cborHead` with a clear error
22
+ * rather than silently truncated (RFC 8949 §3.1 mandates the smallest form,
23
+ * but truncating would produce structurally invalid CBOR). If you have a
24
+ * legitimate 64-bit uint to encode here in the future, extend `cborHead` to
25
+ * accept `bigint` and emit the `additional = 27` (8-byte) form — don't route
26
+ * it around this check.
27
+ */
28
+ /** Concatenate byte arrays. */
29
+ export declare const concat: (parts: Uint8Array[]) => Uint8Array;
30
+ /** Encode a CBOR byte string (major type 2). Length must be ≤ 2^32 − 1. */
31
+ export declare const cborBytes: (data: Uint8Array) => Uint8Array;
32
+ /** Encode a CBOR text string (major type 3). UTF-8 byte length must be ≤ 2^32 − 1. */
33
+ export declare const cborText: (s: string) => Uint8Array;
34
+ /**
35
+ * Encode a CBOR unsigned integer (major type 0).
36
+ *
37
+ * `n` must be a non-negative integer in `[0, 2^32 − 1]`. Throws otherwise.
38
+ * See the module-level docstring for why 64-bit uints route through
39
+ * `cardanoCborEncoder` instead.
40
+ */
41
+ export declare const cborUint: (n: number) => Uint8Array;
42
+ /**
43
+ * Encode a CBOR negative integer (major type 1): encodes the value `-(n+1)`.
44
+ *
45
+ * `n` must be a non-negative integer in `[0, 2^32 − 1]` (i.e. the encoded
46
+ * value lies in `[-2^32, -1]`). Throws otherwise.
47
+ */
48
+ export declare const cborNegint: (n: number) => Uint8Array;
49
+ /** Encode a CBOR array header (major type 4) followed by items. Cardinality must be ≤ 2^32 − 1. */
50
+ export declare const cborArray: (items: Uint8Array[]) => Uint8Array;
51
+ /** Encode a CBOR map header (major type 5) followed by key-value pairs. Cardinality must be ≤ 2^32 − 1. */
52
+ export declare const cborMap: (entries: Array<[Uint8Array, Uint8Array]>) => Uint8Array;
53
+ //# sourceMappingURL=cardanoCborPrimitives.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cardanoCborPrimitives.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cardanoCborPrimitives.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AAEH,+BAA+B;AAC/B,eAAO,MAAM,MAAM,GAAI,OAAO,UAAU,EAAE,KAAG,UAS5C,CAAA;AAED,2EAA2E;AAC3E,eAAO,MAAM,SAAS,GAAI,MAAM,UAAU,KAAG,UAG5C,CAAA;AAED,sFAAsF;AACtF,eAAO,MAAM,QAAQ,GAAI,GAAG,MAAM,KAAG,UAGpC,CAAA;AAED;;;;;;GAMG;AACH,eAAO,MAAM,QAAQ,GAAI,GAAG,MAAM,KAAG,UAA4B,CAAA;AAEjE;;;;;GAKG;AACH,eAAO,MAAM,UAAU,GAAI,GAAG,MAAM,KAAG,UAA4B,CAAA;AAEnE,mGAAmG;AACnG,eAAO,MAAM,SAAS,GAAI,OAAO,UAAU,EAAE,KAAG,UACD,CAAA;AAE/C,2GAA2G;AAC3G,eAAO,MAAM,OAAO,GAAI,SAAS,KAAK,CAAC,CAAC,UAAU,EAAE,UAAU,CAAC,CAAC,KAAG,UAI/D,CAAA"}
@@ -0,0 +1,91 @@
1
+ /**
2
+ * Minimal hand-rolled CBOR primitives for Cardano CIP-8 / CIP-30 wire format.
3
+ *
4
+ * `cbor-x` tags `Uint8Array` and encodes `Map` with text keys by default,
5
+ * breaking Cardano's strict unsigned-integer-key maps (COSE headers, witness
6
+ * sets, multiasset). These helpers produce spec-conformant CBOR without the
7
+ * library shape collision.
8
+ *
9
+ * **Scope and limits.** Every `uint` / length argument these primitives emit
10
+ * fits in the CBOR `additional = 26` form (4-byte argument, max `2^32 - 1`).
11
+ * That is sufficient for all of our Cardano CIP-8 / CIP-30 call sites:
12
+ *
13
+ * - COSE header keys / algorithm identifiers: small ints (e.g. 1, 3, 6, −8).
14
+ * - Witness-set entry keys: small ints (0 for vkey witnesses).
15
+ * - Byte/text string lengths, array/map cardinalities: well under 2^32.
16
+ *
17
+ * Cardano `value` / `coin` — the one place a CBOR uint *could* exceed 2^32
18
+ * (lovelace) — is **not** encoded through these primitives; it goes through
19
+ * `cardanoCborEncoder` (cbor-x) which handles the 8-byte argument form.
20
+ *
21
+ * Anything outside that range is rejected by `cborHead` with a clear error
22
+ * rather than silently truncated (RFC 8949 §3.1 mandates the smallest form,
23
+ * but truncating would produce structurally invalid CBOR). If you have a
24
+ * legitimate 64-bit uint to encode here in the future, extend `cborHead` to
25
+ * accept `bigint` and emit the `additional = 27` (8-byte) form — don't route
26
+ * it around this check.
27
+ */
28
+ /** Concatenate byte arrays. */
29
+ export const concat = (parts) => {
30
+ const total = parts.reduce((n, p) => n + p.length, 0);
31
+ const out = new Uint8Array(total);
32
+ let offset = 0;
33
+ for (const p of parts) {
34
+ out.set(p, offset);
35
+ offset += p.length;
36
+ }
37
+ return out;
38
+ };
39
+ /** Encode a CBOR byte string (major type 2). Length must be ≤ 2^32 − 1. */
40
+ export const cborBytes = (data) => {
41
+ const head = cborHead(2, data.length);
42
+ return concat([head, data]);
43
+ };
44
+ /** Encode a CBOR text string (major type 3). UTF-8 byte length must be ≤ 2^32 − 1. */
45
+ export const cborText = (s) => {
46
+ const utf8 = new TextEncoder().encode(s);
47
+ return concat([cborHead(3, utf8.length), utf8]);
48
+ };
49
+ /**
50
+ * Encode a CBOR unsigned integer (major type 0).
51
+ *
52
+ * `n` must be a non-negative integer in `[0, 2^32 − 1]`. Throws otherwise.
53
+ * See the module-level docstring for why 64-bit uints route through
54
+ * `cardanoCborEncoder` instead.
55
+ */
56
+ export const cborUint = (n) => cborHead(0, n);
57
+ /**
58
+ * Encode a CBOR negative integer (major type 1): encodes the value `-(n+1)`.
59
+ *
60
+ * `n` must be a non-negative integer in `[0, 2^32 − 1]` (i.e. the encoded
61
+ * value lies in `[-2^32, -1]`). Throws otherwise.
62
+ */
63
+ export const cborNegint = (n) => cborHead(1, n);
64
+ /** Encode a CBOR array header (major type 4) followed by items. Cardinality must be ≤ 2^32 − 1. */
65
+ export const cborArray = (items) => concat([cborHead(4, items.length), ...items]);
66
+ /** Encode a CBOR map header (major type 5) followed by key-value pairs. Cardinality must be ≤ 2^32 − 1. */
67
+ export const cborMap = (entries) => concat([
68
+ cborHead(5, entries.length),
69
+ ...entries.flatMap(([k, v]) => [k, v]),
70
+ ]);
71
+ /**
72
+ * Encode the major-type + argument head (RFC 8949 §3.1).
73
+ *
74
+ * `value` must be a non-negative safe integer ≤ 2^32 − 1. Throws otherwise —
75
+ * see the module-level docstring for the rationale.
76
+ */
77
+ const cborHead = (majorType, value) => {
78
+ if (!Number.isInteger(value) || value < 0 || value > 0xffffffff) {
79
+ throw new Error(`cborHead: value must be a non-negative integer ≤ 2^32-1, got ${value}`);
80
+ }
81
+ const mt = majorType << 5;
82
+ if (value < 24)
83
+ return Uint8Array.of(mt | value);
84
+ if (value < 0x100)
85
+ return Uint8Array.of(mt | 24, value);
86
+ if (value < 0x10000) {
87
+ return Uint8Array.of(mt | 25, (value >> 8) & 0xff, value & 0xff);
88
+ }
89
+ return Uint8Array.of(mt | 26, (value >>> 24) & 0xff, (value >>> 16) & 0xff, (value >>> 8) & 0xff, value & 0xff);
90
+ };
91
+ //# sourceMappingURL=cardanoCborPrimitives.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cardanoCborPrimitives.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cardanoCborPrimitives.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,6 @@
1
+ /**
2
+ * Given the hex-encoded CBOR of a full Cardano transaction, return
3
+ * the blake2b-256 hash of the transaction body (the first array element).
4
+ */
5
+ export declare const cardanoTxBodyHash: (txCborHex: string) => Uint8Array;
6
+ //# sourceMappingURL=cardanoTxBodyHash.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cardanoTxBodyHash.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cardanoTxBodyHash.ts"],"names":[],"mappings":"AAaA;;;GAGG;AACH,eAAO,MAAM,iBAAiB,GAAI,WAAW,MAAM,KAAG,UAIrD,CAAA"}
@@ -0,0 +1,55 @@
1
+ /**
2
+ * Extract the transaction body bytes from a full Cardano transaction CBOR
3
+ * and compute its blake2b-256 hash — the "transaction id".
4
+ *
5
+ * The body bytes are extracted verbatim (not re-encoded) because
6
+ * re-encoding via cbor-x could change key ordering or integer widths,
7
+ * producing a different hash than the one the dApp expects.
8
+ */
9
+ import { blake2b } from '@noble/hashes/blake2b';
10
+ import { decode } from 'cbor-x';
11
+ import { cborSkip } from './cborSkip.js';
12
+ /**
13
+ * Given the hex-encoded CBOR of a full Cardano transaction, return
14
+ * the blake2b-256 hash of the transaction body (the first array element).
15
+ */
16
+ export const cardanoTxBodyHash = (txCborHex) => {
17
+ const txBytes = Uint8Array.from(Buffer.from(txCborHex, 'hex'));
18
+ const bodyBytes = extractTxBodyBytes(txBytes);
19
+ return blake2b(bodyBytes, { dkLen: 32 });
20
+ };
21
+ /**
22
+ * Verify the CBOR is a 4-element array `[body, witnesses, isValid, aux]`
23
+ * and return the raw bytes of the body element without re-encoding.
24
+ */
25
+ const extractTxBodyBytes = (txCbor) => {
26
+ // Validate structure: must be a 4-element array
27
+ const decoded = decode(txCbor);
28
+ if (!Array.isArray(decoded) || decoded.length < 2) {
29
+ throw new Error('Invalid Cardano transaction CBOR: expected array of length >= 2');
30
+ }
31
+ // Walk the raw bytes to find the body element's byte range.
32
+ // Byte 0 is the array header (0x84 for definite 4-item array).
33
+ const arrayHeaderEnd = cborSkipHead(txCbor, 0);
34
+ const bodyEnd = cborSkip(txCbor, arrayHeaderEnd);
35
+ return txCbor.slice(arrayHeaderEnd, bodyEnd);
36
+ };
37
+ /**
38
+ * Skip just the CBOR head (major type + argument) at `offset`.
39
+ * Returns the offset after the head (i.e., where the content starts).
40
+ */
41
+ const cborSkipHead = (data, offset) => {
42
+ const additional = data[offset] & 0x1f;
43
+ if (additional < 24)
44
+ return offset + 1;
45
+ if (additional === 24)
46
+ return offset + 2;
47
+ if (additional === 25)
48
+ return offset + 3;
49
+ if (additional === 26)
50
+ return offset + 5;
51
+ if (additional === 27)
52
+ return offset + 9;
53
+ throw new Error(`Unsupported CBOR additional info ${additional} at offset ${offset}`);
54
+ };
55
+ //# sourceMappingURL=cardanoTxBodyHash.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cardanoTxBodyHash.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cardanoTxBodyHash.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAA;AAC/C,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAA;AAE/B,OAAO,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAA;AAErC;;;GAGG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAAG,CAAC,SAAiB,EAAc,EAAE;IACjE,MAAM,OAAO,GAAG,UAAU,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,SAAS,EAAE,KAAK,CAAC,CAAC,CAAA;IAC9D,MAAM,SAAS,GAAG,kBAAkB,CAAC,OAAO,CAAC,CAAA;IAC7C,OAAO,OAAO,CAAC,SAAS,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE,CAAC,CAAA;AAC1C,CAAC,CAAA;AAED;;;GAGG;AACH,MAAM,kBAAkB,GAAG,CAAC,MAAkB,EAAc,EAAE;IAC5D,gDAAgD;IAChD,MAAM,OAAO,GAAG,MAAM,CAAC,MAAM,CAAC,CAAA;IAC9B,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAClD,MAAM,IAAI,KAAK,CAAC,iEAAiE,CAAC,CAAA;IACpF,CAAC;IAED,4DAA4D;IAC5D,+DAA+D;IAC/D,MAAM,cAAc,GAAG,YAAY,CAAC,MAAM,EAAE,CAAC,CAAC,CAAA;IAC9C,MAAM,OAAO,GAAG,QAAQ,CAAC,MAAM,EAAE,cAAc,CAAC,CAAA;IAEhD,OAAO,MAAM,CAAC,KAAK,CAAC,cAAc,EAAE,OAAO,CAAC,CAAA;AAC9C,CAAC,CAAA;AAED;;;GAGG;AACH,MAAM,YAAY,GAAG,CAAC,IAAgB,EAAE,MAAc,EAAU,EAAE;IAChE,MAAM,UAAU,GAAG,IAAI,CAAC,MAAM,CAAC,GAAG,IAAI,CAAA;IACtC,IAAI,UAAU,GAAG,EAAE;QAAE,OAAO,MAAM,GAAG,CAAC,CAAA;IACtC,IAAI,UAAU,KAAK,EAAE;QAAE,OAAO,MAAM,GAAG,CAAC,CAAA;IACxC,IAAI,UAAU,KAAK,EAAE;QAAE,OAAO,MAAM,GAAG,CAAC,CAAA;IACxC,IAAI,UAAU,KAAK,EAAE;QAAE,OAAO,MAAM,GAAG,CAAC,CAAA;IACxC,IAAI,UAAU,KAAK,EAAE;QAAE,OAAO,MAAM,GAAG,CAAC,CAAA;IACxC,MAAM,IAAI,KAAK,CAAC,oCAAoC,UAAU,cAAc,MAAM,EAAE,CAAC,CAAA;AACvF,CAAC,CAAA"}
@@ -0,0 +1,11 @@
1
+ import { Encoder } from 'cbor-x';
2
+ /**
3
+ * Shared CBOR encoder configured for Cardano's wire format.
4
+ *
5
+ * - `mapsAsObjects: false` keeps JS `Map` objects as true CBOR maps (Cardano
6
+ * multiasset uses byte-string and integer keys, not text keys).
7
+ * - `tagUint8Array: false` strips the cbor-x specific `d840` tag so byte
8
+ * strings round-trip as plain CBOR major type 2.
9
+ */
10
+ export declare const cardanoCborEncoder: Encoder;
11
+ //# sourceMappingURL=cborEncoder.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cborEncoder.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cborEncoder.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,QAAQ,CAAA;AAEhC;;;;;;;GAOG;AACH,eAAO,MAAM,kBAAkB,SAG7B,CAAA"}
@@ -0,0 +1,14 @@
1
+ import { Encoder } from 'cbor-x';
2
+ /**
3
+ * Shared CBOR encoder configured for Cardano's wire format.
4
+ *
5
+ * - `mapsAsObjects: false` keeps JS `Map` objects as true CBOR maps (Cardano
6
+ * multiasset uses byte-string and integer keys, not text keys).
7
+ * - `tagUint8Array: false` strips the cbor-x specific `d840` tag so byte
8
+ * strings round-trip as plain CBOR major type 2.
9
+ */
10
+ export const cardanoCborEncoder = new Encoder({
11
+ mapsAsObjects: false,
12
+ tagUint8Array: false,
13
+ });
14
+ //# sourceMappingURL=cborEncoder.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cborEncoder.js","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cborEncoder.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,QAAQ,CAAA;AAEhC;;;;;;;GAOG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAG,IAAI,OAAO,CAAC;IAC5C,aAAa,EAAE,KAAK;IACpB,aAAa,EAAE,KAAK;CACrB,CAAC,CAAA"}
@@ -0,0 +1,13 @@
1
+ /**
2
+ * Walk a CBOR data item starting at `offset` and return the offset
3
+ * immediately after the item ends. This allows extracting raw byte
4
+ * ranges from CBOR without re-encoding.
5
+ *
6
+ * Supports: unsigned/negative ints, byte/text strings, arrays, maps, tags,
7
+ * and simple values (true/false/null). Does NOT support indefinite-length.
8
+ *
9
+ * Every read is bounds-checked so a truncated / malformed CBOR input fails
10
+ * fast with a descriptive error instead of silently returning bogus offsets.
11
+ */
12
+ export declare const cborSkip: (data: Uint8Array, offset: number) => number;
13
+ //# sourceMappingURL=cborSkip.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cborSkip.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/chain/chains/cardano/cip30/cborSkip.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AACH,eAAO,MAAM,QAAQ,GAAI,MAAM,UAAU,EAAE,QAAQ,MAAM,KAAG,MAwD3D,CAAA"}