@hardkas/accounts 0.12.0-rc.20 → 0.12.0-rc.22

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.
@@ -2,8 +2,7 @@ import {
2
2
  LazyAccountAuthorizer,
3
3
  PrivateKeyAuthorizer,
4
4
  StaticSignatureScriptAuthorizer
5
- } from "./chunk-5266LO4K.js";
6
- import "./chunk-MCKGQKYU.js";
5
+ } from "./chunk-E73SSWAX.js";
7
6
  export {
8
7
  LazyAccountAuthorizer,
9
8
  PrivateKeyAuthorizer,
@@ -425,7 +425,8 @@ async function resolveHardkasAccountAddress(accountOrAddress, config, context =
425
425
  }
426
426
  if (!accountOrAddress.startsWith("kaspa:sim_")) {
427
427
  try {
428
- const kaspa = await import("kaspa-wasm");
428
+ const { loadKaspaWasm } = await import("./signer-backend-LHWY7ULI.js");
429
+ const kaspa = await loadKaspaWasm();
429
430
  try {
430
431
  if (typeof kaspa.Address === "function" || kaspa.Address) {
431
432
  new kaspa.Address(accountOrAddress);
@@ -439,6 +440,7 @@ async function resolveHardkasAccountAddress(accountOrAddress, config, context =
439
440
  }
440
441
  } catch (e) {
441
442
  if (e instanceof Error && e.code === "HARDKAS_INVALID_ADDRESS") throw e;
443
+ if (e instanceof Error && e.code === "WASM_TOOLCHAIN_INTEGRITY_FAILED") throw e;
442
444
  if (e instanceof Error && (e.code === "ERR_MODULE_NOT_FOUND" || (e instanceof Error ? e instanceof Error ? e.message : String(e) : String(e)).includes("Cannot find module") || (e instanceof Error ? e instanceof Error ? e.message : String(e) : String(e)).includes("kaspa-wasm"))) {
443
445
  const err = new Error(
444
446
  "ADDRESS_VALIDATOR_UNAVAILABLE: The Kaspa address validator backend is not available."
@@ -2,18 +2,14 @@
2
2
  import path from "path";
3
3
  import fs from "fs";
4
4
  import { pathToFileURL } from "url";
5
+ import { loadManagedKaspaWasmSync } from "@hardkas/core";
6
+ function loadKaspaWasmSync() {
7
+ return loadManagedKaspaWasmSync();
8
+ }
5
9
  async function loadKaspaWasm(config) {
6
- const provider = config?.provider || "npm";
7
- if (provider === "npm") {
8
- try {
9
- return await import("kaspa-wasm");
10
- } catch (error) {
11
- const err = new Error(
12
- "SIGNER_BACKEND_UNAVAILABLE: Official Kaspa WASM backend is required to sign transactions.\nInstall it via: npm install kaspa-wasm"
13
- );
14
- err.code = "SIGNER_BACKEND_UNAVAILABLE";
15
- throw err;
16
- }
10
+ const provider = config?.provider || "managed";
11
+ if (provider === "managed") {
12
+ return loadKaspaWasmSync();
17
13
  }
18
14
  if (provider === "local" || provider === "release-asset") {
19
15
  if (!config?.path) {
@@ -52,13 +48,7 @@ async function loadKaspaWasm(config) {
52
48
  }
53
49
  }
54
50
  function detectCapabilities(sdk) {
55
- let v1 = false;
56
- if (sdk.createTransaction && sdk.createTransaction.length >= 8) {
57
- v1 = true;
58
- }
59
- if (sdk.createV1Transaction || sdk.Transaction && sdk.Transaction.prototype && !!Object.getOwnPropertyDescriptor(sdk.Transaction.prototype, "storageMass")) {
60
- v1 = true;
61
- }
51
+ const v1 = !!(sdk?.Transaction?.prototype && Object.getOwnPropertyDescriptor(sdk.Transaction.prototype, "storageMass"));
62
52
  return { transactionV1Signing: v1 };
63
53
  }
64
54
  async function getKaspaSigningBackendStatus(config) {
@@ -67,11 +57,11 @@ async function getKaspaSigningBackendStatus(config) {
67
57
  return {
68
58
  available: true,
69
59
  name: "Kaspa WASM SDK",
70
- version: sdk.version || "unknown",
60
+ version: typeof sdk.version === "function" ? String(sdk.version()) : "unknown",
71
61
  capabilities: detectCapabilities(sdk)
72
62
  };
73
63
  } catch (error) {
74
- if (error.code === "WASM_RELEASE_ASSET_NOT_FOUND") {
64
+ if (error.code === "WASM_RELEASE_ASSET_NOT_FOUND" || error.code === "WASM_TOOLCHAIN_INTEGRITY_FAILED") {
75
65
  throw error;
76
66
  }
77
67
  return {
@@ -84,6 +74,7 @@ async function getKaspaSigningBackendStatus(config) {
84
74
  }
85
75
 
86
76
  export {
77
+ loadKaspaWasmSync,
87
78
  loadKaspaWasm,
88
79
  detectCapabilities,
89
80
  getKaspaSigningBackendStatus
@@ -1,12 +1,12 @@
1
1
  import {
2
2
  parseWasmTxToRpc
3
- } from "./chunk-R5P3WIWR.js";
4
- import {
5
- resolveHardkasAccount
6
- } from "./chunk-YBNHOFVX.js";
3
+ } from "./chunk-GM2BY4VS.js";
7
4
  import {
8
5
  loadKaspaWasm
9
- } from "./chunk-6DPO5V3N.js";
6
+ } from "./chunk-BNF566PS.js";
7
+ import {
8
+ resolveHardkasAccount
9
+ } from "./chunk-7KKJXU73.js";
10
10
  import {
11
11
  KeystoreManager
12
12
  } from "./chunk-YLG2NIAU.js";
@@ -20,6 +20,82 @@ import { deterministicCompare, getNetworkPrefix as getNetworkPrefix2 } from "@ha
20
20
  // src/kaspa-wasm-signer.ts
21
21
  import { calculateContentHash } from "@hardkas/artifacts";
22
22
  import { getNetworkPrefix } from "@hardkas/core";
23
+
24
+ // src/wasm-transaction.ts
25
+ function assertValueConservation(input) {
26
+ const inputs = input.inputAmounts.reduce((a, b) => a + b, 0n);
27
+ const outputs = input.outputAmounts.reduce((a, b) => a + b, 0n);
28
+ if (input.feeSompi < 0n || inputs - outputs !== input.feeSompi) {
29
+ const err = new Error(
30
+ `TX_VALUE_NOT_CONSERVED: inputs ${inputs} - outputs ${outputs} = ${inputs - outputs} sompi, but the plan's fee is ${input.feeSompi}. Refusing to build a transaction whose difference would be paid as fee.`
31
+ );
32
+ err.code = "TX_VALUE_NOT_CONSERVED";
33
+ throw err;
34
+ }
35
+ }
36
+ function createBalancedTransaction(sdk, input) {
37
+ assertValueConservation({
38
+ inputAmounts: input.utxos.map((u) => u.utxoEntry.amount),
39
+ outputAmounts: input.outputs.map((o) => o.amountSompi),
40
+ feeSompi: input.feeSompi
41
+ });
42
+ return sdk.createTransaction(
43
+ [...input.utxos],
44
+ input.outputs.map((o) => o.output),
45
+ input.feeSompi
46
+ );
47
+ }
48
+ function createScriptTransaction(sdk, input) {
49
+ assertValueConservation({
50
+ inputAmounts: input.utxos.map((u) => u.utxoEntry.amount),
51
+ outputAmounts: input.outputs.map((o) => o.value),
52
+ feeSompi: input.feeSompi
53
+ });
54
+ return new sdk.Transaction({
55
+ version: 0,
56
+ inputs: input.utxos.map((u) => ({
57
+ previousOutpoint: { transactionId: u.outpoint.transactionId, index: u.outpoint.index },
58
+ signatureScript: "",
59
+ sequence: 0n,
60
+ sigOpCount: 1,
61
+ utxo: {
62
+ address: u.address,
63
+ outpoint: { transactionId: u.outpoint.transactionId, index: u.outpoint.index },
64
+ amount: u.utxoEntry.amount,
65
+ scriptPublicKey: u.utxoEntry.scriptPublicKey,
66
+ blockDaaScore: u.utxoEntry.blockDaaScore,
67
+ isCoinbase: u.utxoEntry.isCoinbase
68
+ }
69
+ })),
70
+ outputs: [...input.outputs],
71
+ lockTime: 0n,
72
+ subnetworkId: "0000000000000000000000000000000000000000",
73
+ gas: 0n,
74
+ payload: ""
75
+ });
76
+ }
77
+ function toWasmScriptPublicKey(sdk, spk) {
78
+ if (spk && typeof spk === "object") {
79
+ const o = spk;
80
+ return new sdk.ScriptPublicKey(Number(o.version ?? 0), String(o.scriptPublicKey || o.script || ""));
81
+ }
82
+ const hex = String(spk ?? "");
83
+ if (/^[0-9a-fA-F]{72}$/.test(hex) && hex.startsWith("0000")) {
84
+ return new sdk.ScriptPublicKey(0, hex.slice(4));
85
+ }
86
+ return new sdk.ScriptPublicKey(0, hex);
87
+ }
88
+ function planOutputsWithChange(plan) {
89
+ const all = [...plan.outputs];
90
+ if (plan.change && BigInt(plan.change.amountSompi) > 0n) all.push(plan.change);
91
+ return all.map((o) => {
92
+ if (!o.address) throw new Error("Output is missing address.");
93
+ const amount = BigInt(o.amountSompi);
94
+ return { amountSompi: amount, output: { address: o.address, amount } };
95
+ });
96
+ }
97
+
98
+ // src/kaspa-wasm-signer.ts
23
99
  var KaspaWasmPrivateKeySigner = class {
24
100
  constructor(options) {
25
101
  this.options = options;
@@ -29,7 +105,7 @@ var KaspaWasmPrivateKeySigner = class {
29
105
  async signTxPlan(input) {
30
106
  const plan = input.planArtifact;
31
107
  const sdk = await loadKaspaWasm(this.options.wasmConfig);
32
- const { detectCapabilities } = await import("./signer-backend-X3FD3XMB.js");
108
+ const { detectCapabilities } = await import("./signer-backend-LHWY7ULI.js");
33
109
  const capabilities = detectCapabilities(sdk);
34
110
  if (plan.computeBudget !== void 0 || plan.outputs.some((o) => o.covenant)) {
35
111
  if (!capabilities.transactionV1Signing) {
@@ -56,8 +132,8 @@ var KaspaWasmPrivateKeySigner = class {
56
132
  }
57
133
  if (!pkValue && account.keystorePath) {
58
134
  try {
59
- const KeystoreManager2 = (await import("./keystore-2KRHVGCM.js")).KeystoreManager;
60
- const DEV_ACCOUNTS_PASSWORD2 = (await import("./dev-accounts-S4WHPHJK.js")).DEV_ACCOUNTS_PASSWORD;
135
+ const KeystoreManager2 = (await import("./keystore-CMWEKGBF.js")).KeystoreManager;
136
+ const DEV_ACCOUNTS_PASSWORD2 = (await import("./dev-accounts-BSWPKAAE.js")).DEV_ACCOUNTS_PASSWORD;
61
137
  const keystore = await KeystoreManager2.loadEncryptedKeystore(account.keystorePath);
62
138
  const unlock = await KeystoreManager2.decryptEncryptedKeystore(keystore, DEV_ACCOUNTS_PASSWORD2);
63
139
  if (unlock.success && unlock.payload) {
@@ -77,7 +153,7 @@ var KaspaWasmPrivateKeySigner = class {
77
153
  throw err;
78
154
  }
79
155
  const expectedAddress = new sdk.PrivateKey(pkValue).toKeypair().toAddress(getNetworkPrefix(plan.networkId || "simnet")).toString();
80
- const { PrivateKeyAuthorizer } = await import("./authorizers-S5IKSHTE.js");
156
+ const { PrivateKeyAuthorizer } = await import("./authorizers-CP222OTW.js");
81
157
  const sourceInputs = plan.inputs || plan.selectedUtxos || [];
82
158
  for (let i = 0; i < numInputs; i++) {
83
159
  if (!authorizers[i]) {
@@ -133,32 +209,28 @@ var KaspaWasmPrivateKeySigner = class {
133
209
  });
134
210
  const priorityFee = BigInt(plan.estimatedFeeSompi);
135
211
  const createFreshTx = () => {
136
- let unsignedTx;
137
- if (plan.txVersion === 1) {
138
- if (!capabilities.transactionV1Signing) {
139
- throw new Error("Transaction V1 signing is not supported by the installed kaspa-wasm version");
140
- }
141
- const allOutputs = [...plan.outputs];
142
- if (plan.change) {
143
- allOutputs.push({
144
- address: plan.change.address,
145
- amountSompi: plan.change.amountSompi
146
- });
147
- }
148
- const wasmOutputs = allOutputs.map((o, idx) => {
149
- if (!o.address) throw new Error("Output is missing address.");
150
- if (o.covenant && o.covenant.covenantId) {
151
- const hash = new sdk.Hash(o.covenant.covenantId);
152
- const binding = new sdk.CovenantBinding(o.covenant.authorizingInput, hash);
153
- return sdk.PaymentOutput.withCovenant(new sdk.Address(o.address), BigInt(o.amountSompi), binding);
154
- }
155
- return new sdk.PaymentOutput(new sdk.Address(o.address), BigInt(o.amountSompi));
212
+ const isV1 = plan.txVersion === 1;
213
+ if (isV1 && !capabilities.transactionV1Signing) {
214
+ throw new Error("Transaction V1 signing is not supported by the installed kaspa-wasm version");
215
+ }
216
+ const allOutputs = [...plan.outputs];
217
+ if (plan.change && BigInt(plan.change.amountSompi) > 0n) {
218
+ allOutputs.push({
219
+ address: plan.change.address,
220
+ amountSompi: plan.change.amountSompi
156
221
  });
157
- unsignedTx = sdk.createTransaction(
158
- utxos,
159
- wasmOutputs,
160
- priorityFee
161
- );
222
+ }
223
+ const outputs = allOutputs.map((o) => {
224
+ if (!o.address) throw new Error("Output is missing address.");
225
+ const amount = BigInt(o.amountSompi);
226
+ if (isV1 && o.covenant && o.covenant.covenantId) {
227
+ const binding = new sdk.CovenantBinding(o.covenant.authorizingInput, new sdk.Hash(o.covenant.covenantId));
228
+ return { amountSompi: amount, output: sdk.PaymentOutput.withCovenant(new sdk.Address(o.address), amount, binding) };
229
+ }
230
+ return { amountSompi: amount, output: new sdk.PaymentOutput(new sdk.Address(o.address), amount) };
231
+ });
232
+ const unsignedTx = createBalancedTransaction(sdk, { utxos, outputs, feeSompi: priorityFee });
233
+ if (isV1) {
162
234
  const genesisGroups = /* @__PURE__ */ new Map();
163
235
  allOutputs.forEach((o, idx) => {
164
236
  if (o.covenant && !o.covenant.covenantId) {
@@ -177,28 +249,6 @@ var KaspaWasmPrivateKeySigner = class {
177
249
  if (plan.storageMass !== void 0) {
178
250
  unsignedTx.storageMass = BigInt(plan.storageMass);
179
251
  }
180
- } else {
181
- const allOutputs = [...plan.outputs];
182
- if (plan.change) {
183
- allOutputs.push({
184
- address: plan.change.address,
185
- amountSompi: plan.change.amountSompi
186
- });
187
- }
188
- const wasmOutputs = allOutputs.map((o) => {
189
- if (!o.address) throw new Error("Output is missing address.");
190
- return {
191
- address: o.address,
192
- amount: BigInt(o.amountSompi)
193
- };
194
- });
195
- const dummyChange = plan.change && plan.change.address || (typeof plan.from === "string" ? plan.from : plan.from?.address) || plan.outputs && plan.outputs[0] && plan.outputs[0].address;
196
- unsignedTx = sdk.createTransaction(
197
- utxos,
198
- wasmOutputs,
199
- dummyChange,
200
- priorityFee
201
- );
202
252
  }
203
253
  const inputs = unsignedTx.inputs;
204
254
  for (let i = 0; i < inputs.length; i++) {
@@ -251,8 +301,7 @@ var KaspaWasmPrivateKeySigner = class {
251
301
  }
252
302
  const finalTx = createFreshTx();
253
303
  const signedTx = finalTx;
254
- const wasmTxStr = typeof signedTx.serializeToJSON === "function" ? signedTx.serializeToJSON() : signedTx.toString();
255
- const rpcTx = parseWasmTxToRpc(wasmTxStr, signedTx, inputOverrides, plan);
304
+ const rpcTx = parseWasmTxToRpc(signedTx.serializeToObject(), signedTx, inputOverrides, plan);
256
305
  const rawTx = JSON.stringify(rpcTx);
257
306
  return {
258
307
  signatureKind: "kaspa",
@@ -319,61 +368,12 @@ async function getOrCreateDevAccount(workspaceDir, index, alias) {
319
368
  const seedString = `${SIMNET_DETERMINISTIC_SEED}-${index}`;
320
369
  const privateKeyHex = crypto.createHash("sha256").update(seedString).digest("hex");
321
370
  const network = "simnet";
322
- const isSimnet = ["simnet", "kaspasim", "local"].includes(network);
323
- let address = "";
324
- let privateKey = "";
325
- let publicKey = "";
326
- try {
327
- if (isSimnet) {
328
- const { loadKaspaWasm: loadKaspaWasm2 } = await import("./signer-backend-X3FD3XMB.js");
329
- const kaspaWasm = await loadKaspaWasm2();
330
- const privKey = new kaspaWasm.PrivateKey(privateKeyHex);
331
- const kp = privKey.toKeypair();
332
- address = kp.toAddress(getNetworkPrefix2(network)).toString();
333
- publicKey = kp.publicKey;
334
- privateKey = privateKeyHex;
335
- } else {
336
- let sdkModule;
337
- try {
338
- sdkModule = await import(
339
- /* @vite-ignore */
340
- "./core-lib-YKSIDZOW.js"
341
- );
342
- } catch (e) {
343
- console.warn(`
344
- [Warning] @kaspa/core-lib is not installed.`);
345
- return { address: "", privateKey: "", publicKey: "" };
346
- }
347
- const sdk = sdkModule.default || sdkModule;
348
- if (typeof sdk.initRuntime === "function") {
349
- await sdk.initRuntime();
350
- }
351
- const privKey = new sdk.PrivateKey(privateKeyHex);
352
- const pubKey = privKey.toPublicKey();
353
- try {
354
- address = pubKey.toAddress(getNetworkPrefix2(network)).toString();
355
- } catch (e) {
356
- const msg = e instanceof Error ? e instanceof Error ? e instanceof Error ? e.message : String(e) : String(e) : String(e);
357
- if (msg.includes("Second argument must be") || msg.includes("Unsupported")) {
358
- const err = new Error("DEV_ACCOUNT_BACKEND_UNSUPPORTED_NETWORK");
359
- err.code = "DEV_ACCOUNT_BACKEND_UNSUPPORTED_NETWORK";
360
- throw err;
361
- }
362
- throw e;
363
- }
364
- publicKey = pubKey.toString();
365
- privateKey = privKey.toString();
366
- }
367
- } catch (e) {
368
- const msg = e instanceof Error ? e instanceof Error ? e instanceof Error ? e.message : String(e) : String(e) : String(e);
369
- if (msg === "DEV_ACCOUNT_BACKEND_UNSUPPORTED_NETWORK") {
370
- throw e;
371
- }
372
- console.warn(`
373
- [Warning] Could not generate dev account '${alias}'.
374
- ${msg}`);
375
- return { address: "", privateKey: "", publicKey: "" };
376
- }
371
+ const { loadKaspaWasm: loadKaspaWasm2 } = await import("./signer-backend-LHWY7ULI.js");
372
+ const kaspaWasm = await loadKaspaWasm2();
373
+ const kp = new kaspaWasm.PrivateKey(privateKeyHex).toKeypair();
374
+ const address = kp.toAddress(getNetworkPrefix2(network)).toString();
375
+ const publicKey = kp.publicKey;
376
+ const privateKey = privateKeyHex;
377
377
  const accountData = {
378
378
  address,
379
379
  privateKey,
@@ -442,6 +442,11 @@ async function createDevSigner(workspaceDir, accountNameOrAddress) {
442
442
  }
443
443
 
444
444
  export {
445
+ assertValueConservation,
446
+ createBalancedTransaction,
447
+ createScriptTransaction,
448
+ toWasmScriptPublicKey,
449
+ planOutputsWithChange,
445
450
  DEV_ACCOUNTS_PASSWORD,
446
451
  ensureDevAccounts,
447
452
  getOrCreateDevAccount,
@@ -62,7 +62,7 @@ var LazyAccountAuthorizer = class {
62
62
  accountName;
63
63
  workspaceRoot;
64
64
  async authorize(context) {
65
- const { resolveHardkasAccount } = await import("./resolve-UTFZTVAK.js");
65
+ const { resolveHardkasAccount } = await import("./resolve-KMMTZWC3.js");
66
66
  const account = await resolveHardkasAccount({
67
67
  nameOrAddress: this.accountName,
68
68
  config: { cwd: this.workspaceRoot }
@@ -73,8 +73,8 @@ var LazyAccountAuthorizer = class {
73
73
  }
74
74
  if (!pkValue && account.keystorePath) {
75
75
  try {
76
- const { KeystoreManager } = await import("./keystore-2KRHVGCM.js");
77
- const { DEV_ACCOUNTS_PASSWORD } = await import("./dev-accounts-S4WHPHJK.js");
76
+ const { KeystoreManager } = await import("./keystore-CMWEKGBF.js");
77
+ const { DEV_ACCOUNTS_PASSWORD } = await import("./dev-accounts-BSWPKAAE.js");
78
78
  const keystore = await KeystoreManager.loadEncryptedKeystore(account.keystorePath);
79
79
  const unlock = await KeystoreManager.decryptEncryptedKeystore(keystore, DEV_ACCOUNTS_PASSWORD);
80
80
  if (unlock.success && unlock.payload) {
@@ -1,17 +1,37 @@
1
1
  // src/internal/wasm-rpc-serialization.ts
2
- function parseWasmTxToRpc(wasmTxStr, signedTx, inputOverrides, plan) {
2
+ function toRpcNumber(value, field) {
3
+ if (typeof value === "bigint") {
4
+ if (value > BigInt(Number.MAX_SAFE_INTEGER)) {
5
+ throw new Error(`RPC_SERIALIZATION_UNSAFE_INTEGER: ${field} ${value} exceeds 2^53`);
6
+ }
7
+ return Number(value);
8
+ }
9
+ return typeof value === "number" ? value : Number(value || 0);
10
+ }
11
+ function storageMassOf(txInner) {
12
+ const value = txInner.storageMass ?? txInner.mass;
13
+ if (value === void 0 || value === null) {
14
+ throw new Error("RPC_STORAGE_MASS_MISSING: the serialized transaction carries no storageMass commitment");
15
+ }
16
+ return toRpcNumber(value, "storageMass");
17
+ }
18
+ function parseWasmTxToRpc(wasmTx, signedTx, inputOverrides, plan) {
3
19
  let parsed;
4
- try {
5
- parsed = JSON.parse(wasmTxStr);
6
- } catch (e) {
7
- throw new Error("Failed to parse WASM transaction JSON: " + String(e));
20
+ if (typeof wasmTx === "string") {
21
+ try {
22
+ parsed = JSON.parse(wasmTx);
23
+ } catch (e) {
24
+ throw new Error("Failed to parse WASM transaction JSON: " + String(e));
25
+ }
26
+ } else {
27
+ parsed = wasmTx;
8
28
  }
9
29
  while (typeof parsed === "string") {
10
30
  parsed = JSON.parse(parsed);
11
31
  }
12
32
  const txInner = parsed.outputs ? parsed : parsed.tx ? parsed.tx.inner : parsed.inner;
13
33
  if (!txInner) throw new Error("Could not find inner tx data");
14
- const version = txInner.version || 0;
34
+ const version = toRpcNumber(txInner.version || 0, "version");
15
35
  const numInputs = txInner.inputs ? txInner.inputs.length : 0;
16
36
  if (inputOverrides) {
17
37
  for (const idxStr of Object.keys(inputOverrides)) {
@@ -38,19 +58,19 @@ function parseWasmTxToRpc(wasmTxStr, signedTx, inputOverrides, plan) {
38
58
  if (!finalSigScript || finalSigScript.length === 0 || !/^[0-9a-fA-F]+$/.test(finalSigScript)) {
39
59
  throw new Error(`INVALID_SIGNATURE_SCRIPT: Missing or invalid hex signature script at input ${idx}`);
40
60
  }
41
- const sigOpCount = version === 1 ? 0 : originalSigOpCount !== void 0 ? originalSigOpCount : 1;
61
+ const sigOpCount = version === 1 ? 0 : originalSigOpCount !== void 0 ? toRpcNumber(originalSigOpCount, "sigOpCount") : 1;
42
62
  if (version === 1 && sigOpCount !== 0) {
43
63
  throw new Error("INVALID_V1_SIG_OP_COUNT: V1 transactions must have sigOpCount = 0.");
44
64
  }
45
65
  const overrideBudget = plan?.computeBudget;
46
- const finalComputeBudget = overrideBudget !== void 0 ? Number(overrideBudget) : computeBudget !== void 0 && computeBudget !== 0 ? computeBudget : 0;
66
+ const finalComputeBudget = overrideBudget !== void 0 ? Number(overrideBudget) : toRpcNumber(computeBudget ?? 0, "computeBudget");
47
67
  return {
48
68
  previousOutpoint: {
49
- transactionId: prevOut.transactionId || prevOut.transactionId,
50
- index: prevOut.index || prevOut.index
69
+ transactionId: prevOut.transactionId,
70
+ index: toRpcNumber(prevOut.index ?? 0, "index")
51
71
  },
52
72
  signatureScript: finalSigScript,
53
- sequence: isFlattened ? i.sequence || 0 : i.inner.sequence || 0,
73
+ sequence: toRpcNumber(isFlattened ? i.sequence || 0 : i.inner.sequence || 0, "sequence"),
54
74
  sigOpCount,
55
75
  computeBudget: finalComputeBudget
56
76
  };
@@ -89,11 +109,13 @@ function parseWasmTxToRpc(wasmTxStr, signedTx, inputOverrides, plan) {
89
109
  }
90
110
  return ret;
91
111
  }),
92
- lockTime: txInner.lockTime || 0,
112
+ lockTime: toRpcNumber(txInner.lockTime || 0, "lockTime"),
93
113
  subnetworkId: txInner.subnetworkId || "0000000000000000000000000000000000000000",
94
- gas: txInner.gas || 0,
95
- mass: txInner.mass || 0,
96
- storageMass: txInner.storageMass || 0,
114
+ gas: toRpcNumber(txInner.gas || 0, "gas"),
115
+ // The transaction's storage mass commitment, under its Toccata name only. The
116
+ // node refuses a `mass` that differs from `storageMass`, so the deprecated
117
+ // field is read (older serializations) but never written.
118
+ storageMass: storageMassOf(txInner),
97
119
  payload: txInner.payload && txInner.payload.length > 0 ? typeof txInner.payload === "string" ? txInner.payload : toHex(txInner.payload) : ""
98
120
  };
99
121
  }
@@ -4,12 +4,11 @@ import {
4
4
  ensureDevAccounts,
5
5
  getOrCreateDevAccount,
6
6
  listDevAccountsSync
7
- } from "./chunk-YZ6W5EBW.js";
8
- import "./chunk-R5P3WIWR.js";
9
- import "./chunk-YBNHOFVX.js";
10
- import "./chunk-6DPO5V3N.js";
7
+ } from "./chunk-CELVD4YG.js";
8
+ import "./chunk-GM2BY4VS.js";
9
+ import "./chunk-BNF566PS.js";
10
+ import "./chunk-7KKJXU73.js";
11
11
  import "./chunk-YLG2NIAU.js";
12
- import "./chunk-MCKGQKYU.js";
13
12
  export {
14
13
  DEV_ACCOUNTS_PASSWORD,
15
14
  createDevSigner,