@openzeppelin/miden-multisig-client 0.18.0-rc.1 → 0.18.0-rc.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.
Files changed (106) hide show
  1. package/README.md +71 -17
  2. package/dist/account/builder.d.ts +3 -4
  3. package/dist/account/builder.d.ts.map +1 -1
  4. package/dist/account/builder.js +6 -13
  5. package/dist/account/builder.js.map +1 -1
  6. package/dist/client.d.ts +11 -4
  7. package/dist/client.d.ts.map +1 -1
  8. package/dist/client.js +8 -3
  9. package/dist/client.js.map +1 -1
  10. package/dist/config.d.ts +3 -0
  11. package/dist/config.d.ts.map +1 -0
  12. package/dist/config.js +14 -0
  13. package/dist/config.js.map +1 -0
  14. package/dist/index.d.ts +5 -5
  15. package/dist/index.d.ts.map +1 -1
  16. package/dist/index.js +3 -3
  17. package/dist/index.js.map +1 -1
  18. package/dist/multisig/authArgErrors.d.ts +15 -1
  19. package/dist/multisig/authArgErrors.d.ts.map +1 -1
  20. package/dist/multisig/authArgErrors.js +20 -0
  21. package/dist/multisig/authArgErrors.js.map +1 -1
  22. package/dist/multisig.d.ts +76 -25
  23. package/dist/multisig.d.ts.map +1 -1
  24. package/dist/multisig.js +196 -156
  25. package/dist/multisig.js.map +1 -1
  26. package/dist/procedures.d.ts +5 -5
  27. package/dist/procedures.js +5 -5
  28. package/dist/prover/workflow.d.ts +7 -3
  29. package/dist/prover/workflow.d.ts.map +1 -1
  30. package/dist/prover/workflow.js +7 -5
  31. package/dist/prover/workflow.js.map +1 -1
  32. package/dist/recovery/proposalNoteImport.d.ts +5 -6
  33. package/dist/recovery/proposalNoteImport.d.ts.map +1 -1
  34. package/dist/recovery/proposalNoteImport.js +12 -13
  35. package/dist/recovery/proposalNoteImport.js.map +1 -1
  36. package/dist/recovery/publicNoteBackfill.d.ts +2 -3
  37. package/dist/recovery/publicNoteBackfill.d.ts.map +1 -1
  38. package/dist/recovery/publicNoteBackfill.js +4 -5
  39. package/dist/recovery/publicNoteBackfill.js.map +1 -1
  40. package/dist/transaction/authArgs.d.ts +2 -3
  41. package/dist/transaction/authArgs.d.ts.map +1 -1
  42. package/dist/transaction/authArgs.js +7 -14
  43. package/dist/transaction/authArgs.js.map +1 -1
  44. package/dist/transaction/consumeNotes.d.ts +4 -12
  45. package/dist/transaction/consumeNotes.d.ts.map +1 -1
  46. package/dist/transaction/consumeNotes.js +10 -4
  47. package/dist/transaction/consumeNotes.js.map +1 -1
  48. package/dist/transaction/noteAuthentication.d.ts +2 -3
  49. package/dist/transaction/noteAuthentication.d.ts.map +1 -1
  50. package/dist/transaction/noteAuthentication.js +11 -11
  51. package/dist/transaction/noteAuthentication.js.map +1 -1
  52. package/dist/transaction/options.d.ts +0 -7
  53. package/dist/transaction/options.d.ts.map +1 -1
  54. package/dist/transaction/p2id.d.ts +2 -3
  55. package/dist/transaction/p2id.d.ts.map +1 -1
  56. package/dist/transaction/p2id.js.map +1 -1
  57. package/dist/transaction/summary.d.ts +94 -22
  58. package/dist/transaction/summary.d.ts.map +1 -1
  59. package/dist/transaction/summary.js +146 -12
  60. package/dist/transaction/summary.js.map +1 -1
  61. package/dist/transaction/updateGuardian.d.ts +3 -7
  62. package/dist/transaction/updateGuardian.d.ts.map +1 -1
  63. package/dist/transaction/updateGuardian.js +3 -4
  64. package/dist/transaction/updateGuardian.js.map +1 -1
  65. package/dist/transaction/updateProcedureThreshold.d.ts +3 -8
  66. package/dist/transaction/updateProcedureThreshold.d.ts.map +1 -1
  67. package/dist/transaction/updateProcedureThreshold.js +3 -4
  68. package/dist/transaction/updateProcedureThreshold.js.map +1 -1
  69. package/dist/transaction/updateSigners.d.ts +3 -8
  70. package/dist/transaction/updateSigners.d.ts.map +1 -1
  71. package/dist/transaction/updateSigners.js +3 -4
  72. package/dist/transaction/updateSigners.js.map +1 -1
  73. package/dist/transaction.d.ts +1 -1
  74. package/dist/transaction.d.ts.map +1 -1
  75. package/dist/transaction.js +1 -1
  76. package/dist/transaction.js.map +1 -1
  77. package/dist/types/proposal.d.ts +9 -8
  78. package/dist/types/proposal.d.ts.map +1 -1
  79. package/dist/types/proposal.js.map +1 -1
  80. package/package.json +4 -4
  81. package/src/account/builder.ts +6 -13
  82. package/src/client.ts +13 -10
  83. package/src/config.ts +14 -0
  84. package/src/index.ts +5 -3
  85. package/src/multisig/authArgErrors.ts +28 -1
  86. package/src/multisig.ts +238 -194
  87. package/src/procedures.ts +5 -5
  88. package/src/prover/workflow.ts +7 -10
  89. package/src/recovery/proposalNoteImport.ts +13 -15
  90. package/src/recovery/publicNoteBackfill.ts +6 -6
  91. package/src/transaction/authArgs.ts +15 -21
  92. package/src/transaction/consumeNotes.ts +6 -34
  93. package/src/transaction/noteAuthentication.ts +18 -13
  94. package/src/transaction/options.ts +0 -9
  95. package/src/transaction/p2id.ts +2 -3
  96. package/src/transaction/summary.ts +160 -57
  97. package/src/transaction/updateGuardian.ts +5 -23
  98. package/src/transaction/updateProcedureThreshold.ts +5 -25
  99. package/src/transaction/updateSigners.ts +5 -22
  100. package/src/transaction.ts +6 -0
  101. package/src/types/proposal.ts +9 -8
  102. package/dist/raw-client.d.ts +0 -14
  103. package/dist/raw-client.d.ts.map +0 -1
  104. package/dist/raw-client.js +0 -60
  105. package/dist/raw-client.js.map +0 -1
  106. package/src/raw-client.ts +0 -89
@@ -1,12 +1,8 @@
1
- import type {
2
- MidenClient,
3
- TransactionRequest,
4
- TransactionSummary,
5
- WasmWebClient,
6
- } from '@miden-sdk/miden-sdk';
7
- import { AccountId, ChainAnchor, Word } from '@miden-sdk/miden-sdk';
8
- import { getRawMidenClient } from '../raw-client.js';
1
+ import type { MidenClient, TransactionRequest, TransactionSummary } from '@miden-sdk/miden-sdk';
2
+ import { ChainAnchor, Word } from '@miden-sdk/miden-sdk';
3
+ import { BoundBlockNotDeclaredError } from '../multisig/authArgErrors.js';
9
4
  import { base64ToUint8Array, normalizeHexWord, uint8ArrayToBase64 } from '../utils/encoding.js';
5
+ import { requestBoundBlockNum } from './authArgs.js';
10
6
 
11
7
  /**
12
8
  * Layout of the six user params a multisig auth component binds into the
@@ -37,42 +33,61 @@ export class SummaryAnchorMismatchError extends Error {
37
33
  }
38
34
 
39
35
  /**
40
- * Captures a `ChainAnchor` for the request at the current sync height and
41
- * executes the transaction against it to obtain the summary awaiting
42
- * authorization. The anchor is returned alongside the summary so the proposer
43
- * can ship it with the signed data; cosigners and the executor then reproduce
44
- * the summary with {@link executeForSummaryAt} regardless of their own sync
45
- * height.
36
+ * The Miden client synced and its node still has not produced the block a
37
+ * proposal binds, so the proposal cannot execute at this client's tip yet.
38
+ * Worth retrying once the node catches up.
39
+ */
40
+ export class ChainBehindBoundBlockError extends Error {
41
+ readonly retryable = true;
42
+ readonly syncHeight: number;
43
+ readonly boundBlockNum: number;
44
+
45
+ constructor(details: { syncHeight: number; boundBlockNum: number }) {
46
+ super(
47
+ `the Miden client synced to block ${details.syncHeight}, below block ` +
48
+ `${details.boundBlockNum} the proposal binds; its node has not reached that block yet`,
49
+ );
50
+ this.name = 'ChainBehindBoundBlockError';
51
+ this.syncHeight = details.syncHeight;
52
+ this.boundBlockNum = details.boundBlockNum;
53
+ }
54
+ }
55
+
56
+ /**
57
+ * Whether a failed re-execution came from chain state this client can catch up
58
+ * with rather than from the proposal itself: a node that has not reached the
59
+ * bound block yet, or account state the node pruned because this client had
60
+ * not synced recently. Either clears on a later attempt, which syncs first.
61
+ */
62
+ export function isStaleChainError(error: unknown): boolean {
63
+ if (error instanceof ChainBehindBoundBlockError) {
64
+ return true;
65
+ }
66
+ const message = error instanceof Error ? error.message : String(error);
67
+ return message.includes('has been pruned');
68
+ }
69
+
70
+ /**
71
+ * Derives the summary awaiting authorization for a proposal the caller is
72
+ * creating now, and captures a `ChainAnchor` at the current sync height to ship
73
+ * with it.
46
74
  *
47
- * The request's auth args bind the block its summary commits to, and this
48
- * package pins that block to the anchor: a proposer builds at the sync height
49
- * the anchor is captured at, and a rebuild passes the anchor's block number.
50
- * The check below is what makes the first half hold.
75
+ * The summary is derived at the chain tip, like every other execution of a
76
+ * multisig proposal (see {@link executeForSummaryAtTip}). The anchor still
77
+ * travels in the proposal: it names the block the request's auth args bind,
78
+ * which is how a rebuild learns that block, and 0.18.0-rc.1 clients re-execute
79
+ * at it. A proposer builds at the sync height the anchor is captured at, and
80
+ * the check below is what makes that hold.
51
81
  */
52
- export function executeForSummary(
53
- client: MidenClient,
54
- accountId: string,
55
- txRequest: TransactionRequest,
56
- midenRpcEndpoint: string,
57
- ): Promise<{ summary: TransactionSummary; anchor: ChainAnchor }>;
58
- export function executeForSummary(
59
- client: WasmWebClient,
60
- accountId: string,
61
- txRequest: TransactionRequest,
62
- midenRpcEndpoint?: string,
63
- ): Promise<{ summary: TransactionSummary; anchor: ChainAnchor }>;
64
82
  export async function executeForSummary(
65
- client: MidenClient | WasmWebClient,
83
+ client: MidenClient,
66
84
  accountId: string,
67
85
  txRequest: TransactionRequest,
68
- midenRpcEndpoint?: string,
69
86
  ): Promise<{ summary: TransactionSummary; anchor: ChainAnchor }> {
70
- const acc = AccountId.fromHex(accountId);
71
- const rawClient = await getRawMidenClient(client, midenRpcEndpoint);
72
- const anchor = await rawClient.chainAnchorForRequest(txRequest);
87
+ const anchor = await client.transactions.captureAnchor(txRequest);
73
88
  let summary: TransactionSummary;
74
89
  try {
75
- summary = await rawClient.executeForSummaryAt(acc, txRequest, anchor);
90
+ summary = await executeForSummaryAtTip(client, accountId, txRequest);
76
91
  } catch (error) {
77
92
  anchor.free();
78
93
  throw error;
@@ -92,35 +107,122 @@ export async function executeForSummary(
92
107
  }
93
108
 
94
109
  /**
95
- * Executes a transaction at the given `ChainAnchor`'s reference block to
96
- * obtain the summary awaiting authorization: the anchored counterpart of
97
- * {@link executeForSummary} for cosigners and executors holding a proposal's
98
- * anchor.
110
+ * Executes a multisig request at the chain tip to obtain the summary awaiting
111
+ * authorization. This is how cosigners and the executor reproduce a proposal's
112
+ * summary, whatever block they have synced to.
113
+ *
114
+ * Since protocol 0.17 a multisig summary binds the block its auth args name
115
+ * (the bound block), not the block the transaction executes against, so it
116
+ * reproduces at any later tip once the bound block is in the transaction's
117
+ * partial blockchain. The request declares it through `withBlockNumbers`, and
118
+ * foreign accounts, the fee faucet among them, load at the tip. Re-executing at
119
+ * the proposal's anchor instead loads them at the bound block, which a node
120
+ * prunes about 50 blocks later (issue #462).
121
+ *
122
+ * The client has to have synced to at least the bound block. When it has not,
123
+ * this syncs once before executing.
124
+ *
125
+ * @throws BoundBlockNotDeclaredError when the request binds a block in its
126
+ * multisig auth args without declaring it.
99
127
  */
100
- export function executeForSummaryAt(
128
+ export async function executeForSummaryAtTip(
101
129
  client: MidenClient,
102
130
  accountId: string,
103
131
  txRequest: TransactionRequest,
104
- anchor: ChainAnchor,
105
- midenRpcEndpoint: string,
106
- ): Promise<TransactionSummary>;
107
- export function executeForSummaryAt(
108
- client: WasmWebClient,
109
- accountId: string,
110
- txRequest: TransactionRequest,
111
- anchor: ChainAnchor,
112
- midenRpcEndpoint?: string,
113
- ): Promise<TransactionSummary>;
132
+ ): Promise<TransactionSummary> {
133
+ await prepareTipExecution(client, txRequest);
134
+ return client.transactions.preview({
135
+ operation: 'custom',
136
+ account: accountId,
137
+ request: txRequest,
138
+ });
139
+ }
140
+
141
+ /**
142
+ * Gets `client` ready to execute `request` at the chain tip: checks the
143
+ * request declares the block its multisig auth args bind, and syncs to that
144
+ * block (see {@link syncToBoundBlock}).
145
+ *
146
+ * @throws BoundBlockNotDeclaredError when the request binds a block in its
147
+ * multisig auth args without declaring it.
148
+ */
149
+ export async function prepareTipExecution(
150
+ client: MidenClient,
151
+ request: TransactionRequest,
152
+ syncChain?: () => Promise<unknown>,
153
+ ): Promise<void> {
154
+ const boundBlockNum = requireDeclaredBoundBlock(request);
155
+ if (boundBlockNum !== undefined) {
156
+ await syncToBoundBlock(client, boundBlockNum, syncChain);
157
+ }
158
+ }
159
+
160
+ /**
161
+ * The block `request`'s multisig auth args bind, after checking the request
162
+ * declares it. `undefined` for a request without multisig auth args, which
163
+ * has no bound block to declare.
164
+ *
165
+ * @throws BoundBlockNotDeclaredError when the block is bound but not declared.
166
+ */
167
+ export function requireDeclaredBoundBlock(request: TransactionRequest): number | undefined {
168
+ const boundBlockNum = requestBoundBlockNum(request);
169
+ if (boundBlockNum !== undefined && !request.blockNumbers().includes(boundBlockNum)) {
170
+ throw new BoundBlockNotDeclaredError(boundBlockNum);
171
+ }
172
+ return boundBlockNum;
173
+ }
174
+
175
+ /**
176
+ * Syncs `client` once when its sync height is below `blockNum`, the block a
177
+ * proposal binds. Execution at a tip below it fails with "requested block N is
178
+ * after transaction reference block M", and a store that has never synced (a
179
+ * cosigner that has only just loaded the account) holds no header to rebuild
180
+ * the request from. The sync is a chain sync; `syncChain` lets a caller wrap
181
+ * it in its own retry policy.
182
+ *
183
+ * This does not make a store that is already past the bound block current. An
184
+ * execution loads foreign accounts, the fee faucet among them, at the store's
185
+ * sync height, which a node prunes about 50 blocks later, so the multisig
186
+ * entry points that re-execute a proposal sync the chain first.
187
+ *
188
+ * @throws ChainBehindBoundBlockError when the node has not reached the block.
189
+ */
190
+ export async function syncToBoundBlock(
191
+ client: MidenClient,
192
+ blockNum: number,
193
+ syncChain: () => Promise<unknown> = () => client.syncChain(),
194
+ ): Promise<void> {
195
+ if ((await client.getSyncHeight()) >= blockNum) {
196
+ return;
197
+ }
198
+ await syncChain();
199
+ const syncHeight = await client.getSyncHeight();
200
+ if (syncHeight < blockNum) {
201
+ throw new ChainBehindBoundBlockError({ syncHeight, boundBlockNum: blockNum });
202
+ }
203
+ }
204
+
205
+ /**
206
+ * Executes a transaction at the given `ChainAnchor`'s reference block to
207
+ * obtain the summary awaiting authorization.
208
+ *
209
+ * For a summary that binds the reference block, such as a single-signature
210
+ * one. A multisig proposal's summary binds its bound block instead and is
211
+ * reproduced with {@link executeForSummaryAtTip}: re-executing it at an anchor
212
+ * fails once the node prunes the anchor block's account state.
213
+ */
114
214
  export async function executeForSummaryAt(
115
- client: MidenClient | WasmWebClient,
215
+ client: MidenClient,
116
216
  accountId: string,
117
217
  txRequest: TransactionRequest,
118
218
  anchor: ChainAnchor,
119
- midenRpcEndpoint?: string,
120
219
  ): Promise<TransactionSummary> {
121
- const acc = AccountId.fromHex(accountId);
122
- const rawClient = await getRawMidenClient(client, midenRpcEndpoint);
123
- return rawClient.executeForSummaryAt(acc, txRequest, anchor);
220
+ return client.transactions.preview({
221
+ operation: 'custom',
222
+ account: accountId,
223
+ request: txRequest,
224
+ anchor,
225
+ });
124
226
  }
125
227
 
126
228
  /**
@@ -134,7 +236,8 @@ export function chainAnchorToBase64(anchor: ChainAnchor): string {
134
236
  * Deserializes a `ChainAnchor` from its base64 wire form. `ChainAnchor`
135
237
  * deserialization validates the header/chain consistency internally, so a
136
238
  * decoded anchor only needs its block commitment checked against the signed
137
- * transaction summary before it is safe to execute against.
239
+ * transaction summary before the block it names is taken as the one the
240
+ * summary binds.
138
241
  */
139
242
  export function chainAnchorFromBase64(anchorBase64: string): ChainAnchor {
140
243
  return ChainAnchor.deserialize(base64ToUint8Array(anchorBase64));
@@ -2,21 +2,18 @@ import {
2
2
  type MidenClient,
3
3
  TransactionRequest,
4
4
  TransactionScript,
5
- type WasmWebClient,
6
5
  Word,
7
6
  } from '@miden-sdk/miden-sdk';
8
- import { compileTxScript } from '../raw-client.js';
9
7
  import { normalizeHexWord } from '../utils/encoding.js';
10
8
  import { authSchemeId } from '../utils/signature.js';
11
9
  import { buildMultisigRequest, multisigRequestBuilder } from './authArgs.js';
12
- import type { MidenClientMultisigRequestOptions, MultisigRequestOptions } from './options.js';
10
+ import type { MultisigRequestOptions } from './options.js';
13
11
  import type { SignatureScheme } from '../types.js';
14
12
 
15
13
  async function buildUpdateGuardianScript(
16
- client: MidenClient | WasmWebClient,
14
+ client: MidenClient,
17
15
  newGuardianPubkey: string,
18
16
  signatureScheme: SignatureScheme,
19
- midenRpcEndpoint?: string,
20
17
  ): Promise<TransactionScript> {
21
18
  // A word literal preserves the key's element order on the operand stack.
22
19
  const keyLiteral = normalizeHexWord(newGuardianPubkey);
@@ -36,31 +33,16 @@ pub proc main
36
33
  end
37
34
  `;
38
35
 
39
- return compileTxScript(client, scriptSource, [], midenRpcEndpoint);
36
+ return client.compile.txScript({ code: scriptSource });
40
37
  }
41
38
 
42
- export function buildUpdateGuardianTransactionRequest(
43
- client: MidenClient,
44
- newGuardianPubkey: string,
45
- options: MidenClientMultisigRequestOptions,
46
- ): Promise<{ request: TransactionRequest; salt: Word }>;
47
- export function buildUpdateGuardianTransactionRequest(
48
- client: WasmWebClient,
49
- newGuardianPubkey: string,
50
- options: MultisigRequestOptions,
51
- ): Promise<{ request: TransactionRequest; salt: Word }>;
52
39
  export async function buildUpdateGuardianTransactionRequest(
53
- client: MidenClient | WasmWebClient,
40
+ client: MidenClient,
54
41
  newGuardianPubkey: string,
55
42
  options: MultisigRequestOptions,
56
43
  ): Promise<{ request: TransactionRequest; salt: Word }> {
57
44
  const signatureScheme = options.signatureScheme ?? 'falcon';
58
- const script = await buildUpdateGuardianScript(
59
- client,
60
- newGuardianPubkey,
61
- signatureScheme,
62
- options.midenRpcEndpoint,
63
- );
45
+ const script = await buildUpdateGuardianScript(client, newGuardianPubkey, signatureScheme);
64
46
 
65
47
  const { builder, saltHex } = await multisigRequestBuilder(client, options);
66
48
  let txBuilder = builder.withCustomScript(script);
@@ -5,15 +5,13 @@ import {
5
5
  Poseidon2,
6
6
  TransactionRequest,
7
7
  TransactionScript,
8
- type WasmWebClient,
9
8
  Word,
10
9
  Word as WordType,
11
10
  } from '@miden-sdk/miden-sdk';
12
11
  import { getProcedureRoot, type ProcedureName } from '../procedures.js';
13
- import { compileTxScript } from '../raw-client.js';
14
12
  import { normalizeHexWord } from '../utils/encoding.js';
15
13
  import { buildMultisigRequest, multisigRequestBuilder } from './authArgs.js';
16
- import type { MidenClientMultisigRequestOptions, MultisigRequestOptions } from './options.js';
14
+ import type { MultisigRequestOptions } from './options.js';
17
15
 
18
16
  function buildProcedureThresholdFelts(procedure: ProcedureName, threshold: number): Felt[] {
19
17
  const procedureRoot = WordType.fromHex(normalizeHexWord(getProcedureRoot(procedure)));
@@ -38,10 +36,9 @@ function buildProcedureThresholdConfigHash(procedure: ProcedureName, threshold:
38
36
  }
39
37
 
40
38
  async function buildUpdateProcedureThresholdScript(
41
- client: MidenClient | WasmWebClient,
39
+ client: MidenClient,
42
40
  procedure: ProcedureName,
43
41
  threshold: number,
44
- midenRpcEndpoint?: string,
45
42
  ): Promise<TransactionScript> {
46
43
  const procedureRoot = normalizeHexWord(getProcedureRoot(procedure));
47
44
 
@@ -58,35 +55,18 @@ pub proc main
58
55
  end
59
56
  `;
60
57
 
61
- return compileTxScript(client, scriptSource, [], midenRpcEndpoint);
58
+ return client.compile.txScript({ code: scriptSource });
62
59
  }
63
60
 
64
- export function buildUpdateProcedureThresholdTransactionRequest(
65
- client: MidenClient,
66
- procedure: ProcedureName,
67
- threshold: number,
68
- options: MidenClientMultisigRequestOptions,
69
- ): Promise<{ request: TransactionRequest; salt: Word; configHash: Word }>;
70
- export function buildUpdateProcedureThresholdTransactionRequest(
71
- client: WasmWebClient,
72
- procedure: ProcedureName,
73
- threshold: number,
74
- options: MultisigRequestOptions,
75
- ): Promise<{ request: TransactionRequest; salt: Word; configHash: Word }>;
76
61
  export async function buildUpdateProcedureThresholdTransactionRequest(
77
- client: MidenClient | WasmWebClient,
62
+ client: MidenClient,
78
63
  procedure: ProcedureName,
79
64
  threshold: number,
80
65
  options: MultisigRequestOptions,
81
66
  ): Promise<{ request: TransactionRequest; salt: Word; configHash: Word }> {
82
67
  const configHash = buildProcedureThresholdConfigHash(procedure, threshold);
83
68
 
84
- const script = await buildUpdateProcedureThresholdScript(
85
- client,
86
- procedure,
87
- threshold,
88
- options.midenRpcEndpoint,
89
- );
69
+ const script = await buildUpdateProcedureThresholdScript(client, procedure, threshold);
90
70
  const { builder, saltHex } = await multisigRequestBuilder(client, options);
91
71
  let txBuilder = builder.withCustomScript(script);
92
72
 
@@ -6,15 +6,13 @@ import {
6
6
  Poseidon2,
7
7
  TransactionRequest,
8
8
  TransactionScript,
9
- type WasmWebClient,
10
9
  Word,
11
10
  Word as WordType,
12
11
  } from '@miden-sdk/miden-sdk';
13
- import { compileTxScript } from '../raw-client.js';
14
12
  import { normalizeHexWord } from '../utils/encoding.js';
15
13
  import { authSchemeId } from '../utils/signature.js';
16
14
  import { buildMultisigRequest, multisigRequestBuilder } from './authArgs.js';
17
- import type { MidenClientMultisigRequestOptions, MultisigRequestOptions } from './options.js';
15
+ import type { MultisigRequestOptions } from './options.js';
18
16
  import type { SignatureScheme } from '../types.js';
19
17
 
20
18
  function buildMultisigConfigFelts(
@@ -56,10 +54,7 @@ export function buildMultisigConfigAdvice(
56
54
  return { configHash, payload };
57
55
  }
58
56
 
59
- async function buildUpdateSignersScript(
60
- client: MidenClient | WasmWebClient,
61
- midenRpcEndpoint?: string,
62
- ): Promise<TransactionScript> {
57
+ async function buildUpdateSignersScript(client: MidenClient): Promise<TransactionScript> {
63
58
  const scriptSource = `
64
59
  use miden::standards::auth::multisig
65
60
 
@@ -69,23 +64,11 @@ pub proc main
69
64
  end
70
65
  `;
71
66
 
72
- return compileTxScript(client, scriptSource, [], midenRpcEndpoint);
67
+ return client.compile.txScript({ code: scriptSource });
73
68
  }
74
69
 
75
- export function buildUpdateSignersTransactionRequest(
76
- client: MidenClient,
77
- threshold: number,
78
- signerCommitments: string[],
79
- options: MidenClientMultisigRequestOptions,
80
- ): Promise<{ request: TransactionRequest; salt: Word; configHash: Word }>;
81
- export function buildUpdateSignersTransactionRequest(
82
- client: WasmWebClient,
83
- threshold: number,
84
- signerCommitments: string[],
85
- options: MultisigRequestOptions,
86
- ): Promise<{ request: TransactionRequest; salt: Word; configHash: Word }>;
87
70
  export async function buildUpdateSignersTransactionRequest(
88
- client: MidenClient | WasmWebClient,
71
+ client: MidenClient,
89
72
  threshold: number,
90
73
  signerCommitments: string[],
91
74
  options: MultisigRequestOptions,
@@ -112,7 +95,7 @@ export async function buildUpdateSignersTransactionRequest(
112
95
  const advice = new AdviceMap();
113
96
  advice.insert(configHashForAdvice, payload);
114
97
 
115
- const script = await buildUpdateSignersScript(client, options.midenRpcEndpoint);
98
+ const script = await buildUpdateSignersScript(client);
116
99
 
117
100
  const { builder, saltHex } = await multisigRequestBuilder(client, options);
118
101
  let txBuilder = builder
@@ -10,11 +10,17 @@ export {
10
10
  buildConsumeNotesTransactionRequestFromNotes,
11
11
  } from './transaction/consumeNotes.js';
12
12
  export {
13
+ ChainBehindBoundBlockError,
13
14
  chainAnchorBlockNum,
14
15
  chainAnchorFromBase64,
15
16
  chainAnchorToBase64,
16
17
  executeForSummary,
17
18
  executeForSummaryAt,
19
+ executeForSummaryAtTip,
20
+ prepareTipExecution,
21
+ isStaleChainError,
22
+ requireDeclaredBoundBlock,
23
+ syncToBoundBlock,
18
24
  summaryApprovalExpirationBlockNum,
19
25
  summarySalt,
20
26
  SummaryAnchorMismatchError,
@@ -38,11 +38,11 @@ interface BaseProposalMetadata {
38
38
  saltHex?: string;
39
39
  requiredSignatures?: number;
40
40
  /**
41
- * Base64-serialized Miden `ChainAnchor` pinning the reference block the
42
- * proposal's transaction summary was built at. Required to verify or
43
- * execute the proposal: since protocol 0.16 the signed summary binds the
44
- * reference block commitment, so it only reproduces when re-executed at
45
- * that block.
41
+ * Base64-serialized Miden `ChainAnchor` at the block the proposal's
42
+ * transaction summary binds, the proposer's sync height when it built the
43
+ * request. Required, and checked against the summary's block commitment: a
44
+ * rebuild binds the block it names. The proposal executes at the chain tip,
45
+ * not at the anchor; 0.18.0-rc.1 clients still re-execute at it.
46
46
  */
47
47
  chainAnchor?: string;
48
48
  }
@@ -175,9 +175,10 @@ export interface Proposal {
175
175
  /**
176
176
  * Outcome of checking a proposal's metadata against its signed summary.
177
177
  * `failed.retryable` is true when the failure came from a transient node or
178
- * RPC error, so the same proposal may verify on a later sync; false when the
179
- * proposal itself cannot be reproduced (tampered metadata, an anchor block the
180
- * node has pruned) and it has to be re-proposed.
178
+ * RPC error, or from chain state this client had not caught up with, so the
179
+ * same proposal may verify on a later sync; false when the proposal itself
180
+ * cannot be reproduced (tampered metadata, for example) and it has to be
181
+ * re-proposed.
181
182
  */
182
183
  export type ProposalVerification =
183
184
  | { status: 'unchecked' }
@@ -1,14 +0,0 @@
1
- import { MidenClient, type TransactionProver, type TransactionScript, WasmWebClient } from '@miden-sdk/miden-sdk';
2
- export type RawClientSource = MidenClient | WasmWebClient;
3
- export interface ScriptLibrarySource {
4
- namespace: string;
5
- code: string;
6
- linking?: 'dynamic' | 'static';
7
- }
8
- export declare function requireConfigValue(field: string, value?: unknown): string;
9
- export declare function requireMidenRpcEndpoint(endpoint?: string): string;
10
- export declare function isPublicMidenClient(client: RawClientSource): client is MidenClient;
11
- export declare function getRawMidenClient(client: RawClientSource, rpcUrl?: string): Promise<WasmWebClient>;
12
- export declare function getTransactionProver(client: RawClientSource): TransactionProver | null;
13
- export declare function compileTxScript(client: RawClientSource, code: string, libraries?: ScriptLibrarySource[], rpcUrl?: string): Promise<TransactionScript>;
14
- //# sourceMappingURL=raw-client.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"raw-client.d.ts","sourceRoot":"","sources":["../src/raw-client.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,WAAW,EACX,KAAK,iBAAiB,EACtB,KAAK,iBAAiB,EACtB,aAAa,EACd,MAAM,sBAAsB,CAAC;AAE9B,MAAM,MAAM,eAAe,GAAG,WAAW,GAAG,aAAa,CAAC;AAC1D,MAAM,WAAW,mBAAmB;IAClC,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,CAAC,EAAE,SAAS,GAAG,QAAQ,CAAC;CAChC;AAID,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,CAAC,EAAE,OAAO,GAAG,MAAM,CASzE;AAED,wBAAgB,uBAAuB,CAAC,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,CAEjE;AAED,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,eAAe,GAAG,MAAM,IAAI,WAAW,CAElF;AAED,wBAAsB,iBAAiB,CACrC,MAAM,EAAE,eAAe,EACvB,MAAM,CAAC,EAAE,MAAM,GACd,OAAO,CAAC,aAAa,CAAC,CAcxB;AAWD,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,eAAe,GAAG,iBAAiB,GAAG,IAAI,CAEtF;AAED,wBAAsB,eAAe,CACnC,MAAM,EAAE,eAAe,EACvB,IAAI,EAAE,MAAM,EACZ,SAAS,GAAE,mBAAmB,EAAO,EACrC,MAAM,CAAC,EAAE,MAAM,GACd,OAAO,CAAC,iBAAiB,CAAC,CAgB5B"}
@@ -1,60 +0,0 @@
1
- import { WasmWebClient, } from '@miden-sdk/miden-sdk';
2
- const rawClientCache = new WeakMap();
3
- export function requireConfigValue(field, value) {
4
- if (typeof value !== 'string') {
5
- throw new Error(`missing required configuration: ${field}`);
6
- }
7
- const normalizedValue = value.trim();
8
- if (normalizedValue === '') {
9
- throw new Error(`missing required configuration: ${field}`);
10
- }
11
- return normalizedValue;
12
- }
13
- export function requireMidenRpcEndpoint(endpoint) {
14
- return requireConfigValue('midenRpcEndpoint', endpoint);
15
- }
16
- export function isPublicMidenClient(client) {
17
- return 'accounts' in client && 'sync' in client;
18
- }
19
- export async function getRawMidenClient(client, rpcUrl) {
20
- if (!isPublicMidenClient(client)) {
21
- return client;
22
- }
23
- const cached = rawClientCache.get(client);
24
- if (cached) {
25
- return cached;
26
- }
27
- const endpoint = requireMidenRpcEndpoint(rpcUrl);
28
- const rawClient = createRawClient(client, endpoint);
29
- rawClientCache.set(client, rawClient);
30
- return rawClient;
31
- }
32
- /**
33
- * Opens the WASM client behind `client` on the same store. The protocol
34
- * configuration comes from the node with every sync and is read from that
35
- * shared store, so the shadow needs no fee faucet of its own.
36
- */
37
- async function createRawClient(client, endpoint) {
38
- return WasmWebClient.createClient(endpoint, undefined, undefined, await client.storeIdentifier());
39
- }
40
- export function getTransactionProver(client) {
41
- return isPublicMidenClient(client) ? client.defaultProver : null;
42
- }
43
- export async function compileTxScript(client, code, libraries = [], rpcUrl) {
44
- if (isPublicMidenClient(client)) {
45
- return client.compile.txScript({ code, libraries });
46
- }
47
- const rawClient = await getRawMidenClient(client, rpcUrl);
48
- const builder = await rawClient.createCodeBuilder();
49
- for (const library of libraries) {
50
- const builtLibrary = builder.buildLibrary(library.namespace, library.code);
51
- if (library.linking === 'static') {
52
- builder.linkStaticLibrary(builtLibrary);
53
- }
54
- else {
55
- builder.linkDynamicLibrary(builtLibrary);
56
- }
57
- }
58
- return builder.compileTxScript(code);
59
- }
60
- //# sourceMappingURL=raw-client.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"raw-client.js","sourceRoot":"","sources":["../src/raw-client.ts"],"names":[],"mappings":"AAAA,OAAO,EAIL,aAAa,GACd,MAAM,sBAAsB,CAAC;AAS9B,MAAM,cAAc,GAAG,IAAI,OAAO,EAAuC,CAAC;AAE1E,MAAM,UAAU,kBAAkB,CAAC,KAAa,EAAE,KAAe;IAC/D,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;QAC9B,MAAM,IAAI,KAAK,CAAC,mCAAmC,KAAK,EAAE,CAAC,CAAC;IAC9D,CAAC;IACD,MAAM,eAAe,GAAG,KAAK,CAAC,IAAI,EAAE,CAAC;IACrC,IAAI,eAAe,KAAK,EAAE,EAAE,CAAC;QAC3B,MAAM,IAAI,KAAK,CAAC,mCAAmC,KAAK,EAAE,CAAC,CAAC;IAC9D,CAAC;IACD,OAAO,eAAe,CAAC;AACzB,CAAC;AAED,MAAM,UAAU,uBAAuB,CAAC,QAAiB;IACvD,OAAO,kBAAkB,CAAC,kBAAkB,EAAE,QAAQ,CAAC,CAAC;AAC1D,CAAC;AAED,MAAM,UAAU,mBAAmB,CAAC,MAAuB;IACzD,OAAO,UAAU,IAAI,MAAM,IAAI,MAAM,IAAI,MAAM,CAAC;AAClD,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,iBAAiB,CACrC,MAAuB,EACvB,MAAe;IAEf,IAAI,CAAC,mBAAmB,CAAC,MAAM,CAAC,EAAE,CAAC;QACjC,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,MAAM,GAAG,cAAc,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;IAC1C,IAAI,MAAM,EAAE,CAAC;QACX,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,QAAQ,GAAG,uBAAuB,CAAC,MAAM,CAAC,CAAC;IACjD,MAAM,SAAS,GAAG,eAAe,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;IACpD,cAAc,CAAC,GAAG,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC;IACtC,OAAO,SAAS,CAAC;AACnB,CAAC;AAED;;;;GAIG;AACH,KAAK,UAAU,eAAe,CAAC,MAAmB,EAAE,QAAgB;IAClE,OAAO,aAAa,CAAC,YAAY,CAAC,QAAQ,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,MAAM,CAAC,eAAe,EAAE,CAAC,CAAC;AACpG,CAAC;AAED,MAAM,UAAU,oBAAoB,CAAC,MAAuB;IAC1D,OAAO,mBAAmB,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC,CAAC,IAAI,CAAC;AACnE,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,eAAe,CACnC,MAAuB,EACvB,IAAY,EACZ,YAAmC,EAAE,EACrC,MAAe;IAEf,IAAI,mBAAmB,CAAC,MAAM,CAAC,EAAE,CAAC;QAChC,OAAO,MAAM,CAAC,OAAO,CAAC,QAAQ,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,CAAC,CAAC;IACtD,CAAC;IAED,MAAM,SAAS,GAAG,MAAM,iBAAiB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC1D,MAAM,OAAO,GAAG,MAAM,SAAS,CAAC,iBAAiB,EAAE,CAAC;IACpD,KAAK,MAAM,OAAO,IAAI,SAAS,EAAE,CAAC;QAChC,MAAM,YAAY,GAAG,OAAO,CAAC,YAAY,CAAC,OAAO,CAAC,SAAS,EAAE,OAAO,CAAC,IAAI,CAAC,CAAC;QAC3E,IAAI,OAAO,CAAC,OAAO,KAAK,QAAQ,EAAE,CAAC;YACjC,OAAO,CAAC,iBAAiB,CAAC,YAAY,CAAC,CAAC;QAC1C,CAAC;aAAM,CAAC;YACN,OAAO,CAAC,kBAAkB,CAAC,YAAY,CAAC,CAAC;QAC3C,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC,eAAe,CAAC,IAAI,CAAC,CAAC;AACvC,CAAC"}