@invisible-labs/sdk 0.8.0-devnet → 0.10.0-devnet
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +17 -3
- package/dist/.invisible-sdk-build-target.json +2 -2
- package/dist/{chunk-MZKJU3UA.js → chunk-6AGC3IOB.js} +16 -6
- package/dist/chunk-6AGC3IOB.js.map +1 -0
- package/dist/{chunk-HJFMDMPY.js → chunk-6AKBRYKO.js} +3 -3
- package/dist/{chunk-HJFMDMPY.js.map → chunk-6AKBRYKO.js.map} +1 -1
- package/dist/{chunk-DCTYBUY3.js → chunk-AIKC2XQS.js} +3 -3
- package/dist/{chunk-DCTYBUY3.js.map → chunk-AIKC2XQS.js.map} +1 -1
- package/dist/{chunk-Y7AK6RBV.js → chunk-ANQMIQYS.js} +587 -19
- package/dist/chunk-ANQMIQYS.js.map +1 -0
- package/dist/{chunk-MPNVF727.js → chunk-DFBH5XLM.js} +569 -78
- package/dist/chunk-DFBH5XLM.js.map +1 -0
- package/dist/{chunk-EBWTAXNT.js → chunk-EPWTRF5U.js} +3 -3
- package/dist/{chunk-EBWTAXNT.js.map → chunk-EPWTRF5U.js.map} +1 -1
- package/dist/{chunk-IG6JJFR2.js → chunk-HWRMSK7E.js} +8 -6
- package/dist/chunk-HWRMSK7E.js.map +1 -0
- package/dist/{chunk-K67FTCQU.js → chunk-JNNVPZEU.js} +3 -3
- package/dist/chunk-JNNVPZEU.js.map +1 -0
- package/dist/{chunk-QRN46R3F.js → chunk-RWKG7N7I.js} +10 -3
- package/dist/chunk-RWKG7N7I.js.map +1 -0
- package/dist/coordinator-T2B7253V.js +4 -0
- package/dist/{coordinator-E2TS6NR2.js.map → coordinator-T2B7253V.js.map} +1 -1
- package/dist/dkgWorker.js +1 -1
- package/dist/events.js +3 -3
- package/dist/frostRuntime-JESDHN6O.js +4 -0
- package/dist/{frostRuntime-6FTPKUCP.js.map → frostRuntime-JESDHN6O.js.map} +1 -1
- package/dist/index.d.ts +4 -4
- package/dist/index.js +9 -9
- package/dist/index.js.map +1 -1
- package/dist/lp.d.ts +48 -1
- package/dist/lp.js +360 -82
- package/dist/lp.js.map +1 -1
- package/dist/stats.js +1 -1
- package/dist/storage.js +2 -2
- package/dist/{types.generated-YhFu9ZBR.d.ts → types.generated-CtMxCo9F.d.ts} +80 -2
- package/dist/user.d.ts +25 -11
- package/dist/user.js +124 -37
- package/dist/user.js.map +1 -1
- package/package.json +2 -2
- package/dist/chunk-IG6JJFR2.js.map +0 -1
- package/dist/chunk-K67FTCQU.js.map +0 -1
- package/dist/chunk-MPNVF727.js.map +0 -1
- package/dist/chunk-MZKJU3UA.js.map +0 -1
- package/dist/chunk-QRN46R3F.js.map +0 -1
- package/dist/chunk-Y7AK6RBV.js.map +0 -1
- package/dist/coordinator-E2TS6NR2.js +0 -4
- package/dist/frostRuntime-6FTPKUCP.js +0 -4
package/dist/stats.js
CHANGED
package/dist/storage.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
export { browserStorage, extensionStorage, inMemoryStorage } from './chunk-
|
|
2
|
-
import './chunk-
|
|
1
|
+
export { browserStorage, extensionStorage, inMemoryStorage } from './chunk-AIKC2XQS.js';
|
|
2
|
+
import './chunk-RWKG7N7I.js';
|
|
3
3
|
import './chunk-VR6T6OJS.js';
|
|
4
4
|
//# sourceMappingURL=storage.js.map
|
|
5
5
|
//# sourceMappingURL=storage.js.map
|
|
@@ -18,9 +18,10 @@ type TransportErrorCode = "WS_HANDSHAKE_FAILED" | "NOISE_HANDSHAKE_FAILED" | "NO
|
|
|
18
18
|
/** Leader/role routing failures. Failover and re-attest. */
|
|
19
19
|
type RoutingErrorCode = "WRONG_ROLE" | "STALE_LEADER_EPOCH" | "POOL_DEGRADED" | "VERSION_NOT_SUPPORTED";
|
|
20
20
|
/** Coordinator-side command rejections. Product decides whether to retry. */
|
|
21
|
-
type CommandErrorCode = "REJECTED_GUARD" | "REJECTED_STATE" | "REJECTED_EXPIRED" | "REJECTED_STALE_JOB" | "REJECTED_RESOURCE_CAP";
|
|
21
|
+
type CommandErrorCode = "REJECTED_GUARD" | "REJECTED_STATE" | "REJECTED_EXPIRED" | "REJECTED_STALE_JOB" | "REJECTED_RESOURCE_CAP" | "RETRYABLE_BUSY";
|
|
22
|
+
declare const COORDINATOR_CAPACITY_FULL_ERROR_CODE: "ERR_ADMISSION_CAPACITY_FULL";
|
|
22
23
|
/** Coordinator wire error code preserved on command rejections. */
|
|
23
|
-
type CoordinatorWireErrorCode = "ERR_INVALID_PAYLOAD" | "ERR_UNEXPECTED_TYPE" | "ERR_UNKNOWN_SWAP" | "ERR_POLICY_VIOLATION" | "ERR_INVALID_RECOVERY_CODE" | "ERR_SWAP_NOT_REFUNDABLE" | "ERR_DKG_FAILURE" | "ERR_INTERNAL" | "ERR_INVALID_DEPOSIT" | "ERR_SETTLEMENT_FAILED";
|
|
24
|
+
type CoordinatorWireErrorCode = "ERR_INVALID_PAYLOAD" | "ERR_UNEXPECTED_TYPE" | "ERR_UNKNOWN_SWAP" | "ERR_POLICY_VIOLATION" | "ERR_INVALID_RECOVERY_CODE" | "ERR_SWAP_NOT_REFUNDABLE" | "ERR_DKG_FAILURE" | "ERR_INTERNAL" | "ERR_PRESEAL_ADMISSION_BUSY" | "ERR_INITIALIZATION_BUSY" | typeof COORDINATOR_CAPACITY_FULL_ERROR_CODE | "ERR_INVALID_DEPOSIT" | "ERR_SETTLEMENT_FAILED";
|
|
24
25
|
/** Local input-validation failures. Never sent on the wire; fix the input. */
|
|
25
26
|
type PolicyValidationErrorCode = "INVALID_PAYOUT_PLAN" | "INVALID_WITHDRAWAL_PLAN" | "INVALID_POSITION_AUTH" | "INVALID_REDEMPTION_PLAN" | "INVALID_DESTINATION_ADDRESS" | "INVALID_AMOUNT";
|
|
26
27
|
/** Storage-adapter failures. */
|
|
@@ -53,6 +54,8 @@ interface StorageErrorOptions extends InvisibleErrorOptions {
|
|
|
53
54
|
interface CommandErrorOptions extends InvisibleErrorOptions {
|
|
54
55
|
/** Exact coordinator `Error` envelope code, when the rejection came from the wire. */
|
|
55
56
|
readonly coordinatorCode?: CoordinatorWireErrorCode;
|
|
57
|
+
/** Exact coordinator `Error` envelope message, when `message` is user-facing copy. */
|
|
58
|
+
readonly coordinatorMessage?: string;
|
|
56
59
|
/** Request id rejected by the coordinator, when present in the `Error` envelope. */
|
|
57
60
|
readonly failedReqId?: number;
|
|
58
61
|
}
|
|
@@ -84,6 +87,7 @@ declare class RoutingError extends InvisibleError {
|
|
|
84
87
|
declare class CommandError extends InvisibleError {
|
|
85
88
|
readonly code: CommandErrorCode;
|
|
86
89
|
readonly coordinatorCode?: CoordinatorWireErrorCode;
|
|
90
|
+
readonly coordinatorMessage?: string;
|
|
87
91
|
readonly failedReqId?: number;
|
|
88
92
|
constructor(code: CommandErrorCode, message: string, options?: CommandErrorOptions);
|
|
89
93
|
}
|
|
@@ -142,6 +146,12 @@ type RuntimeMeasurements = {
|
|
|
142
146
|
readonly rtmr2: string;
|
|
143
147
|
readonly rtmr3: string;
|
|
144
148
|
};
|
|
149
|
+
type LpFeePolicy = {
|
|
150
|
+
readonly version: 1;
|
|
151
|
+
readonly profile: "internal" | "partner";
|
|
152
|
+
readonly commission_bps: 0 | 6000;
|
|
153
|
+
readonly policy_hash: string;
|
|
154
|
+
};
|
|
145
155
|
type LpPositionView = {
|
|
146
156
|
readonly id: string;
|
|
147
157
|
readonly status: "dkg_pending" | "active" | "withdrawing" | "closed";
|
|
@@ -161,6 +171,74 @@ type LpPositionView = {
|
|
|
161
171
|
readonly grantRevision: number;
|
|
162
172
|
readonly observedAtMs: number;
|
|
163
173
|
};
|
|
174
|
+
readonly feePolicy?: LpFeePolicy;
|
|
175
|
+
readonly lpFeePolicyVersion?: 1;
|
|
176
|
+
readonly actorSync?: {
|
|
177
|
+
readonly economicReturn?: {
|
|
178
|
+
readonly providerRewardLamports: string;
|
|
179
|
+
readonly sourceExpenseCompensationLamports: string;
|
|
180
|
+
readonly chargedReimbursementLossLamports: string;
|
|
181
|
+
readonly netEconomicReturnLamports: string;
|
|
182
|
+
};
|
|
183
|
+
readonly lpPositionId: string;
|
|
184
|
+
readonly status: "idle" | "settling" | "reimbursement_due";
|
|
185
|
+
readonly sourceLiquidityUse: "not_materialized" | "available" | "locked_for_payout" | "pending_finality" | "spent" | "released";
|
|
186
|
+
readonly redeemablePrincipalLamports?: number;
|
|
187
|
+
readonly redeemableFeeLamports?: number;
|
|
188
|
+
readonly lifetimeEarnedLamports?: number;
|
|
189
|
+
readonly redeemablePrincipalSourceCount?: number;
|
|
190
|
+
readonly redeemableFeeSourceCount?: number;
|
|
191
|
+
readonly redeemableSourceCount?: number;
|
|
192
|
+
readonly pendingReservationCount: number;
|
|
193
|
+
readonly reservedPayoutLamports: number;
|
|
194
|
+
readonly estimatedNetworkFeeLamports: number;
|
|
195
|
+
readonly reimbursementDueCount: number;
|
|
196
|
+
readonly reimbursementDueSourceCount: number;
|
|
197
|
+
readonly reimbursementDuePayoutLamports: number;
|
|
198
|
+
readonly reimbursementDueNetworkFeeLamports: number;
|
|
199
|
+
readonly withdrawalRequestedLamports: number;
|
|
200
|
+
readonly withdrawalLandedLamports: number;
|
|
201
|
+
readonly withdrawalLandedFeeLamports: number;
|
|
202
|
+
readonly withdrawalCanceledLamports: number;
|
|
203
|
+
readonly withdrawalNetworkFeeLossLamports: number;
|
|
204
|
+
readonly withdrawalTxHashes: readonly string[];
|
|
205
|
+
readonly redemptionHistory?: readonly {
|
|
206
|
+
readonly redemptionId: string;
|
|
207
|
+
readonly state: "requested" | "match_requested" | "reserved" | "pending" | "confirmed" | "rejected";
|
|
208
|
+
readonly withdrawalMode?: "exact" | "max_available";
|
|
209
|
+
readonly acceptedLamports: number;
|
|
210
|
+
readonly acceptedDepositPrincipalLamports: number;
|
|
211
|
+
readonly acceptedEarnedFeeLamports: number;
|
|
212
|
+
readonly landedLamports: number;
|
|
213
|
+
readonly landedDepositPrincipalLamports: number;
|
|
214
|
+
readonly landedEarnedFeeLamports: number;
|
|
215
|
+
readonly canceledLamports: number;
|
|
216
|
+
readonly canceledDepositPrincipalLamports: number;
|
|
217
|
+
readonly canceledEarnedFeeLamports: number;
|
|
218
|
+
readonly networkFeeLamports: number;
|
|
219
|
+
readonly networkFeeLossLamports: number;
|
|
220
|
+
readonly failedAttempts: number;
|
|
221
|
+
readonly destinationAddresses: readonly string[];
|
|
222
|
+
readonly destinationCount: number;
|
|
223
|
+
readonly txSignatures: readonly string[];
|
|
224
|
+
readonly txSignatureCount: number;
|
|
225
|
+
readonly detailsTruncated: boolean;
|
|
226
|
+
readonly stateVersion: number;
|
|
227
|
+
readonly createdAtMs: number;
|
|
228
|
+
readonly updatedAtMs: number;
|
|
229
|
+
readonly feePolicyHash?: string;
|
|
230
|
+
readonly feeBasisRevision?: number;
|
|
231
|
+
}[];
|
|
232
|
+
readonly redemptionHistoryHasMore?: boolean;
|
|
233
|
+
readonly redemptionHistoryNextCursor?: string;
|
|
234
|
+
readonly stateVersion: number;
|
|
235
|
+
readonly updatedAtMs: number;
|
|
236
|
+
readonly feePolicy?: LpFeePolicy;
|
|
237
|
+
readonly feeBasisRevision?: number;
|
|
238
|
+
readonly grossFeeLamports?: number;
|
|
239
|
+
readonly protocolCommissionLamports?: number;
|
|
240
|
+
readonly redeemableProjectionAvailable: boolean;
|
|
241
|
+
};
|
|
164
242
|
};
|
|
165
243
|
type PayoutDestination = {
|
|
166
244
|
readonly address: string;
|
package/dist/user.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
+
import { C as CommandError, P as PayoutPolicy } from './types.generated-CtMxCo9F.js';
|
|
2
|
+
export { I as InvalidDepositAmountError } from './types.generated-CtMxCo9F.js';
|
|
1
3
|
import { S as Session } from './session-DFuy54C-.js';
|
|
2
|
-
import { P as PayoutPolicy } from './types.generated-YhFu9ZBR.js';
|
|
3
|
-
export { I as InvalidDepositAmountError } from './types.generated-YhFu9ZBR.js';
|
|
4
4
|
|
|
5
5
|
/**
|
|
6
6
|
* Acceptance receipts (spec section 8.2).
|
|
@@ -30,6 +30,7 @@ type PayoutSpec = {
|
|
|
30
30
|
readonly destination_addresses: readonly string[];
|
|
31
31
|
};
|
|
32
32
|
type SpendingPolicySnapshot = {
|
|
33
|
+
readonly economics?: "legacy" | "zero_protocol_fees";
|
|
33
34
|
readonly asset: "SOL";
|
|
34
35
|
readonly entry_amount_lamports: number;
|
|
35
36
|
readonly total_committed_lamports: number;
|
|
@@ -79,6 +80,7 @@ type NormalUserRefundStatus = "queued" | "reserved" | "submitted" | "confirming"
|
|
|
79
80
|
type SourceLiquidityUse = "not_materialized" | "available" | "locked_for_payout" | "pending_finality" | "spent" | "released";
|
|
80
81
|
type NormalUserContractSyncSnapshot = {
|
|
81
82
|
readonly contract_id: string;
|
|
83
|
+
readonly deposit_origin_address?: string | null;
|
|
82
84
|
readonly status: NormalUserContractStatus;
|
|
83
85
|
readonly settlement_phase: NormalUserSettlementPhase;
|
|
84
86
|
readonly refundability: NormalUserRefundability;
|
|
@@ -129,8 +131,17 @@ type RefundAcceptanceReceipt = AcceptanceReceipt & {
|
|
|
129
131
|
readonly amountLamports: number;
|
|
130
132
|
readonly acceptedAtMs?: number;
|
|
131
133
|
};
|
|
134
|
+
/** Caller-owned delay/continuation for a proven, same-command initialization rejection. */
|
|
135
|
+
type InitializationRetry = {
|
|
136
|
+
readonly swapId: string;
|
|
137
|
+
readonly stage: "DkgRound2" | "DelegateShare";
|
|
138
|
+
readonly error: CommandError;
|
|
139
|
+
};
|
|
132
140
|
type RunSwapParams = {
|
|
141
|
+
/** No automatic policy: absent this callback, initialization busy is returned to the caller. */
|
|
142
|
+
onInitializationRetry?: (retry: InitializationRetry) => Promise<void>;
|
|
133
143
|
amountLamports: number;
|
|
144
|
+
batchExclusionId?: string;
|
|
134
145
|
payoutSpec: PayoutSpec;
|
|
135
146
|
payoutDeadlineMs?: number;
|
|
136
147
|
onPolicySnapshot?: (policy: SpendingPolicySnapshot) => void;
|
|
@@ -167,6 +178,7 @@ type RunSwapParams = {
|
|
|
167
178
|
originAddress: string | undefined;
|
|
168
179
|
}) => void | Promise<void>;
|
|
169
180
|
payoutWindowMs?: number;
|
|
181
|
+
signal?: AbortSignal;
|
|
170
182
|
};
|
|
171
183
|
/**
|
|
172
184
|
* Details returned once the coordinator has accepted, initialized, and
|
|
@@ -197,6 +209,8 @@ type ContractRequestResult = {
|
|
|
197
209
|
};
|
|
198
210
|
/** Inputs for resuming an already allocated pre-delegation contract. */
|
|
199
211
|
type ResumePreDelegationParams = {
|
|
212
|
+
readonly onInitializationRetry?: RunSwapParams["onInitializationRetry"];
|
|
213
|
+
readonly signal?: AbortSignal;
|
|
200
214
|
readonly swapId: string;
|
|
201
215
|
readonly resumeSecret: Uint8Array;
|
|
202
216
|
readonly syncSecret?: Uint8Array;
|
|
@@ -273,19 +287,13 @@ declare function recoveryCodeToHex(code: Uint8Array): string;
|
|
|
273
287
|
declare function recoveryCodeFromHex(hex: string): Uint8Array;
|
|
274
288
|
declare function recoveryCodeFromUserInput(input: string): Uint8Array;
|
|
275
289
|
|
|
276
|
-
/**
|
|
277
|
-
* `@invisible-labs/sdk/user` - normal-user (private transfer) commands (spec 4.3).
|
|
278
|
-
*
|
|
279
|
-
* The normal-user API is functional and operates on the caller-owned attested
|
|
280
|
-
* Session. Importing this module must not pull in `/lp`, `/stats`, or `/events`.
|
|
281
|
-
*/
|
|
282
|
-
|
|
283
290
|
/** Inclusive minimum private-transfer entry amount in lamports. */
|
|
284
291
|
declare const MIN_ENTRY_AMOUNT_LAMPORTS = 1500000000;
|
|
285
292
|
/** Inclusive maximum private-transfer entry amount in lamports. */
|
|
286
293
|
declare const MAX_ENTRY_AMOUNT_LAMPORTS = 100000000000;
|
|
287
294
|
/** Arguments to start a new private-transfer pool entry. */
|
|
288
295
|
interface ContractRequestArgs {
|
|
296
|
+
readonly onInitializationRetry?: RunSwapParams["onInitializationRetry"];
|
|
289
297
|
/**
|
|
290
298
|
* Gross private-transfer amount in lamports.
|
|
291
299
|
*
|
|
@@ -300,8 +308,12 @@ interface ContractRequestArgs {
|
|
|
300
308
|
/**
|
|
301
309
|
* Where and how the output is delivered. V0 normal-user requests support
|
|
302
310
|
* exactly one payout destination and validate the policy locally before
|
|
303
|
-
* submission. `batchExclusionId`
|
|
304
|
-
*
|
|
311
|
+
* submission. Reuse the same `batchExclusionId` for each contract belonging
|
|
312
|
+
* to one user so liquidity from their own deposits, including deposits that
|
|
313
|
+
* later reimbursed an LP, cannot fund their own payout. The payout waits
|
|
314
|
+
* when no other liquidity is available.
|
|
315
|
+
* This opaque value is not proof of identity; integrators are responsible
|
|
316
|
+
* for assigning and retaining it.
|
|
305
317
|
* `destinations[*].minDelayMs` and `destinations[*].maxDelayMs` are also
|
|
306
318
|
* rejected in V0 because the current runtime does not honor them.
|
|
307
319
|
* `totalDeadlineMs` selects the payout window: use `0` for instant payout,
|
|
@@ -338,6 +350,8 @@ interface ContractRequestArgs {
|
|
|
338
350
|
swapId: string;
|
|
339
351
|
delegateShare: Uint8Array;
|
|
340
352
|
}) => void | Promise<void>;
|
|
353
|
+
/** Cancels only a pending pre-seal admission backoff; it cannot reverse an accepted contract. */
|
|
354
|
+
readonly signal?: AbortSignal;
|
|
341
355
|
}
|
|
342
356
|
/**
|
|
343
357
|
* Start a new pool entry through the current normal-user coordinator flow.
|
package/dist/user.js
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
import { scheduledPayoutWindowSeconds } from './chunk-
|
|
2
|
-
import { validatePayoutPolicyShape, formatAjvErrors, persistTransferStatus, createSession, disabledClientPersistence, readPersistedTransferForResume, persistTransferReady, createExponentialBackoff, persistTransferTerminal, persistTransferRecoveryCode, persistTransferAllocation, persistTransferDkgMetadata } from './chunk-
|
|
3
|
-
export { getPersistedTransfer, listPersistedTransfers, purgePersistedTransfers, removePersistedTransfer } from './chunk-
|
|
4
|
-
import { PRODUCT_MAX_ENTRY_LAMPORTS, PRODUCT_MIN_ENTRY_LAMPORTS } from './chunk-
|
|
5
|
-
import { assertAttested, publicKey, solanaAddressFromPublicKeyBytes } from './chunk-
|
|
6
|
-
import { requestEnvelope, CoordinatorMessageType, onEnvelope, closeProtocolRuntime, EnvelopeKind } from './chunk-
|
|
7
|
-
import { getSessionState } from './chunk-
|
|
8
|
-
import './chunk-
|
|
9
|
-
import { PolicyValidationError, CommandError, StorageError, TransportError, normalizeError, InvalidDepositAmountError, AttestationError, RoutingError } from './chunk-
|
|
10
|
-
export { InvalidDepositAmountError } from './chunk-
|
|
1
|
+
import { scheduledPayoutWindowSeconds, ErrorCode } from './chunk-DFBH5XLM.js';
|
|
2
|
+
import { validatePayoutPolicyShape, formatAjvErrors, persistTransferStatus, createSession, disabledClientPersistence, readPersistedTransferForResume, persistTransferReady, createExponentialBackoff, persistTransferTerminal, persistTransferRecoveryCode, persistTransferAllocation, persistTransferDkgMetadata } from './chunk-ANQMIQYS.js';
|
|
3
|
+
export { getPersistedTransfer, listPersistedTransfers, purgePersistedTransfers, removePersistedTransfer } from './chunk-ANQMIQYS.js';
|
|
4
|
+
import { PRODUCT_MAX_ENTRY_LAMPORTS, PRODUCT_MIN_ENTRY_LAMPORTS } from './chunk-HWRMSK7E.js';
|
|
5
|
+
import { assertAttested, publicKey, solanaAddressFromPublicKeyBytes } from './chunk-EPWTRF5U.js';
|
|
6
|
+
import { requestEnvelope, CoordinatorMessageType, onEnvelope, closeProtocolRuntime, EnvelopeKind } from './chunk-6AGC3IOB.js';
|
|
7
|
+
import { getSessionState } from './chunk-6AKBRYKO.js';
|
|
8
|
+
import './chunk-AIKC2XQS.js';
|
|
9
|
+
import { PolicyValidationError, CommandError, StorageError, TransportError, normalizeError, InvalidDepositAmountError, AttestationError, RoutingError } from './chunk-RWKG7N7I.js';
|
|
10
|
+
export { InvalidDepositAmountError } from './chunk-RWKG7N7I.js';
|
|
11
11
|
import './chunk-VR6T6OJS.js';
|
|
12
12
|
|
|
13
13
|
// src/validation/payoutPolicy.ts
|
|
@@ -27,7 +27,6 @@ Math.max(...SUPPORTED_TOTAL_DEADLINE_MS);
|
|
|
27
27
|
var SHARE_SUM_TOLERANCE = 0.01;
|
|
28
28
|
var CURRENT_USER_PAYOUT_DESTINATION_LIMIT = 1;
|
|
29
29
|
var CURRENT_USER_PAYOUT_DESTINATION_LIMIT_MESSAGE = "current V0 normal-user SDK and coordinator support exactly one payout destination; multi-address receive is not supported yet";
|
|
30
|
-
var CURRENT_USER_BATCH_EXCLUSION_ID_UNSUPPORTED_MESSAGE = "batchExclusionId is not supported in V0 normal-user payout requests; V1 defines it as campaign-scoped batch exclusion, never a stable actor identity";
|
|
31
30
|
var CURRENT_USER_MIN_DELAY_UNSUPPORTED_MESSAGE = "destinations[*].minDelayMs is not supported in V0 normal-user payout requests";
|
|
32
31
|
var CURRENT_USER_MAX_DELAY_UNSUPPORTED_MESSAGE = "destinations[*].maxDelayMs is not supported in V0 normal-user payout requests";
|
|
33
32
|
var CURRENT_USER_PAYOUT_FRAGMENT_LIMIT = 1;
|
|
@@ -91,12 +90,6 @@ function validatePayoutPolicy(input, ctx = {}) {
|
|
|
91
90
|
return policy;
|
|
92
91
|
}
|
|
93
92
|
function assertCurrentUserUnsupportedPayoutFeatures(policy) {
|
|
94
|
-
if (policy.batchExclusionId !== void 0) {
|
|
95
|
-
throw new PolicyValidationError(
|
|
96
|
-
"INVALID_PAYOUT_PLAN",
|
|
97
|
-
CURRENT_USER_BATCH_EXCLUSION_ID_UNSUPPORTED_MESSAGE
|
|
98
|
-
);
|
|
99
|
-
}
|
|
100
93
|
for (const destination of policy.destinations) {
|
|
101
94
|
if (destination.minDelayMs !== void 0) {
|
|
102
95
|
throw new PolicyValidationError(
|
|
@@ -172,11 +165,11 @@ function recoveryCodeFromUserInput(input) {
|
|
|
172
165
|
var protocolPromise = null;
|
|
173
166
|
var frostRuntimePromise = null;
|
|
174
167
|
function loadProtocol() {
|
|
175
|
-
protocolPromise ??= import('./coordinator-
|
|
168
|
+
protocolPromise ??= import('./coordinator-T2B7253V.js');
|
|
176
169
|
return protocolPromise;
|
|
177
170
|
}
|
|
178
171
|
function loadFrostRuntime() {
|
|
179
|
-
frostRuntimePromise ??= import('./frostRuntime-
|
|
172
|
+
frostRuntimePromise ??= import('./frostRuntime-JESDHN6O.js');
|
|
180
173
|
return frostRuntimePromise;
|
|
181
174
|
}
|
|
182
175
|
function loadFrost() {
|
|
@@ -195,6 +188,11 @@ var MAX_EVENT_DEDUP_ENTRIES_PER_KIND = 1024;
|
|
|
195
188
|
var SWAP_STATUS_RETRY_JITTER_RATIO = 0.2;
|
|
196
189
|
var DEFAULT_REFUND_OUTCOME_POLL_BUDGET_MS = 5 * 60 * 1e3;
|
|
197
190
|
var REFUND_OUTCOME_POLL_INTERVAL_MS = 3e3;
|
|
191
|
+
var INITIALIZATION_PUSH_TIMEOUT_MS = 3e4;
|
|
192
|
+
var CONTRACT_ADMISSION_BUSY_MAX_ATTEMPTS = 6;
|
|
193
|
+
var CONTRACT_ADMISSION_BUSY_INITIAL_DELAY_MS = 250;
|
|
194
|
+
var CONTRACT_ADMISSION_BUSY_MAX_DELAY_MS = 4e3;
|
|
195
|
+
var CONTRACT_ADMISSION_BUSY_JITTER_RATIO = 0.2;
|
|
198
196
|
var REFUND_OUTCOME_PER_POLL_TIMEOUT_MS = 5e3;
|
|
199
197
|
var UNBOUND_RECONCILIATION_KEY = "__unbound__";
|
|
200
198
|
var REQUEST_TIMEOUT_MESSAGE = "coordinator request timed out";
|
|
@@ -202,6 +200,9 @@ var REFUND_PENDING_FINALIZATION_MESSAGE = "refund accepted and pending finalizat
|
|
|
202
200
|
var CURRENT_SCHEDULED_PAYOUT_WINDOW_SECONDS = new Set(scheduledPayoutWindowSeconds());
|
|
203
201
|
var CURRENT_SCHEDULED_PAYOUT_WINDOW_MESSAGE = `scheduled payout_spec.window_seconds must be one of [${scheduledPayoutWindowSeconds().join(", ")}]`;
|
|
204
202
|
var TERMINAL_SWAP_STATES = /* @__PURE__ */ new Set(["completed", "refunded", "failed"]);
|
|
203
|
+
function createRequestAbortError() {
|
|
204
|
+
return new DOMException("coordinator request aborted", "AbortError");
|
|
205
|
+
}
|
|
205
206
|
function isBenignTransportDrop(err) {
|
|
206
207
|
return typeof err === "object" && err !== null && err[BENIGN_TRANSPORT_DROP] === true;
|
|
207
208
|
}
|
|
@@ -503,7 +504,8 @@ var UserCoordinatorSession = class {
|
|
|
503
504
|
const dkg = await this.runDkg(
|
|
504
505
|
context,
|
|
505
506
|
params.onDelegateShareReady,
|
|
506
|
-
persistedResumeRecord !== null
|
|
507
|
+
persistedResumeRecord !== null,
|
|
508
|
+
params
|
|
507
509
|
);
|
|
508
510
|
jointPublicKey = dkg.jointPublicKey;
|
|
509
511
|
depositAddress = solanaAddressFromPublicKeyBytes(jointPublicKey);
|
|
@@ -515,14 +517,15 @@ var UserCoordinatorSession = class {
|
|
|
515
517
|
const delegateAckPromise = this.awaitPush(CoordinatorMessageType.DelegateAck, context.swapId);
|
|
516
518
|
let delegateResp;
|
|
517
519
|
try {
|
|
518
|
-
delegateResp = await this.
|
|
520
|
+
delegateResp = await this.requestInitialization(
|
|
519
521
|
CoordinatorMessageType.DelegateShare,
|
|
520
522
|
{
|
|
521
523
|
share: delegateShare,
|
|
522
524
|
recovery_commitment: new Uint8Array(params.recoveryCommitment),
|
|
523
525
|
resume_secret: context.resumeSecret
|
|
524
526
|
},
|
|
525
|
-
|
|
527
|
+
context,
|
|
528
|
+
params
|
|
526
529
|
);
|
|
527
530
|
} catch (err) {
|
|
528
531
|
void delegateAckPromise.catch(() => void 0);
|
|
@@ -972,11 +975,13 @@ var UserCoordinatorSession = class {
|
|
|
972
975
|
if (generatedResumeSecret) {
|
|
973
976
|
await params.onResumeSecretReady?.({ secretHex: resumeSecretHex });
|
|
974
977
|
}
|
|
975
|
-
const swapResp = await this.
|
|
976
|
-
CoordinatorMessageType.ContractRequest,
|
|
978
|
+
const swapResp = await this.requestContract(
|
|
977
979
|
{
|
|
978
980
|
actor: "user",
|
|
979
981
|
amount_lamports: params.amountLamports,
|
|
982
|
+
...params.batchExclusionId !== void 0 && {
|
|
983
|
+
batch_exclusion_id: params.batchExclusionId
|
|
984
|
+
},
|
|
980
985
|
payout_spec: params.payoutSpec,
|
|
981
986
|
sync_commitment: syncCommitment,
|
|
982
987
|
resume_commitment: resumeCommitment,
|
|
@@ -984,7 +989,7 @@ var UserCoordinatorSession = class {
|
|
|
984
989
|
payout_deadline_ms: params.payoutDeadlineMs ?? payoutDeadlineMs
|
|
985
990
|
}
|
|
986
991
|
},
|
|
987
|
-
|
|
992
|
+
params.signal
|
|
988
993
|
);
|
|
989
994
|
const swapPayload = protocol.asSwapRequestResponsePayload(swapResp);
|
|
990
995
|
const swapId = swapPayload.swap_id;
|
|
@@ -1022,7 +1027,12 @@ var UserCoordinatorSession = class {
|
|
|
1022
1027
|
null
|
|
1023
1028
|
);
|
|
1024
1029
|
void depositConfirmedPromise.catch(() => void 0);
|
|
1025
|
-
const { jointPublicKey, keyHandle, depositExpiresAtMs, coordinatorTimestampMs } = await this.runDkg(
|
|
1030
|
+
const { jointPublicKey, keyHandle, depositExpiresAtMs, coordinatorTimestampMs } = await this.runDkg(
|
|
1031
|
+
context,
|
|
1032
|
+
params.delegateShare ? void 0 : params.onDelegateShareReady,
|
|
1033
|
+
true,
|
|
1034
|
+
params
|
|
1035
|
+
);
|
|
1026
1036
|
this.updateContextState(context, "awaiting_deposit");
|
|
1027
1037
|
let recoveryCommitment = params.recoveryCommitment;
|
|
1028
1038
|
let recoveryCodeHex;
|
|
@@ -1045,14 +1055,15 @@ var UserCoordinatorSession = class {
|
|
|
1045
1055
|
const share = params.delegateShare ?? keyHandle.secretShareBytes();
|
|
1046
1056
|
let delegateResp;
|
|
1047
1057
|
try {
|
|
1048
|
-
delegateResp = await this.
|
|
1058
|
+
delegateResp = await this.requestInitialization(
|
|
1049
1059
|
CoordinatorMessageType.DelegateShare,
|
|
1050
1060
|
{
|
|
1051
1061
|
share,
|
|
1052
1062
|
recovery_commitment: recoveryCommitment,
|
|
1053
1063
|
resume_secret: context.resumeSecret
|
|
1054
1064
|
},
|
|
1055
|
-
|
|
1065
|
+
context,
|
|
1066
|
+
params
|
|
1056
1067
|
);
|
|
1057
1068
|
} catch (err) {
|
|
1058
1069
|
void delegateAckPromise.catch(() => void 0);
|
|
@@ -1119,7 +1130,7 @@ var UserCoordinatorSession = class {
|
|
|
1119
1130
|
}
|
|
1120
1131
|
}
|
|
1121
1132
|
}
|
|
1122
|
-
async runDkg(context, onDelegateShareReady, persistDkgMetadata = true) {
|
|
1133
|
+
async runDkg(context, onDelegateShareReady, persistDkgMetadata = true, retryOptions = {}) {
|
|
1123
1134
|
await ensureFrostWasm();
|
|
1124
1135
|
const protocol = this.requireProtocol();
|
|
1125
1136
|
const { dkgRound1 } = await loadFrost();
|
|
@@ -1159,13 +1170,14 @@ var UserCoordinatorSession = class {
|
|
|
1159
1170
|
});
|
|
1160
1171
|
const dkgCompletePromise = this.awaitPush(CoordinatorMessageType.DkgComplete, context.swapId);
|
|
1161
1172
|
void dkgCompletePromise.catch(() => void 0);
|
|
1162
|
-
await this.
|
|
1173
|
+
await this.requestInitialization(
|
|
1163
1174
|
CoordinatorMessageType.DkgRound2,
|
|
1164
1175
|
{
|
|
1165
1176
|
package: aliceRound2Bytes,
|
|
1166
1177
|
resume_secret: context.resumeSecret
|
|
1167
1178
|
},
|
|
1168
|
-
|
|
1179
|
+
context,
|
|
1180
|
+
retryOptions
|
|
1169
1181
|
);
|
|
1170
1182
|
const completeEnvelope = await dkgCompletePromise;
|
|
1171
1183
|
const complete = readDkgComplete(protocol, completeEnvelope);
|
|
@@ -1509,23 +1521,72 @@ var UserCoordinatorSession = class {
|
|
|
1509
1521
|
return requestEnvelope(this.session, type, payload, {
|
|
1510
1522
|
swapId: options.swapId === void 0 ? this.swapId : options.swapId,
|
|
1511
1523
|
timeoutMs: options.timeoutMs,
|
|
1524
|
+
signal: options.signal,
|
|
1512
1525
|
rejectMatchingOutOfBandErrors: options.rejectMatchingOutOfBandErrors,
|
|
1513
1526
|
requireNonNullResponseSwapId: options.requireNonNullResponseSwapId,
|
|
1514
1527
|
onLog: (message, direction) => this.log(message, direction)
|
|
1515
1528
|
});
|
|
1516
1529
|
}
|
|
1530
|
+
async requestInitialization(stage, payload, context, options) {
|
|
1531
|
+
let retrying = false;
|
|
1532
|
+
for (; ; ) {
|
|
1533
|
+
if (retrying && options.signal?.aborted) throw createRequestAbortError();
|
|
1534
|
+
try {
|
|
1535
|
+
return await this.request(stage, payload, { swapId: context.swapId });
|
|
1536
|
+
} catch (error) {
|
|
1537
|
+
if (!(error instanceof CommandError) || error.coordinatorCode !== ErrorCode.ERR_INITIALIZATION_BUSY || error.failedReqId === void 0 || !options.onInitializationRetry)
|
|
1538
|
+
throw error;
|
|
1539
|
+
const pushType = stage === CoordinatorMessageType.DkgRound2 ? CoordinatorMessageType.DkgComplete : CoordinatorMessageType.DelegateAck;
|
|
1540
|
+
const listener = this.pushListeners.get(pushType)?.find((candidate) => candidate.swapId === context.swapId);
|
|
1541
|
+
if (listener) this.setPushTimeout(pushType, listener, null);
|
|
1542
|
+
try {
|
|
1543
|
+
await options.onInitializationRetry({ swapId: context.swapId, stage, error });
|
|
1544
|
+
} finally {
|
|
1545
|
+
if (listener && this.pushListeners.get(pushType)?.includes(listener))
|
|
1546
|
+
this.setPushTimeout(pushType, listener, INITIALIZATION_PUSH_TIMEOUT_MS);
|
|
1547
|
+
}
|
|
1548
|
+
retrying = true;
|
|
1549
|
+
}
|
|
1550
|
+
}
|
|
1551
|
+
}
|
|
1552
|
+
async requestContract(payload, signal) {
|
|
1553
|
+
const busyBackoff = createExponentialBackoff({
|
|
1554
|
+
initialDelayMs: CONTRACT_ADMISSION_BUSY_INITIAL_DELAY_MS,
|
|
1555
|
+
maxDelayMs: CONTRACT_ADMISSION_BUSY_MAX_DELAY_MS,
|
|
1556
|
+
jitterRatio: CONTRACT_ADMISSION_BUSY_JITTER_RATIO
|
|
1557
|
+
});
|
|
1558
|
+
for (let attempt = 1; ; attempt += 1) {
|
|
1559
|
+
if (signal?.aborted) throw createRequestAbortError();
|
|
1560
|
+
try {
|
|
1561
|
+
return await this.request(CoordinatorMessageType.ContractRequest, payload, {
|
|
1562
|
+
swapId: null,
|
|
1563
|
+
requireNonNullResponseSwapId: true
|
|
1564
|
+
});
|
|
1565
|
+
} catch (error) {
|
|
1566
|
+
if (!(error instanceof CommandError) || error.coordinatorCode !== ErrorCode.ERR_PRESEAL_ADMISSION_BUSY || error.failedReqId === void 0 || attempt >= CONTRACT_ADMISSION_BUSY_MAX_ATTEMPTS)
|
|
1567
|
+
throw error;
|
|
1568
|
+
await abortableDelay(busyBackoff.nextDelayMs(), signal);
|
|
1569
|
+
}
|
|
1570
|
+
}
|
|
1571
|
+
}
|
|
1517
1572
|
awaitPush(type, swapId, timeoutMs = 3e4) {
|
|
1518
1573
|
return new Promise((resolve, reject) => {
|
|
1519
|
-
const
|
|
1520
|
-
|
|
1521
|
-
reject(new CommandError("REJECTED_STALE_JOB", `timed out waiting for ${type} push`));
|
|
1522
|
-
}, timeoutMs);
|
|
1523
|
-
const listener = { swapId, resolve, reject, timer };
|
|
1574
|
+
const listener = { swapId, resolve, reject, timer: null };
|
|
1575
|
+
this.setPushTimeout(type, listener, timeoutMs);
|
|
1524
1576
|
const listeners = this.pushListeners.get(type) ?? [];
|
|
1525
1577
|
listeners.push(listener);
|
|
1526
1578
|
this.pushListeners.set(type, listeners);
|
|
1527
1579
|
});
|
|
1528
1580
|
}
|
|
1581
|
+
setPushTimeout(type, listener, timeoutMs) {
|
|
1582
|
+
if (listener.timer) clearTimeout(listener.timer);
|
|
1583
|
+
listener.timer = timeoutMs === null ? null : setTimeout(() => {
|
|
1584
|
+
this.removePushListener(type, listener);
|
|
1585
|
+
listener.reject(
|
|
1586
|
+
new CommandError("REJECTED_STALE_JOB", `timed out waiting for ${type} push`)
|
|
1587
|
+
);
|
|
1588
|
+
}, timeoutMs);
|
|
1589
|
+
}
|
|
1529
1590
|
rejectAllPushListeners(err) {
|
|
1530
1591
|
for (const listeners of this.pushListeners.values()) {
|
|
1531
1592
|
for (const listener of listeners) {
|
|
@@ -1787,6 +1848,21 @@ function bytesToHex(bytes) {
|
|
|
1787
1848
|
function delay(ms) {
|
|
1788
1849
|
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
1789
1850
|
}
|
|
1851
|
+
function abortableDelay(ms, signal) {
|
|
1852
|
+
if (signal === void 0) return delay(ms);
|
|
1853
|
+
if (signal.aborted) return Promise.reject(createRequestAbortError());
|
|
1854
|
+
return new Promise((resolve, reject) => {
|
|
1855
|
+
const onAbort = () => {
|
|
1856
|
+
clearTimeout(timer);
|
|
1857
|
+
reject(createRequestAbortError());
|
|
1858
|
+
};
|
|
1859
|
+
const timer = setTimeout(() => {
|
|
1860
|
+
signal.removeEventListener("abort", onAbort);
|
|
1861
|
+
resolve();
|
|
1862
|
+
}, ms);
|
|
1863
|
+
signal.addEventListener("abort", onAbort, { once: true });
|
|
1864
|
+
});
|
|
1865
|
+
}
|
|
1790
1866
|
function payoutWindowMsFromSpec(payoutSpec) {
|
|
1791
1867
|
if (payoutSpec.mode === "instant") return void 0;
|
|
1792
1868
|
return payoutSpec.window_seconds * 1e3;
|
|
@@ -1829,7 +1905,7 @@ function bytesEqual(a, b) {
|
|
|
1829
1905
|
return diff === 0;
|
|
1830
1906
|
}
|
|
1831
1907
|
function spendingPoliciesEqual(a, b) {
|
|
1832
|
-
return a.asset === b.asset && a.entry_amount_lamports === b.entry_amount_lamports && a.total_committed_lamports === b.total_committed_lamports && a.payout_deadline_ms === b.payout_deadline_ms && a.payout_window_ms === b.payout_window_ms && a.fragment_count === b.fragment_count && a.payout_mode === b.payout_mode && a.matching_mode === b.matching_mode && a.fragmentation_allowed === b.fragmentation_allowed && a.min_fee_bps === b.min_fee_bps && a.fee_bps === b.fee_bps && a.fee_lamports === b.fee_lamports && a.net_payout_lamports === b.net_payout_lamports && payoutSchedulesEqual(a.payout_schedule, b.payout_schedule);
|
|
1908
|
+
return (a.economics ?? "legacy") === (b.economics ?? "legacy") && a.asset === b.asset && a.entry_amount_lamports === b.entry_amount_lamports && a.total_committed_lamports === b.total_committed_lamports && a.payout_deadline_ms === b.payout_deadline_ms && a.payout_window_ms === b.payout_window_ms && a.fragment_count === b.fragment_count && a.payout_mode === b.payout_mode && a.matching_mode === b.matching_mode && a.fragmentation_allowed === b.fragmentation_allowed && a.min_fee_bps === b.min_fee_bps && a.fee_bps === b.fee_bps && a.fee_lamports === b.fee_lamports && a.net_payout_lamports === b.net_payout_lamports && payoutSchedulesEqual(a.payout_schedule, b.payout_schedule);
|
|
1833
1909
|
}
|
|
1834
1910
|
function payoutSchedulesEqual(a, b) {
|
|
1835
1911
|
if (a.length !== b.length) return false;
|
|
@@ -1890,6 +1966,9 @@ async function contractRequest(session, args) {
|
|
|
1890
1966
|
return contractRequestOnSession(session, {
|
|
1891
1967
|
amountLamports: args.amountLamports,
|
|
1892
1968
|
payoutSpec: wirePayoutSpec,
|
|
1969
|
+
...payoutPolicy.batchExclusionId !== void 0 && {
|
|
1970
|
+
batchExclusionId: payoutPolicy.batchExclusionId
|
|
1971
|
+
},
|
|
1893
1972
|
...args.syncSecret !== void 0 && { syncSecret: args.syncSecret },
|
|
1894
1973
|
...args.recoveryCommitment !== void 0 && {
|
|
1895
1974
|
recoveryCommitment: args.recoveryCommitment
|
|
@@ -1909,6 +1988,10 @@ async function contractRequest(session, args) {
|
|
|
1909
1988
|
},
|
|
1910
1989
|
...args.onDelegateShareReady !== void 0 && {
|
|
1911
1990
|
onDelegateShareReady: args.onDelegateShareReady
|
|
1991
|
+
},
|
|
1992
|
+
...args.signal !== void 0 && { signal: args.signal },
|
|
1993
|
+
...args.onInitializationRetry !== void 0 && {
|
|
1994
|
+
onInitializationRetry: args.onInitializationRetry
|
|
1912
1995
|
}
|
|
1913
1996
|
});
|
|
1914
1997
|
}
|
|
@@ -1920,6 +2003,10 @@ async function resumePreDelegation(session, args) {
|
|
|
1920
2003
|
...args.syncSecret !== void 0 && { syncSecret: new Uint8Array(args.syncSecret) },
|
|
1921
2004
|
recoveryCommitment: new Uint8Array(args.recoveryCommitment),
|
|
1922
2005
|
policySnapshot: args.policySnapshot,
|
|
2006
|
+
...args.onInitializationRetry !== void 0 && {
|
|
2007
|
+
onInitializationRetry: args.onInitializationRetry
|
|
2008
|
+
},
|
|
2009
|
+
...args.signal !== void 0 && { signal: args.signal },
|
|
1923
2010
|
...args.onDelegateShareReady !== void 0 && {
|
|
1924
2011
|
onDelegateShareReady: args.onDelegateShareReady
|
|
1925
2012
|
},
|