@conto_finance/sdk 0.6.2-beta.1 → 0.7.1

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 CHANGED
@@ -112,8 +112,8 @@ await conto.checkout.reportOutcome(confirmed.id, { outcome: 'PAID', reference: o
112
112
 
113
113
  ## Stripe Link cards
114
114
 
115
- The Link controls integration kit targets SDK `0.6.2-beta.1`. Install the bundled
116
- tarball when evaluating that candidate; packaging does not publish it to npm.
115
+ The Stripe Link card integration ships in SDK 0.7.0 and later (`npm install @conto_finance/sdk`).
116
+ The Link controls integration kit bundles the same SDK.
117
117
  The [minimal trusted-runtime example](https://github.com/Conto-Finance/conto/tree/main/examples/link-wallet-agent)
118
118
  uses the existing agent SDK key, requires no shopping frontend, and never pays.
119
119
 
@@ -121,7 +121,7 @@ Stripe Link is Stripe's payment wallet, and Conto integrates with it. `conto.che
121
121
  asks Conto first, then asks Stripe Link for a card only after Conto approves the purchase, for
122
122
  exactly the approved amount at that store. Stripe Link issues the card. It runs Stripe's `link-cli`
123
123
  on your machine with your own Link login (`npm i -g @stripe/link-cli`, then `link-cli auth login`).
124
- The person approves each card in the Link app. Conto does not receive the card. It stores only the
124
+ The person approves each card in Link, in the app or on the web. Conto does not receive the card. It stores only the
125
125
  Link request ID.
126
126
 
127
127
  ```typescript
@@ -156,6 +156,11 @@ const confirmed = await conto.checkout.confirm(result.checkpoint, {
156
156
  held spend and throws `LinkCardDeniedError`, `LinkCardExpiredError`, `LinkCardTimeoutError`, or
157
157
  `LinkWalletUnavailableError`. All extend `LinkCardError`. Do not pay.
158
158
  - Retrying with the same input resumes the same checkpoint and Link request.
159
+ - Pass `onLinkApproval` to get Stripe Link's approval page, so a person without the Link app can
160
+ approve on the web while signed in to Link. It is called once, after Conto approves and Link
161
+ creates the request, with `{ checkpoint, linkRequestId, approvalUrl, approvalExpiresAt }`.
162
+ `approvalUrl` is always an HTTPS link.com address. A `LinkCardError` has it too when the SDK
163
+ stopped while the person had not decided.
159
164
  - The card (`number`, `securityValue` for the CVC, `expMonth`, `expYear`, `validUntil`, `last4`,
160
165
  `brand`) stays in this process. Printing or serializing the result shows only the last four
161
166
  digits. It never appears in an error.
@@ -151,4 +151,5 @@ declare function createBrowserbaseSessionManager(config: BrowserbaseSessionConfi
151
151
  */
152
152
  declare function createBrowserbaseGuardedPlaywrightCheckoutRuntimeHost(config: BrowserbaseGuardedPlaywrightCheckoutRuntimeHostConfig): BrowserbaseGuardedPlaywrightCheckoutRuntimeHost;
153
153
 
154
- export { BROWSERBASE_CONNECT_ORIGINS, type BrowserbaseAttachedSession, type BrowserbaseGuardedPlaywrightCheckoutRuntimeHost, type BrowserbaseGuardedPlaywrightCheckoutRuntimeHostConfig, type BrowserbaseOwnedLiveView, type BrowserbaseOwnedSession, type BrowserbaseSessionBinding, type BrowserbaseSessionBindingState, type BrowserbaseSessionBindingStore, type BrowserbaseSessionConfig, BrowserbaseSessionError, type BrowserbaseSessionErrorCode, type BrowserbaseSessionHandoff, type BrowserbaseSessionHandoffAssertionInput, type BrowserbaseSessionLifecycleOwner, type BrowserbaseSessionManager, type BrowserbaseSessionStatus, createBrowserbaseGuardedPlaywrightCheckoutRuntimeHost, createBrowserbaseSessionHandoffAssertion, createBrowserbaseSessionManager };
154
+ export { BROWSERBASE_CONNECT_ORIGINS, BrowserbaseSessionError, createBrowserbaseGuardedPlaywrightCheckoutRuntimeHost, createBrowserbaseSessionHandoffAssertion, createBrowserbaseSessionManager };
155
+ export type { BrowserbaseAttachedSession, BrowserbaseGuardedPlaywrightCheckoutRuntimeHost, BrowserbaseGuardedPlaywrightCheckoutRuntimeHostConfig, BrowserbaseOwnedLiveView, BrowserbaseOwnedSession, BrowserbaseSessionBinding, BrowserbaseSessionBindingState, BrowserbaseSessionBindingStore, BrowserbaseSessionConfig, BrowserbaseSessionErrorCode, BrowserbaseSessionHandoff, BrowserbaseSessionHandoffAssertionInput, BrowserbaseSessionLifecycleOwner, BrowserbaseSessionManager, BrowserbaseSessionStatus };
@@ -151,4 +151,5 @@ declare function createBrowserbaseSessionManager(config: BrowserbaseSessionConfi
151
151
  */
152
152
  declare function createBrowserbaseGuardedPlaywrightCheckoutRuntimeHost(config: BrowserbaseGuardedPlaywrightCheckoutRuntimeHostConfig): BrowserbaseGuardedPlaywrightCheckoutRuntimeHost;
153
153
 
154
- export { BROWSERBASE_CONNECT_ORIGINS, type BrowserbaseAttachedSession, type BrowserbaseGuardedPlaywrightCheckoutRuntimeHost, type BrowserbaseGuardedPlaywrightCheckoutRuntimeHostConfig, type BrowserbaseOwnedLiveView, type BrowserbaseOwnedSession, type BrowserbaseSessionBinding, type BrowserbaseSessionBindingState, type BrowserbaseSessionBindingStore, type BrowserbaseSessionConfig, BrowserbaseSessionError, type BrowserbaseSessionErrorCode, type BrowserbaseSessionHandoff, type BrowserbaseSessionHandoffAssertionInput, type BrowserbaseSessionLifecycleOwner, type BrowserbaseSessionManager, type BrowserbaseSessionStatus, createBrowserbaseGuardedPlaywrightCheckoutRuntimeHost, createBrowserbaseSessionHandoffAssertion, createBrowserbaseSessionManager };
154
+ export { BROWSERBASE_CONNECT_ORIGINS, BrowserbaseSessionError, createBrowserbaseGuardedPlaywrightCheckoutRuntimeHost, createBrowserbaseSessionHandoffAssertion, createBrowserbaseSessionManager };
155
+ export type { BrowserbaseAttachedSession, BrowserbaseGuardedPlaywrightCheckoutRuntimeHost, BrowserbaseGuardedPlaywrightCheckoutRuntimeHostConfig, BrowserbaseOwnedLiveView, BrowserbaseOwnedSession, BrowserbaseSessionBinding, BrowserbaseSessionBindingState, BrowserbaseSessionBindingStore, BrowserbaseSessionConfig, BrowserbaseSessionErrorCode, BrowserbaseSessionHandoff, BrowserbaseSessionHandoffAssertionInput, BrowserbaseSessionLifecycleOwner, BrowserbaseSessionManager, BrowserbaseSessionStatus };
@@ -322,13 +322,16 @@ function createEncryptedPlaywrightCheckoutTargetStore(config) {
322
322
  if (envelope.version !== TARGET_STORE_ENVELOPE_VERSION || typeof envelope.iv !== "string" || typeof envelope.ciphertext !== "string" || typeof envelope.tag !== "string") {
323
323
  throw new Error("invalid envelope");
324
324
  }
325
+ const tag = Buffer.from(envelope.tag, "base64url");
326
+ if (tag.length !== 16) throw new Error("invalid envelope");
325
327
  const decipher = (0, import_node_crypto2.createDecipheriv)(
326
328
  "aes-256-gcm",
327
329
  key,
328
- Buffer.from(envelope.iv, "base64url")
330
+ Buffer.from(envelope.iv, "base64url"),
331
+ { authTagLength: 16 }
329
332
  );
330
333
  decipher.setAAD(Buffer.from(storageKey));
331
- decipher.setAuthTag(Buffer.from(envelope.tag, "base64url"));
334
+ decipher.setAuthTag(tag);
332
335
  const plaintext = Buffer.concat([
333
336
  decipher.update(Buffer.from(envelope.ciphertext, "base64url")),
334
337
  decipher.final()
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  createGuardedPlaywrightCheckoutRuntimeHost
3
- } from "./chunk-VSIO6PYA.mjs";
3
+ } from "./chunk-JBTJXIMI.mjs";
4
4
  import "./chunk-O5RAAB2U.mjs";
5
5
  import "./chunk-TGOYFBKZ.mjs";
6
6
 
@@ -92,4 +92,5 @@ interface VerifyCheckoutIntegrationOptions {
92
92
  */
93
93
  declare function verifyCheckoutIntegration(value: CheckoutCapabilityManifest | unknown, options?: VerifyCheckoutIntegrationOptions): Promise<CheckoutIntegrationVerificationReport>;
94
94
 
95
- export { CHECKOUT_CAPABILITY_KINDS, CHECKOUT_CAPABILITY_MANIFEST_VERSION, CHECKOUT_CONFORMANCE_PROBE_IDS, CHECKOUT_METHOD_IDS, CHECKOUT_VERIFICATION_REPORT_VERSION, type CheckoutCapabilityDescriptor, type CheckoutCapabilityExposure, type CheckoutCapabilityInventoryScope, type CheckoutCapabilityKind, type CheckoutCapabilityManifest, type CheckoutCapabilityPaymentBoundary, type CheckoutConformanceProbeId, type CheckoutConformanceProbeObservation, type CheckoutConformanceProbeOutcome, type CheckoutConformanceProbeRequest, type CheckoutConformanceProbeResult, type CheckoutConformanceProbeRunner, type CheckoutIntegrationComponent, type CheckoutIntegrationStatus, type CheckoutIntegrationVerificationReport, type CheckoutMethodId, type CheckoutSessionBinding, type CheckoutVerificationFinding, type CheckoutVerificationFindingCode, type VerifyCheckoutIntegrationOptions, verifyCheckoutIntegration };
95
+ export { CHECKOUT_CAPABILITY_KINDS, CHECKOUT_CAPABILITY_MANIFEST_VERSION, CHECKOUT_CONFORMANCE_PROBE_IDS, CHECKOUT_METHOD_IDS, CHECKOUT_VERIFICATION_REPORT_VERSION, verifyCheckoutIntegration };
96
+ export type { CheckoutCapabilityDescriptor, CheckoutCapabilityExposure, CheckoutCapabilityInventoryScope, CheckoutCapabilityKind, CheckoutCapabilityManifest, CheckoutCapabilityPaymentBoundary, CheckoutConformanceProbeId, CheckoutConformanceProbeObservation, CheckoutConformanceProbeOutcome, CheckoutConformanceProbeRequest, CheckoutConformanceProbeResult, CheckoutConformanceProbeRunner, CheckoutIntegrationComponent, CheckoutIntegrationStatus, CheckoutIntegrationVerificationReport, CheckoutMethodId, CheckoutSessionBinding, CheckoutVerificationFinding, CheckoutVerificationFindingCode, VerifyCheckoutIntegrationOptions };
@@ -92,4 +92,5 @@ interface VerifyCheckoutIntegrationOptions {
92
92
  */
93
93
  declare function verifyCheckoutIntegration(value: CheckoutCapabilityManifest | unknown, options?: VerifyCheckoutIntegrationOptions): Promise<CheckoutIntegrationVerificationReport>;
94
94
 
95
- export { CHECKOUT_CAPABILITY_KINDS, CHECKOUT_CAPABILITY_MANIFEST_VERSION, CHECKOUT_CONFORMANCE_PROBE_IDS, CHECKOUT_METHOD_IDS, CHECKOUT_VERIFICATION_REPORT_VERSION, type CheckoutCapabilityDescriptor, type CheckoutCapabilityExposure, type CheckoutCapabilityInventoryScope, type CheckoutCapabilityKind, type CheckoutCapabilityManifest, type CheckoutCapabilityPaymentBoundary, type CheckoutConformanceProbeId, type CheckoutConformanceProbeObservation, type CheckoutConformanceProbeOutcome, type CheckoutConformanceProbeRequest, type CheckoutConformanceProbeResult, type CheckoutConformanceProbeRunner, type CheckoutIntegrationComponent, type CheckoutIntegrationStatus, type CheckoutIntegrationVerificationReport, type CheckoutMethodId, type CheckoutSessionBinding, type CheckoutVerificationFinding, type CheckoutVerificationFindingCode, type VerifyCheckoutIntegrationOptions, verifyCheckoutIntegration };
95
+ export { CHECKOUT_CAPABILITY_KINDS, CHECKOUT_CAPABILITY_MANIFEST_VERSION, CHECKOUT_CONFORMANCE_PROBE_IDS, CHECKOUT_METHOD_IDS, CHECKOUT_VERIFICATION_REPORT_VERSION, verifyCheckoutIntegration };
96
+ export type { CheckoutCapabilityDescriptor, CheckoutCapabilityExposure, CheckoutCapabilityInventoryScope, CheckoutCapabilityKind, CheckoutCapabilityManifest, CheckoutCapabilityPaymentBoundary, CheckoutConformanceProbeId, CheckoutConformanceProbeObservation, CheckoutConformanceProbeOutcome, CheckoutConformanceProbeRequest, CheckoutConformanceProbeResult, CheckoutConformanceProbeRunner, CheckoutIntegrationComponent, CheckoutIntegrationStatus, CheckoutIntegrationVerificationReport, CheckoutMethodId, CheckoutSessionBinding, CheckoutVerificationFinding, CheckoutVerificationFindingCode, VerifyCheckoutIntegrationOptions };
@@ -184,13 +184,16 @@ function createEncryptedPlaywrightCheckoutTargetStore(config) {
184
184
  if (envelope.version !== TARGET_STORE_ENVELOPE_VERSION || typeof envelope.iv !== "string" || typeof envelope.ciphertext !== "string" || typeof envelope.tag !== "string") {
185
185
  throw new Error("invalid envelope");
186
186
  }
187
+ const tag = Buffer.from(envelope.tag, "base64url");
188
+ if (tag.length !== 16) throw new Error("invalid envelope");
187
189
  const decipher = createDecipheriv(
188
190
  "aes-256-gcm",
189
191
  key,
190
- Buffer.from(envelope.iv, "base64url")
192
+ Buffer.from(envelope.iv, "base64url"),
193
+ { authTagLength: 16 }
191
194
  );
192
195
  decipher.setAAD(Buffer.from(storageKey));
193
- decipher.setAuthTag(Buffer.from(envelope.tag, "base64url"));
196
+ decipher.setAuthTag(tag);
194
197
  const plaintext = Buffer.concat([
195
198
  decipher.update(Buffer.from(envelope.ciphertext, "base64url")),
196
199
  decipher.final()
@@ -0,0 +1,30 @@
1
+ // src/link-approval.ts
2
+ function safeLinkApprovalUrl(value) {
3
+ if (typeof value !== "string" || value.length === 0 || value.length > 2048) return void 0;
4
+ let url;
5
+ try {
6
+ url = new URL(value);
7
+ } catch {
8
+ return void 0;
9
+ }
10
+ if (url.protocol !== "https:" || url.username !== "" || url.password !== "" || url.port !== "" || !(url.hostname === "link.com" || url.hostname.endsWith(".link.com"))) {
11
+ return void 0;
12
+ }
13
+ url.hash = "";
14
+ return url.toString();
15
+ }
16
+ function linkTime(value) {
17
+ let ms = Number.NaN;
18
+ if (typeof value === "number" && Number.isFinite(value) && value > 0) {
19
+ ms = value < 1e12 ? value * 1e3 : value;
20
+ } else if (typeof value === "string" && value.length > 0 && value.length <= 64) {
21
+ ms = Date.parse(value);
22
+ }
23
+ const date = new Date(ms);
24
+ return Number.isNaN(date.getTime()) ? void 0 : date.toISOString();
25
+ }
26
+
27
+ export {
28
+ safeLinkApprovalUrl,
29
+ linkTime
30
+ };
package/dist/index.d.mts CHANGED
@@ -40,6 +40,48 @@ interface PurchaseGroceryItem {
40
40
  interface PurchaseGroceryList {
41
41
  items: PurchaseGroceryItem[];
42
42
  }
43
+ /** A grocery list purchase's items, delivery and fees at the store. */
44
+ interface PurchaseGrocery {
45
+ /** Each list item that has settled so far, by its position in the list. */
46
+ items: ({
47
+ index: number;
48
+ label: string;
49
+ status: 'added';
50
+ /** The store's product name. */
51
+ name: string;
52
+ quantity: number;
53
+ /** The line's price for that quantity. */
54
+ price: PurchaseMoney;
55
+ } | {
56
+ index: number;
57
+ label: string;
58
+ status: 'skipped';
59
+ reason: 'no_match' | 'size_unavailable' | 'brand_unavailable' | 'excluded';
60
+ })[];
61
+ /** The delivery time chosen at checkout. */
62
+ delivery: {
63
+ title: string;
64
+ window: string;
65
+ kind: 'priority' | 'standard' | 'scheduled' | 'other';
66
+ windowStart: string | null;
67
+ windowEnd: string | null;
68
+ price: PurchaseMoney | null;
69
+ } | null;
70
+ /** The store checkout's totals and fees, as it showed them. */
71
+ summary: {
72
+ itemsSubtotal: PurchaseMoney | null;
73
+ deliveryFee: PurchaseMoney | null;
74
+ serviceFee: PurchaseMoney | null;
75
+ bagFee: PurchaseMoney | null;
76
+ tax: PurchaseMoney | null;
77
+ tip: PurchaseMoney | null;
78
+ otherFees: {
79
+ label: string;
80
+ amount: PurchaseMoney;
81
+ }[];
82
+ total: PurchaseMoney | null;
83
+ } | null;
84
+ }
43
85
  interface PurchaseRequest {
44
86
  url: string;
45
87
  task?: string;
@@ -66,6 +108,15 @@ interface PurchaseAction {
66
108
  maximum: PurchaseMoney;
67
109
  maxCost: PurchaseMoney;
68
110
  };
111
+ /**
112
+ * For a merchant_signin you answer: the store sign-in step. Answer `email`
113
+ * with `{ email }` (or `{ email, createAccount: true, agreedToStoreTerms: true }`)
114
+ * and `code` with `{ code }`, the 6-digit code the store sent the buyer.
115
+ */
116
+ signin?: {
117
+ store: 'instacart';
118
+ step: 'email' | 'code';
119
+ };
69
120
  /**
70
121
  * For buyer, cardholder and reviewer actions: the Conto page that completes
71
122
  * it. It works only inside a hosted buyer session or the dashboard, so it is
@@ -119,7 +170,15 @@ interface Purchase {
119
170
  result: {
120
171
  outcome: 'merchant_confirmed' | 'checkout_reported' | 'credential_unused' | 'not_completed' | 'denied' | 'cancelled';
121
172
  merchantReference: string | null;
173
+ /** merchant_confirmed: the store's order number, when shown. */
174
+ orderNumber?: string | null;
175
+ /** merchant_confirmed: the store's receipt or order page, when shown. */
176
+ receiptUrl?: string | null;
177
+ /** merchant_confirmed: the amount the store charged, when shown. */
178
+ charged?: PurchaseMoney | null;
122
179
  } | null;
180
+ /** Present for a grocery list purchase. */
181
+ grocery?: PurchaseGrocery;
123
182
  paymentEvidence: PurchaseEvidence;
124
183
  progress: {
125
184
  steps: number;
@@ -190,8 +249,8 @@ interface CreatePurchaseInput {
190
249
  delegationId: string;
191
250
  };
192
251
  /**
193
- * The buyer's saved delivery details answer the store's delivery form when
194
- * the buyer has them. Leave out to use them when present, pass the buyer id
252
+ * New purchases snapshot saved delivery details at creation for the store's
253
+ * delivery form. Leave out to use them when present, pass the buyer id
195
254
  * to require them, or null to never use them.
196
255
  */
197
256
  buyerProfileId?: string | null;
@@ -1294,6 +1353,29 @@ interface RefreshBalanceResult {
1294
1353
  balances: WalletChainBalanceSnapshot[];
1295
1354
  lastRefreshed: string;
1296
1355
  }
1356
+ /** A one-time message for a self-custody wallet's address to sign. */
1357
+ interface WalletOwnershipChallenge {
1358
+ walletId: string;
1359
+ address: string;
1360
+ chainType: ChainType;
1361
+ chainId: string;
1362
+ /** Sign exactly this text: EIP-191 personal_sign on EVM, Ed25519 on Solana. */
1363
+ message: string;
1364
+ expiresAt: string;
1365
+ /** When the wallet was last proven, or null if never. */
1366
+ provenAt: string | null;
1367
+ }
1368
+ interface ProveWalletOwnershipInput {
1369
+ /** The challenge message, unchanged. */
1370
+ message: string;
1371
+ /** EVM: 0x-prefixed hex signature. Solana: base58 or base64 signature. */
1372
+ signature: string;
1373
+ }
1374
+ interface WalletOwnershipProof {
1375
+ walletId: string;
1376
+ proven: true;
1377
+ provenAt: string;
1378
+ }
1297
1379
  interface PolicyRule {
1298
1380
  id: string;
1299
1381
  policyId: string;
@@ -1583,6 +1665,13 @@ declare class WalletsClient {
1583
1665
  provision(walletId: string): Promise<ProvisionWalletResult>;
1584
1666
  /** Refresh a wallet's balance from the chain */
1585
1667
  refreshBalance(walletId: string): Promise<RefreshBalanceResult>;
1668
+ /**
1669
+ * Get a one-time message for a self-custody wallet's address to sign. It
1670
+ * expires after 10 minutes and replaces any earlier challenge.
1671
+ */
1672
+ createOwnershipChallenge(walletId: string): Promise<WalletOwnershipChallenge>;
1673
+ /** Prove your organization controls a self-custody wallet's address. */
1674
+ proveOwnership(walletId: string, input: ProveWalletOwnershipInput): Promise<WalletOwnershipProof>;
1586
1675
  }
1587
1676
  declare class PoliciesClient {
1588
1677
  private client;
@@ -2554,6 +2643,33 @@ interface WaitForCheckoutApprovalOptions {
2554
2643
  signal?: AbortSignal;
2555
2644
  }
2556
2645
 
2646
+ /**
2647
+ * The Link card request is waiting for the person. Conto has already approved
2648
+ * the purchase, and Link has created the request.
2649
+ */
2650
+ interface LinkApprovalEvent {
2651
+ /** The checkpoint Conto approved. */
2652
+ checkpoint: CheckoutCheckpoint;
2653
+ /** The Link spend request id, such as lsrq_... */
2654
+ linkRequestId: string;
2655
+ /**
2656
+ * The Stripe Link page where the person can approve on the web while signed
2657
+ * in to Link, so they do not need the Link app. Only an HTTPS link.com address
2658
+ * is passed. Absent when Link gave none or it did not pass that check. The
2659
+ * person can still approve in the Link app.
2660
+ */
2661
+ approvalUrl?: string;
2662
+ /** When Link stops accepting approval, as an ISO 8601 time, when Link reports it. */
2663
+ approvalExpiresAt?: string;
2664
+ }
2665
+ /**
2666
+ * Called once when the Link card request is waiting for the person, after
2667
+ * Conto approved the purchase and before the SDK starts waiting. Show
2668
+ * approvalUrl to the person. The SDK does not wait for it to finish, and an
2669
+ * error it throws or rejects with does not affect the purchase. A retry that
2670
+ * resumes a waiting request calls it again with the same URL.
2671
+ */
2672
+ type LinkApprovalCallback = (event: LinkApprovalEvent) => void | Promise<void>;
2557
2673
  /**
2558
2674
  * A Link card for one purchase: the checkpoint begin input plus the Link
2559
2675
  * wallet that runs in your environment. The checkout method is always LINK.
@@ -2565,6 +2681,8 @@ interface GetLinkCardInput extends Omit<BeginCheckoutCheckpointInput, 'checkoutM
2565
2681
  ownerApprovalTimeoutMs?: number;
2566
2682
  /** How long to wait for the person to approve in Link. Defaults to 10 minutes. */
2567
2683
  linkApprovalTimeoutMs?: number;
2684
+ /** Called once with the Link approval page when the person needs to approve in Link. */
2685
+ onLinkApproval?: LinkApprovalCallback;
2568
2686
  signal?: AbortSignal;
2569
2687
  }
2570
2688
  /** A new Link card for a changed final total. */
@@ -2578,6 +2696,8 @@ interface ReplaceLinkCardInput {
2578
2696
  totals?: CommerceTotalInput[];
2579
2697
  ownerApprovalTimeoutMs?: number;
2580
2698
  linkApprovalTimeoutMs?: number;
2699
+ /** Called once with the Link approval page when the person needs to approve in Link. */
2700
+ onLinkApproval?: LinkApprovalCallback;
2581
2701
  signal?: AbortSignal;
2582
2702
  }
2583
2703
  interface LinkCardResult {
@@ -3291,6 +3411,13 @@ declare class CheckoutApprovalTimeoutError extends ContoError {
3291
3411
  declare class LinkCardError extends ContoError {
3292
3412
  readonly checkpoint: CheckoutCheckpoint;
3293
3413
  readonly linkRequestId?: string;
3414
+ /**
3415
+ * The Stripe Link page where the person could approve the request, set when
3416
+ * the SDK stopped while the request was waiting for them. It works only while
3417
+ * the request is still open in Link. When holdReleased is true, Conto has
3418
+ * already cancelled the request.
3419
+ */
3420
+ readonly approvalUrl?: string;
3294
3421
  /** True when Conto cancelled the checkpoint and released the held spend. */
3295
3422
  readonly holdReleased: boolean;
3296
3423
  constructor(input: {
@@ -3298,6 +3425,7 @@ declare class LinkCardError extends ContoError {
3298
3425
  code: string;
3299
3426
  checkpoint: CheckoutCheckpoint;
3300
3427
  linkRequestId?: string;
3428
+ approvalUrl?: string;
3301
3429
  holdReleased: boolean;
3302
3430
  retryGuidance?: string;
3303
3431
  });
@@ -3765,7 +3893,9 @@ declare class CheckoutClient {
3765
3893
  * 1. Conto runs checkpoint 1 and holds the spend. When a rule requires the
3766
3894
  * owner's approval, this waits for it.
3767
3895
  * 2. Only then does the wallet ask Link for a card for exactly the approved
3768
- * amount at this merchant. The person approves it in their Link app.
3896
+ * amount at this merchant. The person approves it in Link. Pass
3897
+ * onLinkApproval to get Link's approval page, so they can approve on the
3898
+ * web without the Link app.
3769
3899
  * 3. The card is returned. It never reaches Conto.
3770
3900
  *
3771
3901
  * Then fill in the card, call confirm(result.checkpoint, { amountMinor,
@@ -3790,4 +3920,5 @@ declare class CheckoutClient {
3790
3920
  replaceLinkCard(previous: LinkCardResult, input: ReplaceLinkCardInput): Promise<LinkCardResult>;
3791
3921
  }
3792
3922
 
3793
- export { type AdminExternalCardOverlayEnforcement, AdminPurchasingClient, type Agent, type AgentCheckoutAction, type AgentCheckoutActionKind, type AgentExternalCard, type AgentSetupResult, type AgentStatus, type AgentType, type AgentWalletLink, type ApprovedExternalCardExecution, type AssignExternalCardInput, type AssignedPolicy, type AuthorizeCheckoutActionResult, type BeginCheckoutCheckpointInput, type BeginCommerceExecutionInput, type BrowserActionClaimResult, type BrowserActionDispatchObservationInput, BrowserActionFinalizationPendingError, type BrowserActionFinalizeResult, type BrowserCheckoutAction, type BrowserCheckoutTargetResolver, type BrowserCheckoutTargetSnapshot, type BrowserCheckoutTargetVerificationCode, BrowserCheckoutTargetVerificationError, type CancellationOutcome, type CanonicalBrowserCheckoutTargetSnapshot, CardsClient, type ChainType, type CheckoutActionAuthorization, CheckoutApprovalDeniedError, CheckoutApprovalExpiredError, CheckoutApprovalPendingError, CheckoutApprovalTimeoutError, type CheckoutCheckpoint, type CheckoutCheckpointApproval, CheckoutCheckpointClosedError, type CheckoutCheckpointMethod, type CheckoutCheckpointNextAction, type CheckoutCheckpointStage, CheckoutClient, type CheckoutOutcome, type CheckoutPaymentReference, type CommerceCheckoutMethod, type CommerceContextRequirement, type CommerceExecution, type CommerceExecutionAdapterKind, type CommerceExecutionArtifactKind, type CommerceExecutionChannel, type CommerceExecutionConstraint, type CommerceExecutionConstraintCoverage, type CommerceExecutionConstraintCoverageLevel, type CommerceExecutionDeliveryMode, type CommerceExecutionEvidence, type CommerceExecutionProvider, type CommerceExecutionResult, type CommerceExecutionSourceKind, type CommerceExecutionStatus, type CommerceFactConfidence, type CommerceFactProvenanceInput, type CommerceFactSource, type CommerceFulfillmentInput, type CommerceLineItemInput, type CommerceProposalFactKey, type CommerceProposalMissingFact, type CommerceProposalResolution, type CommerceProposalState, type CommerceSettlementRail, type CommerceTotalInput, type CommerceTotalType, type ComparePolicyVersionsResponse, type ConfirmCheckoutCheckpointInput, type ConnectedCardBrief, type ConnectedCardCredential, type ConnectedCardDrawInput, type ConnectedCardDrawMerchant, type ConnectedCardDrawResult, type ConnectedCardDrawable, type ConnectedCardListResult, type ConnectedCardMandate, type ConnectedCardMandateMerchant, type ConnectedCardOutcomeReport, type ConnectedCardOutcomeReportResult, type ConnectedCardReference, ConnectedCardsClient, Conto, ContoAdmin, type ContoAdminConfig, ContoAdminError, type ContoConfig, ContoError, type ContoRequestOptions, type ControlledExternalCardPaymentResult, ControlledExternalCardPaymentTool, type CreateAgentInput, type CreatePolicyInput, type CreatePolicyRuleInput, type CreatePurchaseInput, type CreateSdkKeyInput, type CreateSdkKeyResult, type CreateWalletInput, type CustodyType, type CustomerCustodyMode, type CustomerWalletControlModel, type CustomerWalletKeyAccess, type DelegationType, type ExecuteCommerceExecutionResult, type ExternalCard, type ExternalCardApprovalInput, type ExternalCardApprovalResult, type ExternalCardConfirmationInput, ExternalCardConfirmationPendingError, type ExternalCardConfirmationResult, type ExternalCardExecutionClaimResult, type ExternalCardExecutionResult, type ExternalCardExecutor, type ExternalCardOverlayEnforcement, type ExternalCardRequestStatusResult, type ExternalWalletApprovalInput, type ExternalWalletApprovalResult, type ExternalWalletConfirmationInput, type ExternalWalletConfirmationResult, type FreezeAgentInput, type GetLinkCardInput, Conto as Giro, type ContoConfig as GiroConfig, ContoError as GiroError, type GuardCheckoutResult, type GuardedBrowserDispatchResult, type GuardedCheckoutInput, LinkCardCredential, LinkCardDeniedError, LinkCardError, LinkCardExpiredError, type LinkCardResult, LinkCardTimeoutError, LinkWallet, type LinkWalletInput, LinkWalletUnavailableError, type ListAgentsParams, type ListAgentsResponse, type ListPoliciesParams, type ListPoliciesResponse, type ListPolicyVersionsResponse, type ListWalletsParams, type ListWalletsResponse, type MppBudgetResult, type MppPreAuthorizeInput, type MppPreAuthorizeResult, type MppRecordInput, type MppRecordResult, type NormalizeCommerceProposalInput, type OrganizationMember, OrganizationPurchasesClient, OrganizationRecurringPurchasesClient, type PaginatedResponse, type PaginationParams, type PauseExternalCardAssignmentResult, type PaymentExecuteResult, type PaymentRequestInput, type PaymentRequestResult, type PaymentStatusResult, type Policy, type PolicyRule, type PolicyType, type PolicyVersionChangeType, type PolicyVersionDetail, type PolicyVersionDiff, type PolicyVersionFieldChange, type PolicyVersionSnapshot, type PolicyVersionSnapshotRule, type PolicyVersionSummary, type PrivilegedBrowserCheckoutDriver, type ProtocolBudgetResult, type ProtocolPreAuthorizeResult, type ProtocolRecordGrant, type ProtocolRecordGrantResult, type ProtocolServiceSummary, type ProtocolServicesResult, type ProvisionWalletResult, type Purchase, type PurchaseAction, type PurchaseActionAuthority, type PurchaseActionKind, type PurchaseAllowance, type PurchaseBuyer, type PurchaseBuyerCompanyCard, type PurchaseBuyerCompanyCardLimits, type PurchaseBuyerKitchenContext, type PurchaseCompanyCard, type PurchaseDelegation, type PurchaseEvent, type PurchaseEventPage, type PurchaseEvidence, type PurchaseGroceryItem, type PurchaseGroceryList, type PurchaseHostedLink, type PurchaseItem, type PurchaseKitchenContext, type PurchaseKitchenInventoryItem, type PurchaseKitchenListItem, type PurchaseKitchenPreferences, type PurchaseKitchenRecipe, type PurchaseKitchenUsual, type PurchaseList, type PurchaseMoney, type PurchasePaymentMethod, type PurchasePhase, type PurchaseRequest, type PurchaseResponseAck, type PurchaseStatus, PurchasesClient, type PurchasingCapabilities, type PurchasingSettings, type RecurringPurchase, type RecurringPurchaseCycleResult, type RecurringPurchaseCycleStatus, RecurringPurchasesClient, type RefreshBalanceResult, type RegisterExternalCardInput, type ReplaceLinkCardInput, type ReportCheckoutOutcomeInput, type RollbackPolicyVersionResponse, type RuleAction, type RuleOperator, type RuleType, type RunGuardedCheckoutResult, type SdkKey, type SdkKeyType, type SetupCapabilityState, type SetupCardDiagnostics, type SetupDiagnosticAction, type SetupDiagnosticIssue, type SetupDiagnosticIssueCode, type SetupDiagnostics, type SetupWalletDiagnostics, type TestCardCredential, type TestCardDrawResult, type TestCardDrawable, type TestCardListResult, type TestCardReceipt, TestCardsClient, type TestCheckoutInput, type TestCheckoutResult, type TestMerchant, type TestMerchantProduct, type UnfreezeAgentInput, type UpdateAgentInput, type UpdateExternalCardAssignmentInput, type UpdatePolicyInput, type UpdatePolicyRuleInput, type UpdateWalletInput, type VerifiedBrowserCheckoutTarget, type WaitForCheckoutApprovalOptions, type Wallet, type WalletChainBalanceSnapshot, type WalletStatus, type WalletType, type WatchPurchaseOptions, type X402Authorization, type X402BudgetResult, type X402PayInput, type X402PayResult, type X402PaymentRequirements, type X402PreAuthorizeInput, type X402PreAuthorizeResult, type X402RecordInput, type X402RecordResult, canonicalizeBrowserCheckoutTarget, createVerifiedBrowserCheckoutDriver, Conto as default, fingerprintBrowserCheckoutTarget, isFinalPurchaseStatus, parseServerSentEvents, verifyPurchaseWebhook };
3923
+ export { AdminPurchasingClient, BrowserActionFinalizationPendingError, BrowserCheckoutTargetVerificationError, CardsClient, CheckoutApprovalDeniedError, CheckoutApprovalExpiredError, CheckoutApprovalPendingError, CheckoutApprovalTimeoutError, CheckoutCheckpointClosedError, CheckoutClient, ConnectedCardsClient, Conto, ContoAdmin, ContoAdminError, ContoError, ControlledExternalCardPaymentTool, ExternalCardConfirmationPendingError, Conto as Giro, ContoError as GiroError, LinkCardCredential, LinkCardDeniedError, LinkCardError, LinkCardExpiredError, LinkCardTimeoutError, LinkWallet, LinkWalletUnavailableError, OrganizationPurchasesClient, OrganizationRecurringPurchasesClient, PurchasesClient, RecurringPurchasesClient, TestCardsClient, canonicalizeBrowserCheckoutTarget, createVerifiedBrowserCheckoutDriver, Conto as default, fingerprintBrowserCheckoutTarget, isFinalPurchaseStatus, parseServerSentEvents, verifyPurchaseWebhook };
3924
+ export type { AdminExternalCardOverlayEnforcement, Agent, AgentCheckoutAction, AgentCheckoutActionKind, AgentExternalCard, AgentSetupResult, AgentStatus, AgentType, AgentWalletLink, ApprovedExternalCardExecution, AssignExternalCardInput, AssignedPolicy, AuthorizeCheckoutActionResult, BeginCheckoutCheckpointInput, BeginCommerceExecutionInput, BrowserActionClaimResult, BrowserActionDispatchObservationInput, BrowserActionFinalizeResult, BrowserCheckoutAction, BrowserCheckoutTargetResolver, BrowserCheckoutTargetSnapshot, BrowserCheckoutTargetVerificationCode, CancellationOutcome, CanonicalBrowserCheckoutTargetSnapshot, ChainType, CheckoutActionAuthorization, CheckoutCheckpoint, CheckoutCheckpointApproval, CheckoutCheckpointMethod, CheckoutCheckpointNextAction, CheckoutCheckpointStage, CheckoutOutcome, CheckoutPaymentReference, CommerceCheckoutMethod, CommerceContextRequirement, CommerceExecution, CommerceExecutionAdapterKind, CommerceExecutionArtifactKind, CommerceExecutionChannel, CommerceExecutionConstraint, CommerceExecutionConstraintCoverage, CommerceExecutionConstraintCoverageLevel, CommerceExecutionDeliveryMode, CommerceExecutionEvidence, CommerceExecutionProvider, CommerceExecutionResult, CommerceExecutionSourceKind, CommerceExecutionStatus, CommerceFactConfidence, CommerceFactProvenanceInput, CommerceFactSource, CommerceFulfillmentInput, CommerceLineItemInput, CommerceProposalFactKey, CommerceProposalMissingFact, CommerceProposalResolution, CommerceProposalState, CommerceSettlementRail, CommerceTotalInput, CommerceTotalType, ComparePolicyVersionsResponse, ConfirmCheckoutCheckpointInput, ConnectedCardBrief, ConnectedCardCredential, ConnectedCardDrawInput, ConnectedCardDrawMerchant, ConnectedCardDrawResult, ConnectedCardDrawable, ConnectedCardListResult, ConnectedCardMandate, ConnectedCardMandateMerchant, ConnectedCardOutcomeReport, ConnectedCardOutcomeReportResult, ConnectedCardReference, ContoAdminConfig, ContoConfig, ContoRequestOptions, ControlledExternalCardPaymentResult, CreateAgentInput, CreatePolicyInput, CreatePolicyRuleInput, CreatePurchaseInput, CreateSdkKeyInput, CreateSdkKeyResult, CreateWalletInput, CustodyType, CustomerCustodyMode, CustomerWalletControlModel, CustomerWalletKeyAccess, DelegationType, ExecuteCommerceExecutionResult, ExternalCard, ExternalCardApprovalInput, ExternalCardApprovalResult, ExternalCardConfirmationInput, ExternalCardConfirmationResult, ExternalCardExecutionClaimResult, ExternalCardExecutionResult, ExternalCardExecutor, ExternalCardOverlayEnforcement, ExternalCardRequestStatusResult, ExternalWalletApprovalInput, ExternalWalletApprovalResult, ExternalWalletConfirmationInput, ExternalWalletConfirmationResult, FreezeAgentInput, GetLinkCardInput, ContoConfig as GiroConfig, GuardCheckoutResult, GuardedBrowserDispatchResult, GuardedCheckoutInput, LinkApprovalCallback, LinkApprovalEvent, LinkCardResult, LinkWalletInput, ListAgentsParams, ListAgentsResponse, ListPoliciesParams, ListPoliciesResponse, ListPolicyVersionsResponse, ListWalletsParams, ListWalletsResponse, MppBudgetResult, MppPreAuthorizeInput, MppPreAuthorizeResult, MppRecordInput, MppRecordResult, NormalizeCommerceProposalInput, OrganizationMember, PaginatedResponse, PaginationParams, PauseExternalCardAssignmentResult, PaymentExecuteResult, PaymentRequestInput, PaymentRequestResult, PaymentStatusResult, Policy, PolicyRule, PolicyType, PolicyVersionChangeType, PolicyVersionDetail, PolicyVersionDiff, PolicyVersionFieldChange, PolicyVersionSnapshot, PolicyVersionSnapshotRule, PolicyVersionSummary, PrivilegedBrowserCheckoutDriver, ProtocolBudgetResult, ProtocolPreAuthorizeResult, ProtocolRecordGrant, ProtocolRecordGrantResult, ProtocolServiceSummary, ProtocolServicesResult, ProveWalletOwnershipInput, ProvisionWalletResult, Purchase, PurchaseAction, PurchaseActionAuthority, PurchaseActionKind, PurchaseAllowance, PurchaseBuyer, PurchaseBuyerCompanyCard, PurchaseBuyerCompanyCardLimits, PurchaseBuyerKitchenContext, PurchaseCompanyCard, PurchaseDelegation, PurchaseEvent, PurchaseEventPage, PurchaseEvidence, PurchaseGrocery, PurchaseGroceryItem, PurchaseGroceryList, PurchaseHostedLink, PurchaseItem, PurchaseKitchenContext, PurchaseKitchenInventoryItem, PurchaseKitchenListItem, PurchaseKitchenPreferences, PurchaseKitchenRecipe, PurchaseKitchenUsual, PurchaseList, PurchaseMoney, PurchasePaymentMethod, PurchasePhase, PurchaseRequest, PurchaseResponseAck, PurchaseStatus, PurchasingCapabilities, PurchasingSettings, RecurringPurchase, RecurringPurchaseCycleResult, RecurringPurchaseCycleStatus, RefreshBalanceResult, RegisterExternalCardInput, ReplaceLinkCardInput, ReportCheckoutOutcomeInput, RollbackPolicyVersionResponse, RuleAction, RuleOperator, RuleType, RunGuardedCheckoutResult, SdkKey, SdkKeyType, SetupCapabilityState, SetupCardDiagnostics, SetupDiagnosticAction, SetupDiagnosticIssue, SetupDiagnosticIssueCode, SetupDiagnostics, SetupWalletDiagnostics, TestCardCredential, TestCardDrawResult, TestCardDrawable, TestCardListResult, TestCardReceipt, TestCheckoutInput, TestCheckoutResult, TestMerchant, TestMerchantProduct, UnfreezeAgentInput, UpdateAgentInput, UpdateExternalCardAssignmentInput, UpdatePolicyInput, UpdatePolicyRuleInput, UpdateWalletInput, VerifiedBrowserCheckoutTarget, WaitForCheckoutApprovalOptions, Wallet, WalletChainBalanceSnapshot, WalletOwnershipChallenge, WalletOwnershipProof, WalletStatus, WalletType, WatchPurchaseOptions, X402Authorization, X402BudgetResult, X402PayInput, X402PayResult, X402PaymentRequirements, X402PreAuthorizeInput, X402PreAuthorizeResult, X402RecordInput, X402RecordResult };