@delopay/sdk 0.1.6 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -47,11 +47,19 @@ var DelopayError = class extends Error {
47
47
  this.status = options.status;
48
48
  this.code = options.code;
49
49
  this.type = options.type;
50
+ if (options.requestId !== void 0) this.requestId = options.requestId;
51
+ if (options.rawBody !== void 0) this.rawBody = options.rawBody;
50
52
  }
51
53
  };
52
54
  var DelopayAuthenticationError = class extends DelopayError {
53
- constructor(message = "Invalid API key") {
54
- super(message, { status: 401, code: "AUTH_01", type: "authentication_error" });
55
+ constructor(message = "Invalid API key", options) {
56
+ super(message, {
57
+ status: 401,
58
+ code: "AUTH_01",
59
+ type: "authentication_error",
60
+ requestId: options?.requestId,
61
+ rawBody: options?.rawBody
62
+ });
55
63
  Object.setPrototypeOf(this, new.target.prototype);
56
64
  this.name = "DelopayAuthenticationError";
57
65
  }
@@ -72,13 +80,13 @@ var Admin = class {
72
80
  return this.request("POST", "/admin/tenant_signup", { body: params });
73
81
  }
74
82
  // --- Advanced operations (Task 4.10) ---
75
- /** Set signup settings. `POST /admin/signup_settings` */
83
+ /** Set signup settings. `POST /admin/settings/signup` */
76
84
  async setSignupSettings(params) {
77
- return this.request("POST", "/admin/signup_settings", { body: params });
85
+ return this.request("POST", "/admin/settings/signup", { body: params });
78
86
  }
79
- /** Get signup settings. `GET /admin/signup_settings` */
87
+ /** Get signup settings. `GET /admin/settings/signup` */
80
88
  async getSignupSettings() {
81
- return this.request("GET", "/admin/signup_settings");
89
+ return this.request("GET", "/admin/settings/signup");
82
90
  }
83
91
  /** Onboard a merchant. `POST /admin/onboard_merchant` */
84
92
  async onboardMerchant(params) {
@@ -97,7 +105,7 @@ var AdminPortal = class {
97
105
  });
98
106
  }
99
107
  async getCustomer(customerId) {
100
- return this.request("GET", `/admin-portal/customers/${customerId}`);
108
+ return this.request("GET", `/admin-portal/customers/${encodeURIComponent(customerId)}`);
101
109
  }
102
110
  async listTransactions(params) {
103
111
  return this.request("GET", "/admin-portal/transactions", {
@@ -137,7 +145,7 @@ var ApiKeys = class {
137
145
  * ```
138
146
  */
139
147
  async create(merchantId, params) {
140
- return this.request("POST", `/api_keys/${merchantId}`, { body: params });
148
+ return this.request("POST", `/api_keys/${encodeURIComponent(merchantId)}`, { body: params });
141
149
  }
142
150
  /**
143
151
  * Retrieve metadata about an API key (does not return the plaintext secret).
@@ -147,7 +155,10 @@ var ApiKeys = class {
147
155
  * @returns The API key metadata.
148
156
  */
149
157
  async retrieve(merchantId, keyId) {
150
- return this.request("GET", `/api_keys/${merchantId}/${keyId}`);
158
+ return this.request(
159
+ "GET",
160
+ `/api_keys/${encodeURIComponent(merchantId)}/${encodeURIComponent(keyId)}`
161
+ );
151
162
  }
152
163
  /**
153
164
  * Update an API key's name or expiry.
@@ -158,7 +169,11 @@ var ApiKeys = class {
158
169
  * @returns The updated API key metadata.
159
170
  */
160
171
  async update(merchantId, keyId, params) {
161
- return this.request("POST", `/api_keys/${merchantId}/${keyId}`, { body: params });
172
+ return this.request(
173
+ "POST",
174
+ `/api_keys/${encodeURIComponent(merchantId)}/${encodeURIComponent(keyId)}`,
175
+ { body: params }
176
+ );
162
177
  }
163
178
  /**
164
179
  * Revoke an API key, immediately invalidating it.
@@ -168,7 +183,10 @@ var ApiKeys = class {
168
183
  * @returns Revocation confirmation.
169
184
  */
170
185
  async revoke(merchantId, keyId) {
171
- return this.request("DELETE", `/api_keys/${merchantId}/${keyId}`);
186
+ return this.request(
187
+ "DELETE",
188
+ `/api_keys/${encodeURIComponent(merchantId)}/${encodeURIComponent(keyId)}`
189
+ );
172
190
  }
173
191
  /**
174
192
  * List all API keys for a merchant.
@@ -177,7 +195,7 @@ var ApiKeys = class {
177
195
  * @returns Array of API key metadata objects.
178
196
  */
179
197
  async list(merchantId) {
180
- return this.request("GET", `/api_keys/${merchantId}/list`);
198
+ return this.request("GET", `/api_keys/${encodeURIComponent(merchantId)}/list`);
181
199
  }
182
200
  };
183
201
 
@@ -192,7 +210,7 @@ var AuditLogs = class {
192
210
  });
193
211
  }
194
212
  async retrieve(logId) {
195
- return this.request("GET", `/admin-portal/audit/${logId}`);
213
+ return this.request("GET", `/admin-portal/audit/${encodeURIComponent(logId)}`);
196
214
  }
197
215
  };
198
216
 
@@ -205,27 +223,39 @@ var Authentication = class {
205
223
  return this.request("POST", "/authentication", { body: params });
206
224
  }
207
225
  async checkEligibility(authId) {
208
- return this.request("POST", `/authentication/${authId}/eligibility`);
226
+ return this.request("POST", `/authentication/${encodeURIComponent(authId)}/eligibility`);
209
227
  }
210
228
  async authenticate(authId, params) {
211
- return this.request("POST", `/authentication/${authId}/authenticate`, { body: params });
229
+ return this.request("POST", `/authentication/${encodeURIComponent(authId)}/authenticate`, {
230
+ body: params
231
+ });
212
232
  }
213
233
  async sync(authId, params) {
214
- return this.request("POST", `/authentication/${authId}/sync`, { body: params });
234
+ return this.request("POST", `/authentication/${encodeURIComponent(authId)}/sync`, {
235
+ body: params
236
+ });
215
237
  }
216
238
  /** Redirect after authentication. `POST /authentication/{authId}/redirect` */
217
239
  async redirect(authId, params) {
218
- return this.request("POST", `/authentication/${authId}/redirect`, { body: params });
240
+ return this.request("POST", `/authentication/${encodeURIComponent(authId)}/redirect`, {
241
+ body: params
242
+ });
219
243
  }
220
244
  /** Enable authn methods token. `POST /authentication/{authId}/enabled_authn_methods_token` */
221
245
  async enabledAuthnMethodsToken(authId, params) {
222
- return this.request("POST", `/authentication/${authId}/enabled_authn_methods_token`, {
223
- body: params
224
- });
246
+ return this.request(
247
+ "POST",
248
+ `/authentication/${encodeURIComponent(authId)}/enabled_authn_methods_token`,
249
+ {
250
+ body: params
251
+ }
252
+ );
225
253
  }
226
254
  /** Submit eligibility check. `POST /authentication/{authId}/eligibility-check` */
227
255
  async eligibilityCheck(authId, params) {
228
- return this.request("POST", `/authentication/${authId}/eligibility-check`, { body: params });
256
+ return this.request("POST", `/authentication/${encodeURIComponent(authId)}/eligibility-check`, {
257
+ body: params
258
+ });
229
259
  }
230
260
  };
231
261
 
@@ -242,7 +272,11 @@ var BillingAllocations = class {
242
272
  * @returns The allocation transfer result.
243
273
  */
244
274
  async transferIn(merchantId, params) {
245
- return this.request("POST", `/billing/${merchantId}/allocations/transfer-in`, { body: params });
275
+ return this.request(
276
+ "POST",
277
+ `/billing/${encodeURIComponent(merchantId)}/allocations/transfer-in`,
278
+ { body: params }
279
+ );
246
280
  }
247
281
  /**
248
282
  * Transfer funds from a shop's allocation back to the host merchant treasury.
@@ -252,9 +286,13 @@ var BillingAllocations = class {
252
286
  * @returns The allocation transfer result.
253
287
  */
254
288
  async transferOut(merchantId, params) {
255
- return this.request("POST", `/billing/${merchantId}/allocations/transfer-out`, {
256
- body: params
257
- });
289
+ return this.request(
290
+ "POST",
291
+ `/billing/${encodeURIComponent(merchantId)}/allocations/transfer-out`,
292
+ {
293
+ body: params
294
+ }
295
+ );
258
296
  }
259
297
  /**
260
298
  * List all shop balance allocations for a merchant.
@@ -263,7 +301,7 @@ var BillingAllocations = class {
263
301
  * @returns List of shop allocations.
264
302
  */
265
303
  async list(merchantId) {
266
- return this.request("GET", `/billing/${merchantId}/allocations`);
304
+ return this.request("GET", `/billing/${encodeURIComponent(merchantId)}/allocations`);
267
305
  }
268
306
  /**
269
307
  * Get the balance allocation for a specific shop.
@@ -273,7 +311,10 @@ var BillingAllocations = class {
273
311
  * @returns The shop's balance allocation.
274
312
  */
275
313
  async get(merchantId, profileId) {
276
- return this.request("GET", `/billing/${merchantId}/allocations/${profileId}`);
314
+ return this.request(
315
+ "GET",
316
+ `/billing/${encodeURIComponent(merchantId)}/allocations/${encodeURIComponent(profileId)}`
317
+ );
277
318
  }
278
319
  };
279
320
  var Billing = class {
@@ -294,7 +335,7 @@ var Billing = class {
294
335
  * ```
295
336
  */
296
337
  async getProfile(merchantId) {
297
- return this.request("GET", `/billing/${merchantId}`);
338
+ return this.request("GET", `/billing/${encodeURIComponent(merchantId)}`);
298
339
  }
299
340
  /**
300
341
  * Start a Stripe SetupIntent flow to collect a payment card for auto-recharge.
@@ -304,7 +345,9 @@ var Billing = class {
304
345
  * @returns The Stripe client secret needed to render the card element.
305
346
  */
306
347
  async setup(merchantId, params) {
307
- return this.request("POST", `/billing/${merchantId}/setup`, { body: params });
348
+ return this.request("POST", `/billing/${encodeURIComponent(merchantId)}/setup`, {
349
+ body: params
350
+ });
308
351
  }
309
352
  /**
310
353
  * Confirm card setup after the Stripe SetupIntent completes on the frontend.
@@ -314,7 +357,9 @@ var Billing = class {
314
357
  * @returns The updated billing profile.
315
358
  */
316
359
  async completeSetup(merchantId, params) {
317
- return this.request("POST", `/billing/${merchantId}/setup/complete`, { body: params });
360
+ return this.request("POST", `/billing/${encodeURIComponent(merchantId)}/setup/complete`, {
361
+ body: params
362
+ });
318
363
  }
319
364
  /**
320
365
  * Manually top up a merchant's prepaid balance by charging their saved card.
@@ -324,7 +369,9 @@ var Billing = class {
324
369
  * @returns The top-up result.
325
370
  */
326
371
  async topup(merchantId, params) {
327
- return this.request("POST", `/billing/${merchantId}/topup`, { body: params });
372
+ return this.request("POST", `/billing/${encodeURIComponent(merchantId)}/topup`, {
373
+ body: params
374
+ });
328
375
  }
329
376
  /**
330
377
  * List the balance ledger (credits and debits) for a merchant.
@@ -334,7 +381,7 @@ var Billing = class {
334
381
  * @returns The ledger entries.
335
382
  */
336
383
  async listLedger(merchantId, params) {
337
- return this.request("GET", `/billing/${merchantId}/ledger`, {
384
+ return this.request("GET", `/billing/${encodeURIComponent(merchantId)}/ledger`, {
338
385
  query: params
339
386
  });
340
387
  }
@@ -346,7 +393,9 @@ var Billing = class {
346
393
  * @returns The updated billing profile.
347
394
  */
348
395
  async updateAutoRecharge(merchantId, params) {
349
- return this.request("PATCH", `/billing/${merchantId}/auto-recharge`, { body: params });
396
+ return this.request("PATCH", `/billing/${encodeURIComponent(merchantId)}/auto-recharge`, {
397
+ body: params
398
+ });
350
399
  }
351
400
  /**
352
401
  * Admin: manually credit a merchant's balance (e.g. promotional credit).
@@ -356,7 +405,9 @@ var Billing = class {
356
405
  * @returns The adjustment result.
357
406
  */
358
407
  async adminCredit(merchantId, params) {
359
- return this.request("POST", `/billing/${merchantId}/admin/credit`, { body: params });
408
+ return this.request("POST", `/billing/${encodeURIComponent(merchantId)}/admin/credit`, {
409
+ body: params
410
+ });
360
411
  }
361
412
  /**
362
413
  * Admin: manually debit a merchant's balance.
@@ -366,7 +417,9 @@ var Billing = class {
366
417
  * @returns The adjustment result.
367
418
  */
368
419
  async adminDebit(merchantId, params) {
369
- return this.request("POST", `/billing/${merchantId}/admin/debit`, { body: params });
420
+ return this.request("POST", `/billing/${encodeURIComponent(merchantId)}/admin/debit`, {
421
+ body: params
422
+ });
370
423
  }
371
424
  };
372
425
 
@@ -400,7 +453,7 @@ var CardIssuers = class {
400
453
  return this.request("POST", "/card_issuers", { body: params });
401
454
  }
402
455
  async update(issuerId, params) {
403
- return this.request("PUT", `/card_issuers/${issuerId}`, { body: params });
456
+ return this.request("PUT", `/card_issuers/${encodeURIComponent(issuerId)}`, { body: params });
404
457
  }
405
458
  async list() {
406
459
  return this.request("GET", "/card_issuers");
@@ -413,21 +466,33 @@ var Connectors = class {
413
466
  this.request = request;
414
467
  }
415
468
  async create(accountId, params) {
416
- return this.request("POST", `/account/${accountId}/connectors`, { body: params });
469
+ return this.request("POST", `/account/${encodeURIComponent(accountId)}/connectors`, {
470
+ body: params
471
+ });
417
472
  }
418
473
  async retrieve(accountId, connectorId) {
419
- return this.request("GET", `/account/${accountId}/connectors/${connectorId}`);
474
+ return this.request(
475
+ "GET",
476
+ `/account/${encodeURIComponent(accountId)}/connectors/${encodeURIComponent(connectorId)}`
477
+ );
420
478
  }
421
479
  async list(accountId) {
422
- return this.request("GET", `/account/${accountId}/connectors`);
480
+ return this.request("GET", `/account/${encodeURIComponent(accountId)}/connectors`);
423
481
  }
424
482
  async update(accountId, connectorId, params) {
425
- return this.request("POST", `/account/${accountId}/connectors/${connectorId}`, {
426
- body: params
427
- });
483
+ return this.request(
484
+ "POST",
485
+ `/account/${encodeURIComponent(accountId)}/connectors/${encodeURIComponent(connectorId)}`,
486
+ {
487
+ body: params
488
+ }
489
+ );
428
490
  }
429
491
  async delete(accountId, connectorId) {
430
- return this.request("DELETE", `/account/${accountId}/connectors/${connectorId}`);
492
+ return this.request(
493
+ "DELETE",
494
+ `/account/${encodeURIComponent(accountId)}/connectors/${encodeURIComponent(connectorId)}`
495
+ );
431
496
  }
432
497
  // --- Advanced operations (Task 4.8) ---
433
498
  /** Verify connector credentials. `POST /account/connectors/verify` */
@@ -436,11 +501,17 @@ var Connectors = class {
436
501
  }
437
502
  /** Register a webhook for a connector. `POST /account/{merchantId}/connectors/webhooks/{connectorId}` */
438
503
  async registerWebhook(merchantId, connectorId) {
439
- return this.request("POST", `/account/${merchantId}/connectors/webhooks/${connectorId}`);
504
+ return this.request(
505
+ "POST",
506
+ `/account/${encodeURIComponent(merchantId)}/connectors/webhooks/${encodeURIComponent(connectorId)}`
507
+ );
440
508
  }
441
509
  /** Get a webhook for a connector. `GET /account/{merchantId}/connectors/webhooks/{connectorId}` */
442
510
  async getWebhook(merchantId, connectorId) {
443
- return this.request("GET", `/account/${merchantId}/connectors/webhooks/${connectorId}`);
511
+ return this.request(
512
+ "GET",
513
+ `/account/${encodeURIComponent(merchantId)}/connectors/webhooks/${encodeURIComponent(connectorId)}`
514
+ );
444
515
  }
445
516
  /** List available payment methods. `GET /account/payment_methods` */
446
517
  async listPaymentMethods() {
@@ -482,7 +553,7 @@ var Customers = class {
482
553
  * ```
483
554
  */
484
555
  async retrieve(customerId) {
485
- return this.request("GET", `/customers/${customerId}`);
556
+ return this.request("GET", `/customers/${encodeURIComponent(customerId)}`);
486
557
  }
487
558
  /**
488
559
  * Update an existing customer's details.
@@ -492,7 +563,7 @@ var Customers = class {
492
563
  * @returns The updated customer.
493
564
  */
494
565
  async update(customerId, params) {
495
- return this.request("POST", `/customers/${customerId}`, { body: params });
566
+ return this.request("POST", `/customers/${encodeURIComponent(customerId)}`, { body: params });
496
567
  }
497
568
  /**
498
569
  * Delete a customer and all their saved payment methods.
@@ -501,7 +572,7 @@ var Customers = class {
501
572
  * @returns The deleted customer object.
502
573
  */
503
574
  async delete(customerId) {
504
- return this.request("DELETE", `/customers/${customerId}`);
575
+ return this.request("DELETE", `/customers/${encodeURIComponent(customerId)}`);
505
576
  }
506
577
  /**
507
578
  * List customers, optionally filtered by email.
@@ -523,7 +594,7 @@ var Customers = class {
523
594
  }
524
595
  /** List mandates for a customer. `GET /customers/{customerId}/mandates` */
525
596
  async listMandates(customerId) {
526
- return this.request("GET", `/customers/${customerId}/mandates`);
597
+ return this.request("GET", `/customers/${encodeURIComponent(customerId)}/mandates`);
527
598
  }
528
599
  };
529
600
 
@@ -539,7 +610,7 @@ var Disputes = class {
539
610
  * @returns The dispute.
540
611
  */
541
612
  async retrieve(disputeId) {
542
- return this.request("GET", `/disputes/${disputeId}`);
613
+ return this.request("GET", `/disputes/${encodeURIComponent(disputeId)}`);
543
614
  }
544
615
  /**
545
616
  * List disputes, optionally filtered by status, stage, or date range.
@@ -559,7 +630,7 @@ var Disputes = class {
559
630
  * @returns The updated dispute.
560
631
  */
561
632
  async accept(disputeId) {
562
- return this.request("POST", `/disputes/accept/${disputeId}`);
633
+ return this.request("POST", `/disputes/accept/${encodeURIComponent(disputeId)}`);
563
634
  }
564
635
  /**
565
636
  * Submit evidence to challenge a dispute.
@@ -585,7 +656,7 @@ var Disputes = class {
585
656
  * @returns The submitted evidence.
586
657
  */
587
658
  async retrieveEvidence(disputeId) {
588
- return this.request("GET", `/disputes/evidence/${disputeId}`);
659
+ return this.request("GET", `/disputes/evidence/${encodeURIComponent(disputeId)}`);
589
660
  }
590
661
  /**
591
662
  * Delete submitted evidence for a dispute.
@@ -619,9 +690,17 @@ var Disputes = class {
619
690
  async aggregateByProfile(params) {
620
691
  return this.request("GET", "/disputes/profile/aggregate", { query: params });
621
692
  }
622
- /** Fetch dispute from connector. `POST /disputes/{disputeId}/fetch_from_connector` */
623
- async fetchFromConnector(disputeId) {
624
- return this.request("POST", `/disputes/${disputeId}/fetch_from_connector`);
693
+ /**
694
+ * Fetch the latest dispute state from the connector (gateway).
695
+ * `GET /disputes/{connectorId}/fetch`
696
+ *
697
+ * Note: the path parameter is the **connector dispute id** on the gateway, not the
698
+ * Delopay dispute id. Method is GET (not POST) and this method signature was
699
+ * previously wrong — callers depending on the old `POST /disputes/{id}/fetch_from_connector`
700
+ * path were silently hitting 404s.
701
+ */
702
+ async fetchFromConnector(connectorId) {
703
+ return this.request("GET", `/disputes/${encodeURIComponent(connectorId)}/fetch`);
625
704
  }
626
705
  };
627
706
 
@@ -652,7 +731,7 @@ var EphemeralKeys = class {
652
731
  * @returns The deleted key object.
653
732
  */
654
733
  async delete(keyId) {
655
- return this.request("DELETE", `/ephemeral_keys/${keyId}`);
734
+ return this.request("DELETE", `/ephemeral_keys/${encodeURIComponent(keyId)}`);
656
735
  }
657
736
  };
658
737
 
@@ -662,13 +741,19 @@ var Events = class {
662
741
  this.request = request;
663
742
  }
664
743
  async list(merchantId, params) {
665
- return this.request("POST", `/events/${merchantId}`, { body: params });
744
+ return this.request("POST", `/events/${encodeURIComponent(merchantId)}`, { body: params });
666
745
  }
667
746
  async listDeliveryAttempts(merchantId, eventId) {
668
- return this.request("GET", `/events/${merchantId}/${eventId}/attempts`);
747
+ return this.request(
748
+ "GET",
749
+ `/events/${encodeURIComponent(merchantId)}/${encodeURIComponent(eventId)}/attempts`
750
+ );
669
751
  }
670
752
  async retryDelivery(merchantId, eventId) {
671
- return this.request("POST", `/events/${merchantId}/${eventId}/retry`);
753
+ return this.request(
754
+ "POST",
755
+ `/events/${encodeURIComponent(merchantId)}/${encodeURIComponent(eventId)}/retry`
756
+ );
672
757
  }
673
758
  // --- Profile-scoped listing (Task 4.12) ---
674
759
  /** List events (profile-scoped). `POST /events/profile/list` */
@@ -713,7 +798,7 @@ var PlatformFees = class {
713
798
  * @returns The fee schedule.
714
799
  */
715
800
  async retrieve(feeId) {
716
- return this.request("GET", `/admin/fees/${feeId}`);
801
+ return this.request("GET", `/admin/fees/${encodeURIComponent(feeId)}`);
717
802
  }
718
803
  /**
719
804
  * Update a fee schedule (admin only).
@@ -723,7 +808,7 @@ var PlatformFees = class {
723
808
  * @returns The updated fee schedule.
724
809
  */
725
810
  async update(feeId, params) {
726
- return this.request("PUT", `/admin/fees/${feeId}`, { body: params });
811
+ return this.request("PUT", `/admin/fees/${encodeURIComponent(feeId)}`, { body: params });
727
812
  }
728
813
  /**
729
814
  * Delete a fee schedule (admin only).
@@ -732,7 +817,7 @@ var PlatformFees = class {
732
817
  * @returns The deleted fee schedule.
733
818
  */
734
819
  async delete(feeId) {
735
- return this.request("DELETE", `/admin/fees/${feeId}`);
820
+ return this.request("DELETE", `/admin/fees/${encodeURIComponent(feeId)}`);
736
821
  }
737
822
  };
738
823
  var MerchantFees = class {
@@ -771,7 +856,7 @@ var MerchantFees = class {
771
856
  * @returns The updated fee schedule.
772
857
  */
773
858
  async update(feeId, params) {
774
- return this.request("PUT", `/merchant_fees/${feeId}`, { body: params });
859
+ return this.request("PUT", `/merchant_fees/${encodeURIComponent(feeId)}`, { body: params });
775
860
  }
776
861
  /**
777
862
  * Delete a merchant-scoped fee schedule.
@@ -780,7 +865,7 @@ var MerchantFees = class {
780
865
  * @returns The deleted fee schedule.
781
866
  */
782
867
  async delete(feeId) {
783
- return this.request("DELETE", `/merchant_fees/${feeId}`);
868
+ return this.request("DELETE", `/merchant_fees/${encodeURIComponent(feeId)}`);
784
869
  }
785
870
  };
786
871
  var Fees = class {
@@ -821,7 +906,7 @@ var Mandates = class {
821
906
  * @returns The mandate.
822
907
  */
823
908
  async retrieve(mandateId) {
824
- return this.request("GET", `/mandates/${mandateId}`);
909
+ return this.request("GET", `/mandates/${encodeURIComponent(mandateId)}`);
825
910
  }
826
911
  /**
827
912
  * Revoke an active mandate, preventing future charges.
@@ -830,7 +915,7 @@ var Mandates = class {
830
915
  * @returns Revocation confirmation.
831
916
  */
832
917
  async revoke(mandateId) {
833
- return this.request("POST", `/mandates/revoke/${mandateId}`);
918
+ return this.request("POST", `/mandates/revoke/${encodeURIComponent(mandateId)}`);
834
919
  }
835
920
  /**
836
921
  * List mandates, optionally filtered by customer or status.
@@ -854,13 +939,13 @@ var MerchantAccounts = class {
854
939
  return this.request("POST", "/accounts", { body: params });
855
940
  }
856
941
  async retrieve(accountId) {
857
- return this.request("GET", `/accounts/${accountId}`);
942
+ return this.request("GET", `/accounts/${encodeURIComponent(accountId)}`);
858
943
  }
859
944
  async update(accountId, params) {
860
- return this.request("POST", `/accounts/${accountId}`, { body: params });
945
+ return this.request("POST", `/accounts/${encodeURIComponent(accountId)}`, { body: params });
861
946
  }
862
947
  async delete(accountId) {
863
- return this.request("DELETE", `/accounts/${accountId}`);
948
+ return this.request("DELETE", `/accounts/${encodeURIComponent(accountId)}`);
864
949
  }
865
950
  // --- Advanced operations (Task 4.9) ---
866
951
  /** List all merchant accounts. `GET /accounts/list` */
@@ -869,15 +954,15 @@ var MerchantAccounts = class {
869
954
  }
870
955
  /** Toggle key-value store for a merchant. `POST /accounts/{accountId}/kv` */
871
956
  async toggleKv(accountId) {
872
- return this.request("POST", `/accounts/${accountId}/kv`);
957
+ return this.request("POST", `/accounts/${encodeURIComponent(accountId)}/kv`);
873
958
  }
874
959
  /** Get KV status for a merchant. `GET /accounts/{accountId}/kv` */
875
960
  async getKvStatus(accountId) {
876
- return this.request("GET", `/accounts/${accountId}/kv`);
961
+ return this.request("GET", `/accounts/${encodeURIComponent(accountId)}/kv`);
877
962
  }
878
- /** Transfer keys between merchants. `POST /accounts/transfer_keys` */
963
+ /** Transfer keys between merchants. `POST /accounts/transfer` */
879
964
  async transferKeys(params) {
880
- return this.request("POST", "/accounts/transfer_keys", { body: params });
965
+ return this.request("POST", "/accounts/transfer", { body: params });
881
966
  }
882
967
  };
883
968
 
@@ -893,7 +978,7 @@ var PaymentLinks = class {
893
978
  * @returns The payment link details.
894
979
  */
895
980
  async retrieve(linkId) {
896
- return this.request("GET", `/payment_link/${linkId}`);
981
+ return this.request("GET", `/payment_link/${encodeURIComponent(linkId)}`);
897
982
  }
898
983
  /**
899
984
  * List payment links, optionally filtered by status or date range.
@@ -906,11 +991,17 @@ var PaymentLinks = class {
906
991
  }
907
992
  /** Initiate (render) a payment link page. `GET /payment_link/{merchantId}/{paymentId}` */
908
993
  async initiate(merchantId, paymentId) {
909
- return this.request("GET", `/payment_link/${merchantId}/${paymentId}`);
994
+ return this.request(
995
+ "GET",
996
+ `/payment_link/${encodeURIComponent(merchantId)}/${encodeURIComponent(paymentId)}`
997
+ );
910
998
  }
911
999
  /** Get payment link status. `GET /payment_linkstatus/{merchantId}/{paymentId}` */
912
1000
  async status(merchantId, paymentId) {
913
- return this.request("GET", `/payment_linkstatus/${merchantId}/${paymentId}`);
1001
+ return this.request(
1002
+ "GET",
1003
+ `/payment_linkstatus/${encodeURIComponent(merchantId)}/${encodeURIComponent(paymentId)}`
1004
+ );
914
1005
  }
915
1006
  };
916
1007
 
@@ -944,7 +1035,7 @@ var PaymentMethods = class {
944
1035
  * @returns The payment method.
945
1036
  */
946
1037
  async retrieve(methodId) {
947
- return this.request("GET", `/payment_methods/${methodId}`);
1038
+ return this.request("GET", `/payment_methods/${encodeURIComponent(methodId)}`);
948
1039
  }
949
1040
  /**
950
1041
  * Update an existing payment method (e.g. update card expiry).
@@ -954,7 +1045,9 @@ var PaymentMethods = class {
954
1045
  * @returns The updated payment method.
955
1046
  */
956
1047
  async update(methodId, params) {
957
- return this.request("POST", `/payment_methods/${methodId}/update`, { body: params });
1048
+ return this.request("POST", `/payment_methods/${encodeURIComponent(methodId)}/update`, {
1049
+ body: params
1050
+ });
958
1051
  }
959
1052
  /**
960
1053
  * Delete a saved payment method.
@@ -963,7 +1056,7 @@ var PaymentMethods = class {
963
1056
  * @returns Deletion confirmation.
964
1057
  */
965
1058
  async delete(methodId) {
966
- return this.request("DELETE", `/payment_methods/${methodId}`);
1059
+ return this.request("DELETE", `/payment_methods/${encodeURIComponent(methodId)}`);
967
1060
  }
968
1061
  /**
969
1062
  * List payment methods using a client secret.
@@ -977,18 +1070,25 @@ var PaymentMethods = class {
977
1070
  });
978
1071
  }
979
1072
  /**
980
- * List all saved payment methods for a customer.
1073
+ * List all saved payment methods for a customer, optionally filtered.
981
1074
  *
982
1075
  * @param customerId - The customer ID.
1076
+ * @param params - Optional filters: `client_secret`, `accepted_countries`, `accepted_currencies`,
1077
+ * `amount`, `recurring_enabled`, `installment_payment_enabled`, `limit`, `card_networks`.
983
1078
  * @returns Customer's saved payment methods.
984
1079
  *
985
1080
  * @example
986
1081
  * ```typescript
987
- * const { customer_payment_methods } = await delopay.paymentMethods.listForCustomer('cus_123');
1082
+ * const { customer_payment_methods } = await delopay.paymentMethods.listForCustomer(
1083
+ * 'cus_123',
1084
+ * { accepted_currencies: ['EUR'], amount: 5000 },
1085
+ * );
988
1086
  * ```
989
1087
  */
990
- async listForCustomer(customerId) {
991
- return this.request("GET", `/customers/${customerId}/payment_methods`);
1088
+ async listForCustomer(customerId, params) {
1089
+ return this.request("GET", `/customers/${encodeURIComponent(customerId)}/payment_methods`, {
1090
+ query: params
1091
+ });
992
1092
  }
993
1093
  /**
994
1094
  * Set a payment method as the default for a customer.
@@ -998,7 +1098,10 @@ var PaymentMethods = class {
998
1098
  * @returns The updated payment method.
999
1099
  */
1000
1100
  async setDefault(customerId, methodId) {
1001
- return this.request("POST", `/customers/${customerId}/payment_methods/${methodId}/default`);
1101
+ return this.request(
1102
+ "POST",
1103
+ `/customers/${encodeURIComponent(customerId)}/payment_methods/${encodeURIComponent(methodId)}/default`
1104
+ );
1002
1105
  }
1003
1106
  // --- Advanced operations (Task 3.3) ---
1004
1107
  /** Migrate a payment method. `POST /payment_methods/migrate` */
@@ -1031,7 +1134,9 @@ var PaymentMethods = class {
1031
1134
  }
1032
1135
  /** Save a payment method. `POST /payment_methods/{methodId}/save` */
1033
1136
  async save(methodId, params) {
1034
- return this.request("POST", `/payment_methods/${methodId}/save`, { body: params });
1137
+ return this.request("POST", `/payment_methods/${encodeURIComponent(methodId)}/save`, {
1138
+ body: params
1139
+ });
1035
1140
  }
1036
1141
  /** Create payment method auth link token. `POST /payment_methods/auth/link` */
1037
1142
  async createAuthLink(params) {
@@ -1043,7 +1148,9 @@ var PaymentMethods = class {
1043
1148
  }
1044
1149
  /** Tokenize card using existing PM. `POST /payment_methods/{methodId}/tokenize-card` */
1045
1150
  async tokenizeCardForMethod(methodId, params) {
1046
- return this.request("POST", `/payment_methods/${methodId}/tokenize-card`, { body: params });
1151
+ return this.request("POST", `/payment_methods/${encodeURIComponent(methodId)}/tokenize-card`, {
1152
+ body: params
1153
+ });
1047
1154
  }
1048
1155
  };
1049
1156
 
@@ -1082,7 +1189,7 @@ var Payments = class {
1082
1189
  * ```
1083
1190
  */
1084
1191
  async retrieve(paymentId) {
1085
- return this.request("GET", `/payments/${paymentId}`);
1192
+ return this.request("GET", `/payments/${encodeURIComponent(paymentId)}`);
1086
1193
  }
1087
1194
  /**
1088
1195
  * Update an existing payment intent before it is confirmed.
@@ -1092,7 +1199,7 @@ var Payments = class {
1092
1199
  * @returns The updated payment intent.
1093
1200
  */
1094
1201
  async update(paymentId, params) {
1095
- return this.request("POST", `/payments/${paymentId}`, { body: params });
1202
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}`, { body: params });
1096
1203
  }
1097
1204
  /**
1098
1205
  * Confirm a payment intent, triggering authorisation with the selected gateway.
@@ -1102,7 +1209,9 @@ var Payments = class {
1102
1209
  * @returns The updated payment intent.
1103
1210
  */
1104
1211
  async confirm(paymentId, params) {
1105
- return this.request("POST", `/payments/${paymentId}/confirm`, { body: params });
1212
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/confirm`, {
1213
+ body: params
1214
+ });
1106
1215
  }
1107
1216
  /**
1108
1217
  * Capture a previously authorised payment.
@@ -1112,7 +1221,9 @@ var Payments = class {
1112
1221
  * @returns The updated payment intent.
1113
1222
  */
1114
1223
  async capture(paymentId, params) {
1115
- return this.request("POST", `/payments/${paymentId}/capture`, { body: params });
1224
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/capture`, {
1225
+ body: params
1226
+ });
1116
1227
  }
1117
1228
  /**
1118
1229
  * Cancel a payment intent that has not yet been captured.
@@ -1122,7 +1233,9 @@ var Payments = class {
1122
1233
  * @returns The updated payment intent.
1123
1234
  */
1124
1235
  async cancel(paymentId, params) {
1125
- return this.request("POST", `/payments/${paymentId}/cancel`, { body: params });
1236
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/cancel`, {
1237
+ body: params
1238
+ });
1126
1239
  }
1127
1240
  /**
1128
1241
  * List payment intents, optionally filtered by customer or date range.
@@ -1151,33 +1264,47 @@ var Payments = class {
1151
1264
  }
1152
1265
  /** Cancel after partial capture. `POST /payments/{paymentId}/cancel_post_capture` */
1153
1266
  async cancelPostCapture(paymentId, params) {
1154
- return this.request("POST", `/payments/${paymentId}/cancel_post_capture`, { body: params });
1267
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/cancel_post_capture`, {
1268
+ body: params
1269
+ });
1155
1270
  }
1156
1271
  /** Incrementally authorize more funds. `POST /payments/{paymentId}/incremental_authorization` */
1157
1272
  async incrementalAuthorization(paymentId, params) {
1158
- return this.request("POST", `/payments/${paymentId}/incremental_authorization`, {
1159
- body: params
1160
- });
1273
+ return this.request(
1274
+ "POST",
1275
+ `/payments/${encodeURIComponent(paymentId)}/incremental_authorization`,
1276
+ {
1277
+ body: params
1278
+ }
1279
+ );
1161
1280
  }
1162
1281
  /** Extend authorization window. `POST /payments/{paymentId}/extend_authorization` */
1163
1282
  async extendAuthorization(paymentId, params) {
1164
- return this.request("POST", `/payments/${paymentId}/extend_authorization`, { body: params });
1283
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/extend_authorization`, {
1284
+ body: params
1285
+ });
1165
1286
  }
1166
1287
  /** Complete authorization. `POST /payments/{paymentId}/complete_authorize` */
1167
1288
  async completeAuthorize(paymentId, params) {
1168
- return this.request("POST", `/payments/${paymentId}/complete_authorize`, { body: params });
1289
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/complete_authorize`, {
1290
+ body: params
1291
+ });
1169
1292
  }
1170
1293
  /** Dynamic tax calculation. `POST /payments/{paymentId}/calculate_tax` */
1171
1294
  async calculateTax(paymentId, params) {
1172
- return this.request("POST", `/payments/${paymentId}/calculate_tax`, { body: params });
1295
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/calculate_tax`, {
1296
+ body: params
1297
+ });
1173
1298
  }
1174
1299
  /** Update payment metadata. `POST /payments/{paymentId}/update_metadata` */
1175
1300
  async updateMetadata(paymentId, params) {
1176
- return this.request("POST", `/payments/${paymentId}/update_metadata`, { body: params });
1301
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/update_metadata`, {
1302
+ body: params
1303
+ });
1177
1304
  }
1178
1305
  /** Retrieve extended card info. `GET /payments/{paymentId}/extended_card_info` */
1179
1306
  async extendedCardInfo(paymentId) {
1180
- return this.request("GET", `/payments/${paymentId}/extended_card_info`);
1307
+ return this.request("GET", `/payments/${encodeURIComponent(paymentId)}/extended_card_info`);
1181
1308
  }
1182
1309
  // --- OLAP extensions (Task 4.2) ---
1183
1310
  /** List payments (profile-scoped). `GET /payments/profile/list` */
@@ -1214,19 +1341,27 @@ var Payments = class {
1214
1341
  }
1215
1342
  /** Manually update payment status. `PUT /payments/{paymentId}/manual-update` */
1216
1343
  async manualUpdate(paymentId, params) {
1217
- return this.request("PUT", `/payments/${paymentId}/manual-update`, { body: params });
1344
+ return this.request("PUT", `/payments/${encodeURIComponent(paymentId)}/manual-update`, {
1345
+ body: params
1346
+ });
1218
1347
  }
1219
1348
  /** Approve a payment waiting for review. `POST /payments/{paymentId}/approve` */
1220
1349
  async approve(paymentId, params) {
1221
- return this.request("POST", `/payments/${paymentId}/approve`, { body: params });
1350
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/approve`, {
1351
+ body: params
1352
+ });
1222
1353
  }
1223
1354
  /** Reject a payment waiting for review. `POST /payments/{paymentId}/reject` */
1224
1355
  async reject(paymentId, params) {
1225
- return this.request("POST", `/payments/${paymentId}/reject`, { body: params });
1356
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/reject`, {
1357
+ body: params
1358
+ });
1226
1359
  }
1227
1360
  /** Initiate external 3DS authentication. `POST /payments/{paymentId}/3ds/authentication` */
1228
1361
  async threeDsAuthentication(paymentId, params) {
1229
- return this.request("POST", `/payments/${paymentId}/3ds/authentication`, { body: params });
1362
+ return this.request("POST", `/payments/${encodeURIComponent(paymentId)}/3ds/authentication`, {
1363
+ body: params
1364
+ });
1230
1365
  }
1231
1366
  };
1232
1367
 
@@ -1260,7 +1395,7 @@ var Payouts = class {
1260
1395
  * @returns The payout.
1261
1396
  */
1262
1397
  async retrieve(payoutId) {
1263
- return this.request("GET", `/payouts/${payoutId}`);
1398
+ return this.request("GET", `/payouts/${encodeURIComponent(payoutId)}`);
1264
1399
  }
1265
1400
  /**
1266
1401
  * Update a payout before it is confirmed.
@@ -1270,7 +1405,7 @@ var Payouts = class {
1270
1405
  * @returns The updated payout.
1271
1406
  */
1272
1407
  async update(payoutId, params) {
1273
- return this.request("PUT", `/payouts/${payoutId}`, { body: params });
1408
+ return this.request("PUT", `/payouts/${encodeURIComponent(payoutId)}`, { body: params });
1274
1409
  }
1275
1410
  /**
1276
1411
  * Confirm a payout, triggering the actual transfer.
@@ -1280,7 +1415,9 @@ var Payouts = class {
1280
1415
  * @returns The updated payout.
1281
1416
  */
1282
1417
  async confirm(payoutId, params) {
1283
- return this.request("POST", `/payouts/${payoutId}/confirm`, { body: params });
1418
+ return this.request("POST", `/payouts/${encodeURIComponent(payoutId)}/confirm`, {
1419
+ body: params
1420
+ });
1284
1421
  }
1285
1422
  /**
1286
1423
  * Cancel a payout before it is fulfilled.
@@ -1289,7 +1426,7 @@ var Payouts = class {
1289
1426
  * @returns The cancelled payout.
1290
1427
  */
1291
1428
  async cancel(payoutId) {
1292
- return this.request("POST", `/payouts/${payoutId}/cancel`);
1429
+ return this.request("POST", `/payouts/${encodeURIComponent(payoutId)}/cancel`);
1293
1430
  }
1294
1431
  /**
1295
1432
  * Mark a payout as fulfilled (manual confirmation of successful transfer).
@@ -1298,7 +1435,7 @@ var Payouts = class {
1298
1435
  * @returns The fulfilled payout.
1299
1436
  */
1300
1437
  async fulfill(payoutId) {
1301
- return this.request("POST", `/payouts/${payoutId}/fulfill`);
1438
+ return this.request("POST", `/payouts/${encodeURIComponent(payoutId)}/fulfill`);
1302
1439
  }
1303
1440
  /**
1304
1441
  * List payouts, optionally filtered by status or date range.
@@ -1340,7 +1477,9 @@ var Payouts = class {
1340
1477
  }
1341
1478
  /** Manually update payout status. `PUT /payouts/{payoutId}/manual-update` */
1342
1479
  async manualUpdate(payoutId, params) {
1343
- return this.request("PUT", `/payouts/${payoutId}/manual-update`, { body: params });
1480
+ return this.request("PUT", `/payouts/${encodeURIComponent(payoutId)}/manual-update`, {
1481
+ body: params
1482
+ });
1344
1483
  }
1345
1484
  };
1346
1485
 
@@ -1350,7 +1489,7 @@ var Poll = class {
1350
1489
  this.request = request;
1351
1490
  }
1352
1491
  async getStatus(pollId) {
1353
- return this.request("GET", `/poll/status/${pollId}`);
1492
+ return this.request("GET", `/poll/status/${encodeURIComponent(pollId)}`);
1354
1493
  }
1355
1494
  };
1356
1495
 
@@ -1363,9 +1502,13 @@ var ProfileAcquirers = class {
1363
1502
  return this.request("POST", "/profile_acquirer", { body: params });
1364
1503
  }
1365
1504
  async update(profileId, profileAcquirerId, params) {
1366
- return this.request("POST", `/profile_acquirer/${profileId}/${profileAcquirerId}`, {
1367
- body: params
1368
- });
1505
+ return this.request(
1506
+ "POST",
1507
+ `/profile_acquirer/${encodeURIComponent(profileId)}/${encodeURIComponent(profileAcquirerId)}`,
1508
+ {
1509
+ body: params
1510
+ }
1511
+ );
1369
1512
  }
1370
1513
  };
1371
1514
 
@@ -1375,35 +1518,47 @@ var Profiles = class {
1375
1518
  this.request = request;
1376
1519
  }
1377
1520
  async create(accountId, params) {
1378
- return this.request("POST", `/account/${accountId}/business_profile`, { body: params });
1521
+ return this.request("POST", `/account/${encodeURIComponent(accountId)}/business_profile`, {
1522
+ body: params
1523
+ });
1379
1524
  }
1380
1525
  async retrieve(accountId, profileId) {
1381
- return this.request("GET", `/account/${accountId}/business_profile/${profileId}`);
1526
+ return this.request(
1527
+ "GET",
1528
+ `/account/${encodeURIComponent(accountId)}/business_profile/${encodeURIComponent(profileId)}`
1529
+ );
1382
1530
  }
1383
1531
  async list(accountId) {
1384
- return this.request("GET", `/account/${accountId}/business_profile`);
1532
+ return this.request("GET", `/account/${encodeURIComponent(accountId)}/business_profile`);
1385
1533
  }
1386
1534
  async update(accountId, profileId, params) {
1387
- return this.request("POST", `/account/${accountId}/business_profile/${profileId}`, {
1388
- body: params
1389
- });
1535
+ return this.request(
1536
+ "POST",
1537
+ `/account/${encodeURIComponent(accountId)}/business_profile/${encodeURIComponent(profileId)}`,
1538
+ {
1539
+ body: params
1540
+ }
1541
+ );
1390
1542
  }
1391
1543
  async delete(accountId, profileId) {
1392
- return this.request("DELETE", `/account/${accountId}/business_profile/${profileId}`);
1544
+ return this.request(
1545
+ "DELETE",
1546
+ `/account/${encodeURIComponent(accountId)}/business_profile/${encodeURIComponent(profileId)}`
1547
+ );
1393
1548
  }
1394
1549
  // --- Advanced operations (Task 4.8) ---
1395
1550
  /** Toggle extended card info for a profile. `POST /account/{accountId}/business_profile/{profileId}/toggle_extended_card_info` */
1396
1551
  async toggleExtendedCardInfo(accountId, profileId) {
1397
1552
  return this.request(
1398
1553
  "POST",
1399
- `/account/${accountId}/business_profile/${profileId}/toggle_extended_card_info`
1554
+ `/account/${encodeURIComponent(accountId)}/business_profile/${encodeURIComponent(profileId)}/toggle_extended_card_info`
1400
1555
  );
1401
1556
  }
1402
1557
  /** Toggle connector agnostic MIT. `POST /account/{accountId}/business_profile/{profileId}/toggle_connector_agnostic_mit` */
1403
1558
  async toggleConnectorAgnosticMit(accountId, profileId) {
1404
1559
  return this.request(
1405
1560
  "POST",
1406
- `/account/${accountId}/business_profile/${profileId}/toggle_connector_agnostic_mit`
1561
+ `/account/${encodeURIComponent(accountId)}/business_profile/${encodeURIComponent(profileId)}/toggle_connector_agnostic_mit`
1407
1562
  );
1408
1563
  }
1409
1564
  };
@@ -1438,7 +1593,7 @@ var Projects = class {
1438
1593
  * @returns The project.
1439
1594
  */
1440
1595
  async retrieve(projectId) {
1441
- return this.request("GET", `/projects/${projectId}`);
1596
+ return this.request("GET", `/projects/${encodeURIComponent(projectId)}`);
1442
1597
  }
1443
1598
  /**
1444
1599
  * Update a project's details.
@@ -1448,7 +1603,7 @@ var Projects = class {
1448
1603
  * @returns The updated project.
1449
1604
  */
1450
1605
  async update(projectId, params) {
1451
- return this.request("PUT", `/projects/${projectId}`, { body: params });
1606
+ return this.request("PUT", `/projects/${encodeURIComponent(projectId)}`, { body: params });
1452
1607
  }
1453
1608
  /**
1454
1609
  * Delete a project.
@@ -1457,7 +1612,7 @@ var Projects = class {
1457
1612
  * @returns The deleted project object.
1458
1613
  */
1459
1614
  async delete(projectId) {
1460
- return this.request("DELETE", `/projects/${projectId}`);
1615
+ return this.request("DELETE", `/projects/${encodeURIComponent(projectId)}`);
1461
1616
  }
1462
1617
  /**
1463
1618
  * List all projects for a merchant.
@@ -1528,7 +1683,7 @@ var Refunds = class {
1528
1683
  * ```
1529
1684
  */
1530
1685
  async retrieve(refundId) {
1531
- return this.request("GET", `/refunds/${refundId}`);
1686
+ return this.request("GET", `/refunds/${encodeURIComponent(refundId)}`);
1532
1687
  }
1533
1688
  /**
1534
1689
  * Update the reason or metadata on an existing refund.
@@ -1538,7 +1693,7 @@ var Refunds = class {
1538
1693
  * @returns The updated refund.
1539
1694
  */
1540
1695
  async update(refundId, params) {
1541
- return this.request("POST", `/refunds/${refundId}`, { body: params });
1696
+ return this.request("POST", `/refunds/${encodeURIComponent(refundId)}`, { body: params });
1542
1697
  }
1543
1698
  /**
1544
1699
  * List refunds, optionally filtered by payment, status, or date range.
@@ -1572,7 +1727,9 @@ var Refunds = class {
1572
1727
  }
1573
1728
  /** Manually update refund status. `PUT /refunds/{refundId}/manual-update` */
1574
1729
  async manualUpdate(refundId, params) {
1575
- return this.request("PUT", `/refunds/${refundId}/manual-update`, { body: params });
1730
+ return this.request("PUT", `/refunds/${encodeURIComponent(refundId)}/manual-update`, {
1731
+ body: params
1732
+ });
1576
1733
  }
1577
1734
  };
1578
1735
 
@@ -1585,7 +1742,7 @@ var Relay = class {
1585
1742
  return this.request("POST", "/relay", { body: params });
1586
1743
  }
1587
1744
  async retrieve(relayId) {
1588
- return this.request("GET", `/relay/${relayId}`);
1745
+ return this.request("GET", `/relay/${encodeURIComponent(relayId)}`);
1589
1746
  }
1590
1747
  };
1591
1748
 
@@ -1619,7 +1776,7 @@ var Routing = class {
1619
1776
  * @returns The routing configuration.
1620
1777
  */
1621
1778
  async retrieve(algorithmId) {
1622
- return this.request("GET", `/routing/${algorithmId}`);
1779
+ return this.request("GET", `/routing/${encodeURIComponent(algorithmId)}`);
1623
1780
  }
1624
1781
  /**
1625
1782
  * Activate a routing algorithm, making it the active routing strategy for the shop.
@@ -1628,7 +1785,7 @@ var Routing = class {
1628
1785
  * @returns The activated routing configuration.
1629
1786
  */
1630
1787
  async activate(algorithmId) {
1631
- return this.request("POST", `/routing/${algorithmId}/activate`);
1788
+ return this.request("POST", `/routing/${encodeURIComponent(algorithmId)}/activate`);
1632
1789
  }
1633
1790
  /**
1634
1791
  * Deactivate the currently active routing algorithm (falls back to default routing).
@@ -1661,7 +1818,9 @@ var Routing = class {
1661
1818
  }
1662
1819
  /** Update default config for a profile. `POST /routing/default/profile/{profileId}` */
1663
1820
  async updateDefaultProfile(profileId, params) {
1664
- return this.request("POST", `/routing/default/profile/${profileId}`, { body: params });
1821
+ return this.request("POST", `/routing/default/profile/${encodeURIComponent(profileId)}`, {
1822
+ body: params
1823
+ });
1665
1824
  }
1666
1825
  /** List routing configs for profile. `GET /routing/list/profile` */
1667
1826
  async listForProfile() {
@@ -1728,7 +1887,11 @@ var ShopGateways = class {
1728
1887
  * @returns The created gateway connection.
1729
1888
  */
1730
1889
  async connect(merchantId, shopId, params) {
1731
- return this.request("POST", `/shops/${merchantId}/${shopId}/gateways`, { body: params });
1890
+ return this.request(
1891
+ "POST",
1892
+ `/shops/${encodeURIComponent(merchantId)}/${encodeURIComponent(shopId)}/gateways`,
1893
+ { body: params }
1894
+ );
1732
1895
  }
1733
1896
  /**
1734
1897
  * List all gateway connections for a shop.
@@ -1738,7 +1901,10 @@ var ShopGateways = class {
1738
1901
  * @returns Array of gateway connections.
1739
1902
  */
1740
1903
  async list(merchantId, shopId) {
1741
- return this.request("GET", `/shops/${merchantId}/${shopId}/gateways`);
1904
+ return this.request(
1905
+ "GET",
1906
+ `/shops/${encodeURIComponent(merchantId)}/${encodeURIComponent(shopId)}/gateways`
1907
+ );
1742
1908
  }
1743
1909
  /**
1744
1910
  * Disconnect a gateway from a shop.
@@ -1749,7 +1915,10 @@ var ShopGateways = class {
1749
1915
  * @returns The removed gateway connection.
1750
1916
  */
1751
1917
  async disconnect(merchantId, shopId, gatewayId) {
1752
- return this.request("DELETE", `/shops/${merchantId}/${shopId}/gateways/${gatewayId}`);
1918
+ return this.request(
1919
+ "DELETE",
1920
+ `/shops/${encodeURIComponent(merchantId)}/${encodeURIComponent(shopId)}/gateways/${encodeURIComponent(gatewayId)}`
1921
+ );
1753
1922
  }
1754
1923
  };
1755
1924
  var Shops = class {
@@ -1770,7 +1939,7 @@ var Shops = class {
1770
1939
  * ```
1771
1940
  */
1772
1941
  async create(merchantId, params) {
1773
- return this.request("POST", `/shops/${merchantId}`, { body: params });
1942
+ return this.request("POST", `/shops/${encodeURIComponent(merchantId)}`, { body: params });
1774
1943
  }
1775
1944
  /**
1776
1945
  * Retrieve a shop by its ID.
@@ -1780,7 +1949,10 @@ var Shops = class {
1780
1949
  * @returns The shop.
1781
1950
  */
1782
1951
  async retrieve(merchantId, shopId) {
1783
- return this.request("GET", `/shops/${merchantId}/${shopId}`);
1952
+ return this.request(
1953
+ "GET",
1954
+ `/shops/${encodeURIComponent(merchantId)}/${encodeURIComponent(shopId)}`
1955
+ );
1784
1956
  }
1785
1957
  /**
1786
1958
  * Update a shop's configuration.
@@ -1791,7 +1963,11 @@ var Shops = class {
1791
1963
  * @returns The updated shop.
1792
1964
  */
1793
1965
  async update(merchantId, shopId, params) {
1794
- return this.request("PUT", `/shops/${merchantId}/${shopId}`, { body: params });
1966
+ return this.request(
1967
+ "PUT",
1968
+ `/shops/${encodeURIComponent(merchantId)}/${encodeURIComponent(shopId)}`,
1969
+ { body: params }
1970
+ );
1795
1971
  }
1796
1972
  /**
1797
1973
  * Delete a shop.
@@ -1801,7 +1977,10 @@ var Shops = class {
1801
1977
  * @returns The deleted shop object.
1802
1978
  */
1803
1979
  async delete(merchantId, shopId) {
1804
- return this.request("DELETE", `/shops/${merchantId}/${shopId}`);
1980
+ return this.request(
1981
+ "DELETE",
1982
+ `/shops/${encodeURIComponent(merchantId)}/${encodeURIComponent(shopId)}`
1983
+ );
1805
1984
  }
1806
1985
  /**
1807
1986
  * List all shops under a merchant account.
@@ -1810,7 +1989,7 @@ var Shops = class {
1810
1989
  * @returns Array of shops.
1811
1990
  */
1812
1991
  async list(merchantId) {
1813
- return this.request("GET", `/shops/${merchantId}`);
1992
+ return this.request("GET", `/shops/${encodeURIComponent(merchantId)}`);
1814
1993
  }
1815
1994
  };
1816
1995
 
@@ -2068,11 +2247,11 @@ var Users = class {
2068
2247
  }
2069
2248
  /** Get role by ID. `GET /user/role/{roleId}` */
2070
2249
  async getRoleById(roleId) {
2071
- return this.request("GET", `/user/role/${roleId}`);
2250
+ return this.request("GET", `/user/role/${encodeURIComponent(roleId)}`);
2072
2251
  }
2073
2252
  /** Update role by ID. `PUT /user/role/{roleId}` */
2074
2253
  async updateRole(roleId, params) {
2075
- return this.request("PUT", `/user/role/${roleId}`, { body: params });
2254
+ return this.request("PUT", `/user/role/${encodeURIComponent(roleId)}`, { body: params });
2076
2255
  }
2077
2256
  };
2078
2257
 
@@ -2082,7 +2261,9 @@ var Verification = class {
2082
2261
  this.request = request;
2083
2262
  }
2084
2263
  async registerApplePayDomains(merchantId, params) {
2085
- return this.request("POST", `/verify/apple_pay/${merchantId}`, { body: params });
2264
+ return this.request("POST", `/verify/apple_pay/${encodeURIComponent(merchantId)}`, {
2265
+ body: params
2266
+ });
2086
2267
  }
2087
2268
  async getApplePayVerifiedDomains(params) {
2088
2269
  return this.request("GET", "/verify/applepay_verified_domains", {
@@ -2092,10 +2273,23 @@ var Verification = class {
2092
2273
  };
2093
2274
 
2094
2275
  // src/resources/webhooks.ts
2276
+ function hexToBytes(hex) {
2277
+ if (hex.length === 0 || hex.length % 2 !== 0) return null;
2278
+ const bytes = new Uint8Array(hex.length / 2);
2279
+ for (let i = 0; i < hex.length; i += 2) {
2280
+ const byte = Number.parseInt(hex.slice(i, i + 2), 16);
2281
+ if (Number.isNaN(byte)) return null;
2282
+ bytes[i / 2] = byte;
2283
+ }
2284
+ return bytes;
2285
+ }
2095
2286
  var Webhooks = {
2096
2287
  /**
2097
2288
  * Verify the signature of an incoming Delopay webhook and return the parsed event.
2098
2289
  *
2290
+ * Uses the Web Crypto API (`globalThis.crypto.subtle`), so it runs unchanged in
2291
+ * Node 18+, modern browsers, Deno, Bun, and edge runtimes (Cloudflare Workers, Vercel Edge).
2292
+ *
2099
2293
  * This method is available as a static property on the `Delopay` class
2100
2294
  * (`Delopay.webhooks.verify`) and does not require a client instance.
2101
2295
  *
@@ -2103,14 +2297,14 @@ var Webhooks = {
2103
2297
  * @param signatureHeader - The value of the `delopay-signature` HTTP header.
2104
2298
  * @param secret - Your webhook signing secret from the Delopay dashboard.
2105
2299
  * @param options - Optional verification settings (replay tolerance).
2106
- * @returns The parsed webhook event.
2300
+ * @returns Promise that resolves to the parsed webhook event.
2107
2301
  * @throws {Error} When the signature is invalid, the timestamp is missing, or the event is too old.
2108
2302
  *
2109
2303
  * @example
2110
2304
  * ```typescript
2111
2305
  * // Express example
2112
- * app.post('/webhook', express.raw({ type: 'application/json' }), (req, res) => {
2113
- * const event = Delopay.webhooks.verify(
2306
+ * app.post('/webhook', express.raw({ type: 'application/json' }), async (req, res) => {
2307
+ * const event = await Delopay.webhooks.verify(
2114
2308
  * req.body.toString(),
2115
2309
  * req.headers['delopay-signature'] as string,
2116
2310
  * process.env.DELOPAY_WEBHOOK_SECRET!,
@@ -2120,7 +2314,7 @@ var Webhooks = {
2120
2314
  * });
2121
2315
  * ```
2122
2316
  */
2123
- verify(rawBody, signatureHeader, secret, options) {
2317
+ async verify(rawBody, signatureHeader, secret, options) {
2124
2318
  const tolerance = options?.tolerance ?? 300;
2125
2319
  const parts = signatureHeader.split(",");
2126
2320
  const timestampPart = parts.find((p) => p.startsWith("t="));
@@ -2128,19 +2322,29 @@ var Webhooks = {
2128
2322
  if (!timestampPart || !signaturePart) {
2129
2323
  throw new Error("Invalid webhook signature format");
2130
2324
  }
2131
- const timestamp = parseInt(timestampPart.slice(2), 10);
2325
+ const timestamp = Number.parseInt(timestampPart.slice(2), 10);
2132
2326
  if (!Number.isFinite(timestamp)) {
2133
2327
  throw new Error("Invalid webhook timestamp");
2134
2328
  }
2135
- const signature = signaturePart.slice(3);
2136
- const crypto = require("crypto");
2137
- const signedPayload = `${timestamp}.${rawBody}`;
2138
- const expected = crypto.createHmac("sha256", secret).update(signedPayload).digest("hex");
2139
- const sigBuf = Buffer.from(signature);
2140
- const expBuf = Buffer.from(expected);
2141
- const lengthsMatch = sigBuf.length === expBuf.length;
2142
- const paddedSig = lengthsMatch ? sigBuf : Buffer.alloc(expBuf.length, 0);
2143
- const signaturesMatch = lengthsMatch && crypto.timingSafeEqual(paddedSig, expBuf);
2329
+ const signatureHex = signaturePart.slice(3);
2330
+ const signatureBytes = hexToBytes(signatureHex);
2331
+ const subtle = globalThis.crypto?.subtle;
2332
+ if (!subtle) {
2333
+ throw new Error(
2334
+ "Web Crypto unavailable: Delopay.webhooks.verify requires globalThis.crypto.subtle (Node 18+, modern browsers, Workers, Deno)"
2335
+ );
2336
+ }
2337
+ const encoder = new TextEncoder();
2338
+ const asBufferSource = (bytes) => bytes;
2339
+ const key = await subtle.importKey(
2340
+ "raw",
2341
+ asBufferSource(encoder.encode(secret)),
2342
+ { name: "HMAC", hash: "SHA-256" },
2343
+ false,
2344
+ ["verify"]
2345
+ );
2346
+ const signedPayload = asBufferSource(encoder.encode(`${timestamp}.${rawBody}`));
2347
+ const signaturesMatch = signatureBytes !== null && await subtle.verify("HMAC", key, asBufferSource(signatureBytes), signedPayload);
2144
2348
  if (!signaturesMatch) {
2145
2349
  throw new Error("Invalid webhook signature");
2146
2350
  }
@@ -2161,22 +2365,30 @@ var AnalyticsDomain = class {
2161
2365
  /** Get metrics. `POST /analytics/v1/metrics/{domain}` */
2162
2366
  async metrics(params, scope) {
2163
2367
  const prefix = scope ? `/analytics/v1/${scope}` : "/analytics/v1";
2164
- return this.request("POST", `${prefix}/metrics/${this.domain}`, { body: params });
2368
+ return this.request("POST", `${prefix}/metrics/${encodeURIComponent(this.domain)}`, {
2369
+ body: [params]
2370
+ });
2165
2371
  }
2166
2372
  /** Get filters. `POST /analytics/v1/filters/{domain}` */
2167
2373
  async filters(params, scope) {
2168
2374
  const prefix = scope ? `/analytics/v1/${scope}` : "/analytics/v1";
2169
- return this.request("POST", `${prefix}/filters/${this.domain}`, { body: params });
2375
+ return this.request("POST", `${prefix}/filters/${encodeURIComponent(this.domain)}`, {
2376
+ body: params
2377
+ });
2170
2378
  }
2171
2379
  /** Generate report. `POST /analytics/v1/report/{domain}` */
2172
2380
  async report(params, scope) {
2173
2381
  const prefix = scope ? `/analytics/v1/${scope}` : "/analytics/v1";
2174
- return this.request("POST", `${prefix}/report/${this.domain}`, { body: params });
2382
+ return this.request("POST", `${prefix}/report/${encodeURIComponent(this.domain)}`, {
2383
+ body: params
2384
+ });
2175
2385
  }
2176
2386
  /** Sankey chart data. `POST /analytics/v1/metrics/{domain}/sankey` */
2177
2387
  async sankey(params, scope) {
2178
2388
  const prefix = scope ? `/analytics/v1/${scope}` : "/analytics/v1";
2179
- return this.request("POST", `${prefix}/metrics/${this.domain}/sankey`, { body: params });
2389
+ return this.request("POST", `${prefix}/metrics/${encodeURIComponent(this.domain)}/sankey`, {
2390
+ body: params
2391
+ });
2180
2392
  }
2181
2393
  };
2182
2394
  var Analytics = class {
@@ -2197,11 +2409,13 @@ var Analytics = class {
2197
2409
  }
2198
2410
  /** Domain-specific search. `POST /analytics/v1/search/{domain}` */
2199
2411
  async searchDomain(domain, params) {
2200
- return this.request("POST", `/analytics/v1/search/${domain}`, { body: params });
2412
+ return this.request("POST", `/analytics/v1/search/${encodeURIComponent(domain)}`, {
2413
+ body: params
2414
+ });
2201
2415
  }
2202
2416
  /** Get analytics info. `GET /analytics/v1/{domain}/info` */
2203
2417
  async getInfo(domain) {
2204
- return this.request("GET", `/analytics/v1/${domain}/info`);
2418
+ return this.request("GET", `/analytics/v1/${encodeURIComponent(domain)}/info`);
2205
2419
  }
2206
2420
  /** Get API event logs. `GET /analytics/v1/api_event_logs` */
2207
2421
  async apiEventLogs(params) {
@@ -2247,7 +2461,7 @@ var Cache = class {
2247
2461
  }
2248
2462
  /** Invalidate a cache entry by key. `POST /cache/invalidate/{key}` */
2249
2463
  async invalidate(key) {
2250
- return this.request("POST", `/cache/invalidate/${key}`);
2464
+ return this.request("POST", `/cache/invalidate/${encodeURIComponent(key)}`);
2251
2465
  }
2252
2466
  };
2253
2467
 
@@ -2266,7 +2480,7 @@ var Cards = class {
2266
2480
  }
2267
2481
  /** Retrieve card info by BIN. `GET /cards/{bin}` */
2268
2482
  async retrieve(bin) {
2269
- return this.request("GET", `/cards/${bin}`);
2483
+ return this.request("GET", `/cards/${encodeURIComponent(bin)}`);
2270
2484
  }
2271
2485
  };
2272
2486
 
@@ -2281,15 +2495,15 @@ var Configs = class {
2281
2495
  }
2282
2496
  /** Retrieve a config by key. `GET /configs/{key}` */
2283
2497
  async retrieve(key) {
2284
- return this.request("GET", `/configs/${key}`);
2498
+ return this.request("GET", `/configs/${encodeURIComponent(key)}`);
2285
2499
  }
2286
2500
  /** Update a config. `PUT /configs/{key}` */
2287
2501
  async update(key, params) {
2288
- return this.request("PUT", `/configs/${key}`, { body: params });
2502
+ return this.request("PUT", `/configs/${encodeURIComponent(key)}`, { body: params });
2289
2503
  }
2290
2504
  /** Delete a config. `DELETE /configs/{key}` */
2291
2505
  async delete(key) {
2292
- return this.request("DELETE", `/configs/${key}`);
2506
+ return this.request("DELETE", `/configs/${encodeURIComponent(key)}`);
2293
2507
  }
2294
2508
  };
2295
2509
 
@@ -2326,11 +2540,11 @@ var Files = class {
2326
2540
  }
2327
2541
  /** Retrieve/download a file. `GET /files/{fileId}` */
2328
2542
  async retrieve(fileId) {
2329
- return this.request("GET", `/files/${fileId}`);
2543
+ return this.request("GET", `/files/${encodeURIComponent(fileId)}`);
2330
2544
  }
2331
2545
  /** Delete a file. `DELETE /files/{fileId}` */
2332
2546
  async delete(fileId) {
2333
- return this.request("DELETE", `/files/${fileId}`);
2547
+ return this.request("DELETE", `/files/${encodeURIComponent(fileId)}`);
2334
2548
  }
2335
2549
  };
2336
2550
 
@@ -2360,15 +2574,15 @@ var Regions = class {
2360
2574
  }
2361
2575
  /** Retrieve a region by ID. `GET /regions/{regionId}` */
2362
2576
  async retrieve(regionId) {
2363
- return this.request("GET", `/regions/${regionId}`);
2577
+ return this.request("GET", `/regions/${encodeURIComponent(regionId)}`);
2364
2578
  }
2365
2579
  /** Update a region. `PUT /regions/{regionId}` */
2366
2580
  async update(regionId, params) {
2367
- return this.request("PUT", `/regions/${regionId}`, { body: params });
2581
+ return this.request("PUT", `/regions/${encodeURIComponent(regionId)}`, { body: params });
2368
2582
  }
2369
2583
  /** Delete a region. `DELETE /regions/{regionId}` */
2370
2584
  async delete(regionId) {
2371
- return this.request("DELETE", `/regions/${regionId}`);
2585
+ return this.request("DELETE", `/regions/${encodeURIComponent(regionId)}`);
2372
2586
  }
2373
2587
  /** List all regions. `GET /regions/list` */
2374
2588
  async list() {
@@ -2391,17 +2605,19 @@ var Subscriptions = class {
2391
2605
  }
2392
2606
  /** Retrieve a subscription by ID. `GET /subscriptions/{subscriptionId}` */
2393
2607
  async retrieve(subscriptionId) {
2394
- return this.request("GET", `/subscriptions/${subscriptionId}`);
2608
+ return this.request("GET", `/subscriptions/${encodeURIComponent(subscriptionId)}`);
2395
2609
  }
2396
2610
  /** Confirm a subscription. `POST /subscriptions/{subscriptionId}/confirm` */
2397
2611
  async confirm(subscriptionId, params) {
2398
- return this.request("POST", `/subscriptions/${subscriptionId}/confirm`, {
2612
+ return this.request("POST", `/subscriptions/${encodeURIComponent(subscriptionId)}/confirm`, {
2399
2613
  body: params
2400
2614
  });
2401
2615
  }
2402
2616
  /** Update a subscription. `PUT /subscriptions/{subscriptionId}/update` */
2403
2617
  async update(subscriptionId, params) {
2404
- return this.request("PUT", `/subscriptions/${subscriptionId}/update`, { body: params });
2618
+ return this.request("PUT", `/subscriptions/${encodeURIComponent(subscriptionId)}/update`, {
2619
+ body: params
2620
+ });
2405
2621
  }
2406
2622
  /** List subscriptions. `GET /subscriptions/list` */
2407
2623
  async list(params) {
@@ -2419,21 +2635,95 @@ var Subscriptions = class {
2419
2635
  }
2420
2636
  /** Pause a subscription. `POST /subscriptions/{subscriptionId}/pause` */
2421
2637
  async pause(subscriptionId) {
2422
- return this.request("POST", `/subscriptions/${subscriptionId}/pause`);
2638
+ return this.request("POST", `/subscriptions/${encodeURIComponent(subscriptionId)}/pause`);
2423
2639
  }
2424
2640
  /** Resume a subscription. `POST /subscriptions/{subscriptionId}/resume` */
2425
2641
  async resume(subscriptionId) {
2426
- return this.request("POST", `/subscriptions/${subscriptionId}/resume`);
2642
+ return this.request("POST", `/subscriptions/${encodeURIComponent(subscriptionId)}/resume`);
2427
2643
  }
2428
2644
  /** Cancel a subscription. `POST /subscriptions/{subscriptionId}/cancel` */
2429
2645
  async cancel(subscriptionId) {
2430
- return this.request("POST", `/subscriptions/${subscriptionId}/cancel`);
2646
+ return this.request("POST", `/subscriptions/${encodeURIComponent(subscriptionId)}/cancel`);
2431
2647
  }
2432
2648
  };
2433
2649
 
2434
2650
  // src/client.ts
2435
2651
  var PRODUCTION_URL = "https://api.delopay.net";
2436
2652
  var SANDBOX_URL = "https://sandbox.delopay.net";
2653
+ var MAX_RAW_BODY_BYTES = 2048;
2654
+ var MAX_RETRY_AFTER_MS = 3e4;
2655
+ function parseRetryAfter(header) {
2656
+ if (!header) return null;
2657
+ const trimmed = header.trim();
2658
+ const seconds = Number(trimmed);
2659
+ if (Number.isFinite(seconds) && seconds >= 0) {
2660
+ return Math.min(seconds * 1e3, MAX_RETRY_AFTER_MS);
2661
+ }
2662
+ const date = Date.parse(trimmed);
2663
+ if (Number.isFinite(date)) {
2664
+ const delta = date - Date.now();
2665
+ return delta > 0 ? Math.min(delta, MAX_RETRY_AFTER_MS) : 0;
2666
+ }
2667
+ return null;
2668
+ }
2669
+ function truncateRawBody(raw) {
2670
+ if (!raw) return void 0;
2671
+ return raw.length > MAX_RAW_BODY_BYTES ? raw.slice(0, MAX_RAW_BODY_BYTES) + "\u2026" : raw;
2672
+ }
2673
+ function findIdempotencyKey(headers) {
2674
+ for (const [k, v] of Object.entries(headers)) {
2675
+ if (k.toLowerCase() === "idempotency-key") return v;
2676
+ }
2677
+ return void 0;
2678
+ }
2679
+ function noop() {
2680
+ }
2681
+ function combineSignals(signals) {
2682
+ const controller = new AbortController();
2683
+ const listeners = [];
2684
+ const dispose = () => {
2685
+ for (const { signal, handler } of listeners) {
2686
+ signal.removeEventListener("abort", handler);
2687
+ }
2688
+ listeners.length = 0;
2689
+ };
2690
+ for (const signal of signals) {
2691
+ if (signal.aborted) {
2692
+ controller.abort(signal.reason);
2693
+ dispose();
2694
+ return { signal: controller.signal, dispose: noop };
2695
+ }
2696
+ const handler = () => {
2697
+ controller.abort(signal.reason);
2698
+ dispose();
2699
+ };
2700
+ signal.addEventListener("abort", handler, { once: true });
2701
+ listeners.push({ signal, handler });
2702
+ }
2703
+ return { signal: controller.signal, dispose };
2704
+ }
2705
+ var SENSITIVE_QUERY_KEYS = /* @__PURE__ */ new Set([
2706
+ "client_secret",
2707
+ "ephemeral_key",
2708
+ "api_key",
2709
+ "publishable_key"
2710
+ ]);
2711
+ function redactUrlForLogging(url) {
2712
+ const qIdx = url.indexOf("?");
2713
+ if (qIdx === -1) return url;
2714
+ const base = url.slice(0, qIdx);
2715
+ const query = url.slice(qIdx + 1);
2716
+ const parts = query.split("&").map((pair) => {
2717
+ const eqIdx = pair.indexOf("=");
2718
+ if (eqIdx === -1) return pair;
2719
+ const key = pair.slice(0, eqIdx);
2720
+ if (SENSITIVE_QUERY_KEYS.has(decodeURIComponent(key).toLowerCase())) {
2721
+ return `${key}=REDACTED`;
2722
+ }
2723
+ return pair;
2724
+ });
2725
+ return `${base}?${parts.join("&")}`;
2726
+ }
2437
2727
  var Delopay = class {
2438
2728
  /**
2439
2729
  * Create a new Delopay client.
@@ -2447,6 +2737,7 @@ var Delopay = class {
2447
2737
  this.timeout = options?.timeout ?? 3e4;
2448
2738
  this.maxRetries = options?.maxRetries ?? 2;
2449
2739
  this.debug = options?.debug ?? false;
2740
+ if (options?.logger !== void 0) this.logger = options.logger;
2450
2741
  if (options?.baseUrl !== void 0) {
2451
2742
  this.baseUrl = options.baseUrl;
2452
2743
  } else if (options?.sandbox) {
@@ -2532,7 +2823,12 @@ var Delopay = class {
2532
2823
  if (options?.query) {
2533
2824
  const params = new URLSearchParams();
2534
2825
  for (const [key, value] of Object.entries(options.query)) {
2535
- if (value !== void 0) {
2826
+ if (value === void 0 || value === null) continue;
2827
+ if (Array.isArray(value)) {
2828
+ for (const v of value) {
2829
+ if (v !== void 0 && v !== null) params.append(key, String(v));
2830
+ }
2831
+ } else {
2536
2832
  params.set(key, String(value));
2537
2833
  }
2538
2834
  }
@@ -2548,46 +2844,94 @@ var Delopay = class {
2548
2844
  if (options?.body) {
2549
2845
  headers["Content-Type"] = "application/json";
2550
2846
  }
2551
- const isRetryable = method === "GET" || method === "DELETE" || "Idempotency-Key" in headers;
2847
+ const idempotencyKey = findIdempotencyKey(headers)?.trim();
2848
+ const isRetryable = method === "GET" || method === "DELETE" || idempotencyKey !== void 0 && idempotencyKey !== "";
2849
+ const serializedBody = options?.body ? JSON.stringify(options.body) : void 0;
2850
+ const callerSignal = options?.signal;
2851
+ if (callerSignal?.aborted) {
2852
+ throw new DelopayError("Request aborted", {
2853
+ status: 0,
2854
+ code: "ABORTED",
2855
+ type: "abort_error"
2856
+ });
2857
+ }
2858
+ const timeoutMs = options?.timeout ?? this.timeout;
2552
2859
  let lastError;
2860
+ let retryAfterOverrideMs = null;
2861
+ const safeUrl = () => redactUrlForLogging(url);
2862
+ const emit = (event, data) => {
2863
+ if (!this.debug) return;
2864
+ if (this.logger) {
2865
+ this.logger(event, data);
2866
+ return;
2867
+ }
2868
+ if (event === "request")
2869
+ console.log(`[delopay] ${data.method} ${data.url}`);
2870
+ else if (event === "response")
2871
+ console.log(
2872
+ `[delopay] ${data.status} ${data.method} ${data.path}`
2873
+ );
2874
+ else
2875
+ console.log(
2876
+ `[delopay] retry ${data.attempt}/${data.maxRetries} ${data.method} ${data.path}`
2877
+ );
2878
+ };
2553
2879
  for (let attempt = 0; attempt <= this.maxRetries; attempt++) {
2554
2880
  if (attempt > 0) {
2555
- const delay = Math.min(500 * 2 ** (attempt - 1), 5e3);
2881
+ const base = Math.min(500 * 2 ** (attempt - 1), 5e3);
2882
+ const jittered = Math.random() * base;
2883
+ const delay = Math.max(retryAfterOverrideMs ?? 0, jittered);
2884
+ retryAfterOverrideMs = null;
2556
2885
  await new Promise((resolve) => setTimeout(resolve, delay));
2557
- if (this.debug) {
2558
- console.log(`[delopay] retry ${attempt}/${this.maxRetries} ${method} ${path}`);
2559
- }
2886
+ emit("retry", { attempt, maxRetries: this.maxRetries, method, path });
2560
2887
  }
2561
- const controller = new AbortController();
2562
- const timeoutId = setTimeout(() => controller.abort(), this.timeout);
2888
+ const timeoutCtrl = new AbortController();
2889
+ const timeoutId = setTimeout(() => timeoutCtrl.abort(), timeoutMs);
2890
+ const combined = combineSignals(
2891
+ callerSignal ? [timeoutCtrl.signal, callerSignal] : [timeoutCtrl.signal]
2892
+ );
2563
2893
  try {
2564
- if (this.debug) {
2565
- console.log(`[delopay] ${method} ${url}`);
2566
- }
2894
+ emit("request", { method, url: safeUrl(), path });
2567
2895
  const response = await fetch(url, {
2568
2896
  method,
2569
2897
  headers,
2570
- body: options?.body ? JSON.stringify(options.body) : void 0,
2571
- signal: controller.signal
2898
+ body: serializedBody,
2899
+ signal: combined.signal
2572
2900
  });
2573
- if (this.debug) {
2574
- console.log(`[delopay] ${response.status} ${method} ${path}`);
2575
- }
2901
+ const requestId = response.headers?.get("x-request-id") ?? response.headers?.get("x-trace-id") ?? void 0;
2902
+ emit("response", { status: response.status, method, path, requestId });
2576
2903
  if (!response.ok) {
2577
- const body = await response.json().catch(() => ({}));
2578
- const err = body.error ?? body;
2904
+ const rawBody = await response.text().catch(() => "");
2905
+ let parsed = {};
2906
+ if (rawBody) {
2907
+ try {
2908
+ parsed = JSON.parse(rawBody);
2909
+ } catch {
2910
+ }
2911
+ }
2912
+ const err = parsed.error ?? parsed;
2579
2913
  const message = err.message ?? `Request failed with status ${response.status}`;
2580
2914
  const code = err.code ?? "";
2581
2915
  const type = err.error_type ?? err.type ?? "";
2916
+ const truncatedRaw = truncateRawBody(rawBody);
2582
2917
  if (response.status === 401) {
2583
- throw new DelopayAuthenticationError(message);
2918
+ throw new DelopayAuthenticationError(message, {
2919
+ requestId,
2920
+ rawBody: truncatedRaw
2921
+ });
2584
2922
  }
2585
2923
  const error = new DelopayError(message, {
2586
2924
  status: response.status,
2587
2925
  code,
2588
- type
2926
+ type,
2927
+ requestId,
2928
+ rawBody: truncatedRaw
2589
2929
  });
2590
- if (response.status >= 500 && isRetryable && attempt < this.maxRetries) {
2930
+ const isTransientStatus = response.status >= 500 || response.status === 429;
2931
+ if (isTransientStatus && isRetryable && attempt < this.maxRetries) {
2932
+ if (response.status === 429) {
2933
+ retryAfterOverrideMs = parseRetryAfter(response.headers?.get("retry-after") ?? null);
2934
+ }
2591
2935
  lastError = error;
2592
2936
  continue;
2593
2937
  }
@@ -2599,7 +2943,14 @@ var Delopay = class {
2599
2943
  if (err instanceof DelopayError || err instanceof DelopayAuthenticationError) {
2600
2944
  throw err;
2601
2945
  }
2602
- if (err instanceof DOMException && err.name === "AbortError") {
2946
+ if (err instanceof Error && err.name === "AbortError") {
2947
+ if (callerSignal?.aborted) {
2948
+ throw new DelopayError("Request aborted", {
2949
+ status: 0,
2950
+ code: "ABORTED",
2951
+ type: "abort_error"
2952
+ });
2953
+ }
2603
2954
  lastError = new DelopayError("Request timed out", {
2604
2955
  status: 0,
2605
2956
  code: "TIMEOUT",
@@ -2620,6 +2971,7 @@ var Delopay = class {
2620
2971
  throw err;
2621
2972
  } finally {
2622
2973
  clearTimeout(timeoutId);
2974
+ combined.dispose();
2623
2975
  }
2624
2976
  }
2625
2977
  throw lastError;