@billkit-eu/sdk 0.6.0 → 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/CHANGELOG.md +38 -1
- package/README.md +3 -1
- package/dist/index.cjs +206 -79
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +305 -29
- package/dist/index.d.ts +305 -29
- package/dist/index.js +206 -79
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/client.ts +3 -0
- package/src/errors.ts +10 -1
- package/src/index.ts +9 -0
- package/src/resources.ts +417 -99
- package/src/transport.ts +21 -10
- package/src/version.ts +1 -1
package/dist/index.js
CHANGED
|
@@ -24,6 +24,9 @@ async function* paginate(listFn, options = {}) {
|
|
|
24
24
|
}
|
|
25
25
|
|
|
26
26
|
// src/resources.ts
|
|
27
|
+
function p(id) {
|
|
28
|
+
return encodeURIComponent(id);
|
|
29
|
+
}
|
|
27
30
|
function dropUndefined(obj) {
|
|
28
31
|
const out = {};
|
|
29
32
|
for (const [k, v] of Object.entries(obj)) {
|
|
@@ -56,6 +59,12 @@ var BaseResource = class {
|
|
|
56
59
|
this.t = t;
|
|
57
60
|
}
|
|
58
61
|
t;
|
|
62
|
+
/**
|
|
63
|
+
* `query` is a plain object rather than an index-signature type: TypeScript
|
|
64
|
+
* only gives an implicit index signature to type *aliases*, so a closed
|
|
65
|
+
* `*ListParams` interface would otherwise need a cast at every call site.
|
|
66
|
+
* The transport prunes `undefined`/`null` and joins arrays with commas.
|
|
67
|
+
*/
|
|
59
68
|
get(path, query) {
|
|
60
69
|
return this.t.request({ method: "GET", path, query });
|
|
61
70
|
}
|
|
@@ -96,10 +105,10 @@ var Customers = class extends BaseResource {
|
|
|
96
105
|
return this.post("/v1/customers", params);
|
|
97
106
|
}
|
|
98
107
|
retrieve(id) {
|
|
99
|
-
return this.get(`/v1/customers/${id}`);
|
|
108
|
+
return this.get(`/v1/customers/${p(id)}`);
|
|
100
109
|
}
|
|
101
110
|
update(id, params = {}) {
|
|
102
|
-
return this.post(`/v1/customers/${id}`, params);
|
|
111
|
+
return this.post(`/v1/customers/${p(id)}`, params);
|
|
103
112
|
}
|
|
104
113
|
/**
|
|
105
114
|
* Delete a customer. Resolves to `{ id, object: "customer", deleted:
|
|
@@ -112,7 +121,7 @@ var Customers = class extends BaseResource {
|
|
|
112
121
|
* charge them.
|
|
113
122
|
*/
|
|
114
123
|
delete(id, params = {}) {
|
|
115
|
-
return this.del(`/v1/customers/${id}`, params);
|
|
124
|
+
return this.del(`/v1/customers/${p(id)}`, params);
|
|
116
125
|
}
|
|
117
126
|
/**
|
|
118
127
|
* List customers, newest first.
|
|
@@ -129,7 +138,7 @@ var Customers = class extends BaseResource {
|
|
|
129
138
|
}
|
|
130
139
|
/** Walk every page of `list()` and yield each customer. */
|
|
131
140
|
iter(options = {}) {
|
|
132
|
-
return paginate((
|
|
141
|
+
return paginate((page) => this.get("/v1/customers", page), { pageSize: options.pageSize });
|
|
133
142
|
}
|
|
134
143
|
/**
|
|
135
144
|
* Attach or replace the customer's VAT number; triggers server-side
|
|
@@ -137,7 +146,7 @@ var Customers = class extends BaseResource {
|
|
|
137
146
|
* reflecting whether VIES confirmed the number.
|
|
138
147
|
*/
|
|
139
148
|
setVatNumber(id, params) {
|
|
140
|
-
return this.post(`/v1/customers/${id}/vat_number`, params);
|
|
149
|
+
return this.post(`/v1/customers/${p(id)}/vat_number`, params);
|
|
141
150
|
}
|
|
142
151
|
/**
|
|
143
152
|
* Hard-purge a customer's PII for GDPR erasure. Distinct from
|
|
@@ -149,7 +158,7 @@ var Customers = class extends BaseResource {
|
|
|
149
158
|
*/
|
|
150
159
|
purge(id, params = {}) {
|
|
151
160
|
const { confirmed = true, idempotencyKey } = params;
|
|
152
|
-
return this.postFixed(`/v1/customers/${id}/purge`, { confirmed }, { idempotencyKey });
|
|
161
|
+
return this.postFixed(`/v1/customers/${p(id)}/purge`, { confirmed }, { idempotencyKey });
|
|
153
162
|
}
|
|
154
163
|
};
|
|
155
164
|
var Products = class extends BaseResource {
|
|
@@ -157,8 +166,12 @@ var Products = class extends BaseResource {
|
|
|
157
166
|
create(params) {
|
|
158
167
|
return this.post("/v1/products", params);
|
|
159
168
|
}
|
|
160
|
-
|
|
161
|
-
|
|
169
|
+
/**
|
|
170
|
+
* Expandable: `prices` (every price on the product), `stats`, and
|
|
171
|
+
* `default_price` (the price `default_price_id` names).
|
|
172
|
+
*/
|
|
173
|
+
retrieve(id, options = {}) {
|
|
174
|
+
return this.get(`/v1/products/${p(id)}`, options);
|
|
162
175
|
}
|
|
163
176
|
/**
|
|
164
177
|
* Patch mutable Product fields, or archive it with `active: false`.
|
|
@@ -170,13 +183,13 @@ var Products = class extends BaseResource {
|
|
|
170
183
|
* `active: true` un-archives.
|
|
171
184
|
*/
|
|
172
185
|
update(id, params) {
|
|
173
|
-
return this.post(`/v1/products/${id}`, params);
|
|
186
|
+
return this.post(`/v1/products/${p(id)}`, params);
|
|
174
187
|
}
|
|
175
188
|
list(params = {}) {
|
|
176
189
|
return this.get("/v1/products", params);
|
|
177
190
|
}
|
|
178
191
|
iter(options = {}) {
|
|
179
|
-
return paginate((
|
|
192
|
+
return paginate((page) => this.get("/v1/products", page), { pageSize: options.pageSize });
|
|
180
193
|
}
|
|
181
194
|
};
|
|
182
195
|
var Prices = class extends BaseResource {
|
|
@@ -199,7 +212,7 @@ var Prices = class extends BaseResource {
|
|
|
199
212
|
return this.post("/v1/prices", assertPriceRatesAreStrings(params));
|
|
200
213
|
}
|
|
201
214
|
retrieve(id) {
|
|
202
|
-
return this.get(`/v1/prices/${id}`);
|
|
215
|
+
return this.get(`/v1/prices/${p(id)}`);
|
|
203
216
|
}
|
|
204
217
|
/**
|
|
205
218
|
* Archive a Price so it stops selling, or put it back on sale.
|
|
@@ -222,14 +235,14 @@ var Prices = class extends BaseResource {
|
|
|
222
235
|
* `price.archived`; putting one back emits `price.updated`.
|
|
223
236
|
*/
|
|
224
237
|
update(id, params) {
|
|
225
|
-
return this.post(`/v1/prices/${id}`, params);
|
|
238
|
+
return this.post(`/v1/prices/${p(id)}`, params);
|
|
226
239
|
}
|
|
227
240
|
list(params = {}) {
|
|
228
241
|
return this.get("/v1/prices", params);
|
|
229
242
|
}
|
|
230
243
|
iter(options = {}) {
|
|
231
244
|
const filter = options.product_id === void 0 ? {} : { product_id: options.product_id };
|
|
232
|
-
return paginate((
|
|
245
|
+
return paginate((page) => this.get("/v1/prices", { ...filter, ...page }), {
|
|
233
246
|
pageSize: options.pageSize
|
|
234
247
|
});
|
|
235
248
|
}
|
|
@@ -239,7 +252,7 @@ var CheckoutSessions = class extends BaseResource {
|
|
|
239
252
|
return this.post("/v1/checkout/sessions", params);
|
|
240
253
|
}
|
|
241
254
|
retrieve(id) {
|
|
242
|
-
return this.get(`/v1/checkout/sessions/${id}`);
|
|
255
|
+
return this.get(`/v1/checkout/sessions/${p(id)}`);
|
|
243
256
|
}
|
|
244
257
|
};
|
|
245
258
|
var OneShotPayments = class extends BaseResource {
|
|
@@ -248,12 +261,13 @@ var OneShotPayments = class extends BaseResource {
|
|
|
248
261
|
return this.post("/v1/checkout/one_shot", params);
|
|
249
262
|
}
|
|
250
263
|
retrieve(id) {
|
|
251
|
-
return this.get(`/v1/checkout/one_shot/${id}`);
|
|
264
|
+
return this.get(`/v1/checkout/one_shot/${p(id)}`);
|
|
252
265
|
}
|
|
253
266
|
};
|
|
254
267
|
var Subscriptions = class extends BaseResource {
|
|
255
|
-
|
|
256
|
-
|
|
268
|
+
/** Expandable: `customer`, `price`, `refund_eligibility`. */
|
|
269
|
+
retrieve(id, options = {}) {
|
|
270
|
+
return this.get(`/v1/subscriptions/${p(id)}`, options);
|
|
257
271
|
}
|
|
258
272
|
/**
|
|
259
273
|
* List subscriptions, newest first, optionally filtered.
|
|
@@ -271,16 +285,16 @@ var Subscriptions = class extends BaseResource {
|
|
|
271
285
|
*/
|
|
272
286
|
iter(options = {}) {
|
|
273
287
|
const { pageSize, ...filter } = options;
|
|
274
|
-
return paginate((
|
|
288
|
+
return paginate((page) => this.get("/v1/subscriptions", { ...filter, ...page }), { pageSize });
|
|
275
289
|
}
|
|
276
290
|
cancel(id, params = {}) {
|
|
277
|
-
return this.postEmpty(`/v1/subscriptions/${id}/cancel`, params);
|
|
291
|
+
return this.postEmpty(`/v1/subscriptions/${p(id)}/cancel`, params);
|
|
278
292
|
}
|
|
279
293
|
pause(id, params = {}) {
|
|
280
|
-
return this.postEmpty(`/v1/subscriptions/${id}/pause`, params);
|
|
294
|
+
return this.postEmpty(`/v1/subscriptions/${p(id)}/pause`, params);
|
|
281
295
|
}
|
|
282
296
|
resume(id, params = {}) {
|
|
283
|
-
return this.postEmpty(`/v1/subscriptions/${id}/resume`, params);
|
|
297
|
+
return this.postEmpty(`/v1/subscriptions/${p(id)}/resume`, params);
|
|
284
298
|
}
|
|
285
299
|
/**
|
|
286
300
|
* Reactivate a canceled-but-still-in-period subscription.
|
|
@@ -291,23 +305,23 @@ var Subscriptions = class extends BaseResource {
|
|
|
291
305
|
* Returns `409` if the period has already elapsed.
|
|
292
306
|
*/
|
|
293
307
|
reactivate(id, params = {}) {
|
|
294
|
-
return this.postEmpty(`/v1/subscriptions/${id}/reactivate`, params);
|
|
308
|
+
return this.postEmpty(`/v1/subscriptions/${p(id)}/reactivate`, params);
|
|
295
309
|
}
|
|
296
310
|
previewUpdate(id, params) {
|
|
297
|
-
return this.postFixed(`/v1/subscriptions/${id}/preview_update`, {
|
|
311
|
+
return this.postFixed(`/v1/subscriptions/${p(id)}/preview_update`, {
|
|
298
312
|
target_price_id: params.target_price_id
|
|
299
313
|
});
|
|
300
314
|
}
|
|
301
315
|
update(id, params) {
|
|
302
316
|
return this.postFixed(
|
|
303
|
-
`/v1/subscriptions/${id}/update`,
|
|
317
|
+
`/v1/subscriptions/${p(id)}/update`,
|
|
304
318
|
{ target_price_id: params.target_price_id },
|
|
305
319
|
{ idempotencyKey: params.idempotencyKey }
|
|
306
320
|
);
|
|
307
321
|
}
|
|
308
322
|
reauthorizePaymentMethod(id, params) {
|
|
309
323
|
return this.postFixed(
|
|
310
|
-
`/v1/subscriptions/${id}/reauthorize_payment_method`,
|
|
324
|
+
`/v1/subscriptions/${p(id)}/reauthorize_payment_method`,
|
|
311
325
|
{ return_url: params.return_url },
|
|
312
326
|
{ idempotencyKey: params.idempotencyKey }
|
|
313
327
|
);
|
|
@@ -329,7 +343,7 @@ var Subscriptions = class extends BaseResource {
|
|
|
329
343
|
* See {@link CreateUsageRecordParams.identifier}.
|
|
330
344
|
*/
|
|
331
345
|
createUsageRecord(id, params) {
|
|
332
|
-
return this.post(`/v1/subscriptions/${id}/usage_records`, params);
|
|
346
|
+
return this.post(`/v1/subscriptions/${p(id)}/usage_records`, params);
|
|
333
347
|
}
|
|
334
348
|
/**
|
|
335
349
|
* List usage records for one subscription.
|
|
@@ -339,11 +353,11 @@ var Subscriptions = class extends BaseResource {
|
|
|
339
353
|
* invoice charged for.
|
|
340
354
|
*/
|
|
341
355
|
listUsageRecords(id, params = {}) {
|
|
342
|
-
return this.get(`/v1/subscriptions/${id}/usage_records`, params);
|
|
356
|
+
return this.get(`/v1/subscriptions/${p(id)}/usage_records`, params);
|
|
343
357
|
}
|
|
344
358
|
/** Walk every page of `listUsageRecords()` for one subscription. */
|
|
345
359
|
iterUsageRecords(id, options = {}) {
|
|
346
|
-
return paginate((
|
|
360
|
+
return paginate((page) => this.get(`/v1/subscriptions/${p(id)}/usage_records`, page), {
|
|
347
361
|
pageSize: options.pageSize,
|
|
348
362
|
filters: { invoice_id: options.invoice_id }
|
|
349
363
|
});
|
|
@@ -367,7 +381,7 @@ var Subscriptions = class extends BaseResource {
|
|
|
367
381
|
* unsettled; while one is open, this period cannot be charged.
|
|
368
382
|
*/
|
|
369
383
|
retrieveUsageSummary(id) {
|
|
370
|
-
return this.get(`/v1/subscriptions/${id}/usage_summary`);
|
|
384
|
+
return this.get(`/v1/subscriptions/${p(id)}/usage_summary`);
|
|
371
385
|
}
|
|
372
386
|
};
|
|
373
387
|
var Refunds = class extends BaseResource {
|
|
@@ -375,32 +389,45 @@ var Refunds = class extends BaseResource {
|
|
|
375
389
|
return this.post("/v1/refunds", params);
|
|
376
390
|
}
|
|
377
391
|
retrieve(id) {
|
|
378
|
-
return this.get(`/v1/refunds/${id}`);
|
|
392
|
+
return this.get(`/v1/refunds/${p(id)}`);
|
|
379
393
|
}
|
|
380
394
|
list(params = {}) {
|
|
381
395
|
return this.get("/v1/refunds", params);
|
|
382
396
|
}
|
|
383
397
|
iter(options = {}) {
|
|
384
|
-
return paginate((
|
|
398
|
+
return paginate((page) => this.get("/v1/refunds", page), { pageSize: options.pageSize });
|
|
385
399
|
}
|
|
386
400
|
};
|
|
387
401
|
var Disputes = class extends BaseResource {
|
|
388
402
|
retrieve(id) {
|
|
389
|
-
return this.get(`/v1/disputes/${id}`);
|
|
403
|
+
return this.get(`/v1/disputes/${p(id)}`);
|
|
390
404
|
}
|
|
391
405
|
list(params = {}) {
|
|
392
406
|
return this.get("/v1/disputes", params);
|
|
393
407
|
}
|
|
394
408
|
iter(options = {}) {
|
|
395
|
-
return paginate((
|
|
409
|
+
return paginate((page) => this.get("/v1/disputes", page), {
|
|
410
|
+
pageSize: options.pageSize,
|
|
411
|
+
filters: { status: options.status, payment_id: options.payment_id }
|
|
412
|
+
});
|
|
396
413
|
}
|
|
397
414
|
};
|
|
398
415
|
var WebhookEndpoints = class extends BaseResource {
|
|
416
|
+
/**
|
|
417
|
+
* Every event type this deployment can deliver, plus the wildcard.
|
|
418
|
+
*
|
|
419
|
+
* `enabled_events` rejects anything not on this list, so read it rather
|
|
420
|
+
* than hard-coding a set: a name that is not on it fails at
|
|
421
|
+
* registration and leaves you with an endpoint that never fires.
|
|
422
|
+
*/
|
|
423
|
+
listEventTypes() {
|
|
424
|
+
return this.get("/v1/webhook_endpoints/event_types");
|
|
425
|
+
}
|
|
399
426
|
create(params) {
|
|
400
427
|
return this.post("/v1/webhook_endpoints", params);
|
|
401
428
|
}
|
|
402
429
|
retrieve(id) {
|
|
403
|
-
return this.get(`/v1/webhook_endpoints/${id}`);
|
|
430
|
+
return this.get(`/v1/webhook_endpoints/${p(id)}`);
|
|
404
431
|
}
|
|
405
432
|
/**
|
|
406
433
|
* Update an endpoint, or stop delivery with `status: "disabled"`.
|
|
@@ -411,7 +438,7 @@ var WebhookEndpoints = class extends BaseResource {
|
|
|
411
438
|
* disabling is reversible and deleting is not.
|
|
412
439
|
*/
|
|
413
440
|
update(id, params) {
|
|
414
|
-
return this.post(`/v1/webhook_endpoints/${id}`, params);
|
|
441
|
+
return this.post(`/v1/webhook_endpoints/${p(id)}`, params);
|
|
415
442
|
}
|
|
416
443
|
/**
|
|
417
444
|
* Delete an endpoint. Resolves to `{ id, object: "webhook_endpoint",
|
|
@@ -425,17 +452,17 @@ var WebhookEndpoints = class extends BaseResource {
|
|
|
425
452
|
* were sent stays on record.
|
|
426
453
|
*/
|
|
427
454
|
delete(id, params = {}) {
|
|
428
|
-
return this.del(`/v1/webhook_endpoints/${id}`, params);
|
|
455
|
+
return this.del(`/v1/webhook_endpoints/${p(id)}`, params);
|
|
429
456
|
}
|
|
430
457
|
/** Rotate the signing secret. The new `bkwhsec_...` is returned once. */
|
|
431
458
|
rotateSecret(id, params = {}) {
|
|
432
|
-
return this.postEmpty(`/v1/webhook_endpoints/${id}/rotate_secret`, params);
|
|
459
|
+
return this.postEmpty(`/v1/webhook_endpoints/${p(id)}/rotate_secret`, params);
|
|
433
460
|
}
|
|
434
461
|
list(params = {}) {
|
|
435
462
|
return this.get("/v1/webhook_endpoints", params);
|
|
436
463
|
}
|
|
437
464
|
iter(options = {}) {
|
|
438
|
-
return paginate((
|
|
465
|
+
return paginate((page) => this.get("/v1/webhook_endpoints", page), {
|
|
439
466
|
pageSize: options.pageSize
|
|
440
467
|
});
|
|
441
468
|
}
|
|
@@ -448,20 +475,20 @@ var WebhookEndpoints = class extends BaseResource {
|
|
|
448
475
|
*/
|
|
449
476
|
listDeliveries(endpointId, params = {}) {
|
|
450
477
|
return this.get(
|
|
451
|
-
`/v1/webhook_endpoints/${endpointId}/deliveries`,
|
|
478
|
+
`/v1/webhook_endpoints/${p(endpointId)}/deliveries`,
|
|
452
479
|
params
|
|
453
480
|
);
|
|
454
481
|
}
|
|
455
482
|
/** Walk every page of `listDeliveries()` for one endpoint. */
|
|
456
483
|
iterDeliveries(endpointId, options = {}) {
|
|
457
484
|
return paginate(
|
|
458
|
-
(
|
|
485
|
+
(page) => this.get(`/v1/webhook_endpoints/${p(endpointId)}/deliveries`, page),
|
|
459
486
|
{ pageSize: options.pageSize }
|
|
460
487
|
);
|
|
461
488
|
}
|
|
462
489
|
/** Fetch one delivery row for inspection before deciding to redeliver. */
|
|
463
490
|
retrieveDelivery(endpointId, deliveryId) {
|
|
464
|
-
return this.get(`/v1/webhook_endpoints/${endpointId}/deliveries/${deliveryId}`);
|
|
491
|
+
return this.get(`/v1/webhook_endpoints/${p(endpointId)}/deliveries/${p(deliveryId)}`);
|
|
465
492
|
}
|
|
466
493
|
/**
|
|
467
494
|
* @deprecated Renamed to {@link WebhookEndpoints.retrieveDelivery}.
|
|
@@ -486,21 +513,21 @@ var WebhookEndpoints = class extends BaseResource {
|
|
|
486
513
|
*/
|
|
487
514
|
redeliver(endpointId, deliveryId, params = {}) {
|
|
488
515
|
return this.postEmpty(
|
|
489
|
-
`/v1/webhook_endpoints/${endpointId}/deliveries/${deliveryId}/redeliver`,
|
|
516
|
+
`/v1/webhook_endpoints/${p(endpointId)}/deliveries/${p(deliveryId)}/redeliver`,
|
|
490
517
|
params
|
|
491
518
|
);
|
|
492
519
|
}
|
|
493
520
|
};
|
|
494
521
|
var Events = class extends BaseResource {
|
|
495
522
|
retrieve(id) {
|
|
496
|
-
return this.get(`/v1/events/${id}`);
|
|
523
|
+
return this.get(`/v1/events/${p(id)}`);
|
|
497
524
|
}
|
|
498
525
|
list(params = {}) {
|
|
499
526
|
return this.get("/v1/events", params);
|
|
500
527
|
}
|
|
501
528
|
/** Walk every page of `list()`. Pass `type` to filter at the server. */
|
|
502
529
|
iter(options = {}) {
|
|
503
|
-
return paginate((
|
|
530
|
+
return paginate((page) => this.get("/v1/events", page), {
|
|
504
531
|
pageSize: options.pageSize,
|
|
505
532
|
filters: { type: options.type }
|
|
506
533
|
});
|
|
@@ -511,6 +538,46 @@ var Tenant = class extends BaseResource {
|
|
|
511
538
|
capabilities() {
|
|
512
539
|
return this.get("/v1/tenant/capabilities");
|
|
513
540
|
}
|
|
541
|
+
/**
|
|
542
|
+
* Your registered country and VAT number: what your customers' VAT is
|
|
543
|
+
* decided against.
|
|
544
|
+
*
|
|
545
|
+
* `country_code` is what you have stored and can be `null`;
|
|
546
|
+
* `effective_country_code` is what the next charge will really use.
|
|
547
|
+
* The two differ only when you have stored nothing, which is exactly
|
|
548
|
+
* the case worth spotting before a first live payment.
|
|
549
|
+
*/
|
|
550
|
+
billingProfile() {
|
|
551
|
+
return this.get("/v1/tenant/billing_profile");
|
|
552
|
+
}
|
|
553
|
+
/**
|
|
554
|
+
* Set the seller identity. `country_code` is required on every call;
|
|
555
|
+
* every other field is partial-update, with an explicit `null` to
|
|
556
|
+
* clear. Changes take effect on the next charge only. Tax is written
|
|
557
|
+
* onto a payment and its invoice before money moves, and nothing goes
|
|
558
|
+
* back and recalculates it.
|
|
559
|
+
*/
|
|
560
|
+
setBillingProfile(params) {
|
|
561
|
+
return this.post("/v1/tenant/billing_profile", params);
|
|
562
|
+
}
|
|
563
|
+
/**
|
|
564
|
+
* Download everything in the account as one JSON document, as raw bytes.
|
|
565
|
+
*
|
|
566
|
+
* ```ts
|
|
567
|
+
* await writeFile("export.json", Buffer.from(await client.tenant.export()));
|
|
568
|
+
* ```
|
|
569
|
+
*
|
|
570
|
+
* The GDPR Article 20 portability route, and the way to take a backup.
|
|
571
|
+
* It is `application/json` streamed inline, with no redirect, and each
|
|
572
|
+
* record has the same shape its `GET` route returns, with
|
|
573
|
+
* `billkit_export_version` naming the shape. It can be large, so write
|
|
574
|
+
* it to a file rather than holding it in memory. Test and live data
|
|
575
|
+
* export separately: you get whichever mode the key belongs to. The
|
|
576
|
+
* access is recorded in your audit log.
|
|
577
|
+
*/
|
|
578
|
+
export() {
|
|
579
|
+
return this.t.requestBinary({ method: "GET", path: "/v1/tenant/export" });
|
|
580
|
+
}
|
|
514
581
|
/** Current portal branding row (business name, theme, capability flags). */
|
|
515
582
|
portalBranding() {
|
|
516
583
|
return this.get("/v1/tenant/portal_branding");
|
|
@@ -544,7 +611,7 @@ var Coupons = class extends BaseResource {
|
|
|
544
611
|
return this.post("/v1/coupons", params);
|
|
545
612
|
}
|
|
546
613
|
retrieve(id) {
|
|
547
|
-
return this.get(`/v1/coupons/${id}`);
|
|
614
|
+
return this.get(`/v1/coupons/${p(id)}`);
|
|
548
615
|
}
|
|
549
616
|
/**
|
|
550
617
|
* Update a coupon's limits, or withdraw it with `active: false`.
|
|
@@ -555,7 +622,7 @@ var Coupons = class extends BaseResource {
|
|
|
555
622
|
* customer was charged. `active: true` brings the campaign back.
|
|
556
623
|
*/
|
|
557
624
|
update(id, params) {
|
|
558
|
-
return this.post(`/v1/coupons/${id}`, params);
|
|
625
|
+
return this.post(`/v1/coupons/${p(id)}`, params);
|
|
559
626
|
}
|
|
560
627
|
/**
|
|
561
628
|
* Server-side dry-run of a coupon redemption.
|
|
@@ -573,7 +640,7 @@ var Coupons = class extends BaseResource {
|
|
|
573
640
|
return this.get("/v1/coupons", params);
|
|
574
641
|
}
|
|
575
642
|
iter(options = {}) {
|
|
576
|
-
return paginate((
|
|
643
|
+
return paginate((page) => this.get("/v1/coupons", page), { pageSize: options.pageSize });
|
|
577
644
|
}
|
|
578
645
|
};
|
|
579
646
|
var TaxRates = class extends BaseResource {
|
|
@@ -581,7 +648,7 @@ var TaxRates = class extends BaseResource {
|
|
|
581
648
|
return this.post("/v1/tax_rates", params);
|
|
582
649
|
}
|
|
583
650
|
retrieve(id) {
|
|
584
|
-
return this.get(`/v1/tax_rates/${id}`);
|
|
651
|
+
return this.get(`/v1/tax_rates/${p(id)}`);
|
|
585
652
|
}
|
|
586
653
|
/**
|
|
587
654
|
* Correct a rate, retire it with `active: false`, or bring one back.
|
|
@@ -592,18 +659,19 @@ var TaxRates = class extends BaseResource {
|
|
|
592
659
|
* is no `delete()`.
|
|
593
660
|
*/
|
|
594
661
|
update(id, params) {
|
|
595
|
-
return this.post(`/v1/tax_rates/${id}`, params);
|
|
662
|
+
return this.post(`/v1/tax_rates/${p(id)}`, params);
|
|
596
663
|
}
|
|
597
664
|
list(params = {}) {
|
|
598
665
|
return this.get("/v1/tax_rates", params);
|
|
599
666
|
}
|
|
600
667
|
iter(options = {}) {
|
|
601
|
-
return paginate((
|
|
668
|
+
return paginate((page) => this.get("/v1/tax_rates", page), { pageSize: options.pageSize });
|
|
602
669
|
}
|
|
603
670
|
};
|
|
604
671
|
var Invoices = class extends BaseResource {
|
|
605
|
-
|
|
606
|
-
|
|
672
|
+
/** Expandable: `customer`. */
|
|
673
|
+
retrieve(id, options = {}) {
|
|
674
|
+
return this.get(`/v1/invoices/${p(id)}`, options);
|
|
607
675
|
}
|
|
608
676
|
/**
|
|
609
677
|
* Download the rendered invoice PDF as raw bytes.
|
|
@@ -624,13 +692,27 @@ var Invoices = class extends BaseResource {
|
|
|
624
692
|
* structured invoice for tenants who render their own.
|
|
625
693
|
*/
|
|
626
694
|
retrievePdf(id) {
|
|
627
|
-
return this.t.requestBinary({ method: "GET", path: `/v1/invoices/${id}/pdf` });
|
|
695
|
+
return this.t.requestBinary({ method: "GET", path: `/v1/invoices/${p(id)}/pdf` });
|
|
696
|
+
}
|
|
697
|
+
/**
|
|
698
|
+
* Send the customer their invoice again.
|
|
699
|
+
*
|
|
700
|
+
* The same tenant-branded "your invoice is ready" email, with a fresh
|
|
701
|
+
* portal link, because the one in the original may have expired. It
|
|
702
|
+
* goes to the address captured **on the invoice**, not the customer's
|
|
703
|
+
* current one: this is a copy of a document that was issued to
|
|
704
|
+
* somebody. An invoice with no address on file is a
|
|
705
|
+
* `InvalidRequestError` rather than a send that did not happen.
|
|
706
|
+
*/
|
|
707
|
+
sendEmail(id, params = {}) {
|
|
708
|
+
return this.postEmpty(`/v1/invoices/${p(id)}/email`, params);
|
|
628
709
|
}
|
|
629
710
|
list(params = {}) {
|
|
630
711
|
return this.get("/v1/invoices", params);
|
|
631
712
|
}
|
|
632
713
|
iter(options = {}) {
|
|
633
|
-
|
|
714
|
+
const { pageSize, ...filters } = options;
|
|
715
|
+
return paginate((page) => this.get("/v1/invoices", page), { pageSize, filters });
|
|
634
716
|
}
|
|
635
717
|
/**
|
|
636
718
|
* Void an invoice: state that the sale was never owed.
|
|
@@ -648,12 +730,12 @@ var Invoices = class extends BaseResource {
|
|
|
648
730
|
* Idempotent: re-voiding an already-void invoice returns it unchanged.
|
|
649
731
|
*/
|
|
650
732
|
void(id, params = {}) {
|
|
651
|
-
return this.post(`/v1/invoices/${id}/void`, params);
|
|
733
|
+
return this.post(`/v1/invoices/${p(id)}/void`, params);
|
|
652
734
|
}
|
|
653
735
|
};
|
|
654
736
|
var CreditNotes = class extends BaseResource {
|
|
655
737
|
retrieve(id) {
|
|
656
|
-
return this.get(`/v1/credit_notes/${id}`);
|
|
738
|
+
return this.get(`/v1/credit_notes/${p(id)}`);
|
|
657
739
|
}
|
|
658
740
|
/**
|
|
659
741
|
* Download the rendered credit note PDF as raw bytes. Same storage
|
|
@@ -661,13 +743,13 @@ var CreditNotes = class extends BaseResource {
|
|
|
661
743
|
* `302`, and `501 rendering_pending` on a deployment with no renderer.
|
|
662
744
|
*/
|
|
663
745
|
retrievePdf(id) {
|
|
664
|
-
return this.t.requestBinary({ method: "GET", path: `/v1/credit_notes/${id}/pdf` });
|
|
746
|
+
return this.t.requestBinary({ method: "GET", path: `/v1/credit_notes/${p(id)}/pdf` });
|
|
665
747
|
}
|
|
666
748
|
list(params = {}) {
|
|
667
749
|
return this.get("/v1/credit_notes", params);
|
|
668
750
|
}
|
|
669
751
|
iter(options = {}) {
|
|
670
|
-
return paginate((
|
|
752
|
+
return paginate((page) => this.get("/v1/credit_notes", page), {
|
|
671
753
|
pageSize: options.pageSize,
|
|
672
754
|
filters: { invoice_id: options.invoice_id, customer_id: options.customer_id }
|
|
673
755
|
});
|
|
@@ -675,13 +757,13 @@ var CreditNotes = class extends BaseResource {
|
|
|
675
757
|
};
|
|
676
758
|
var AuditLogs = class extends BaseResource {
|
|
677
759
|
retrieve(id) {
|
|
678
|
-
return this.get(`/v1/audit_logs/${id}`);
|
|
760
|
+
return this.get(`/v1/audit_logs/${p(id)}`);
|
|
679
761
|
}
|
|
680
762
|
list(params = {}) {
|
|
681
763
|
return this.get("/v1/audit_logs", params);
|
|
682
764
|
}
|
|
683
765
|
iter(options = {}) {
|
|
684
|
-
return paginate((
|
|
766
|
+
return paginate((page) => this.get("/v1/audit_logs", page), {
|
|
685
767
|
pageSize: options.pageSize,
|
|
686
768
|
filters: {
|
|
687
769
|
action: options.action,
|
|
@@ -693,30 +775,72 @@ var AuditLogs = class extends BaseResource {
|
|
|
693
775
|
}
|
|
694
776
|
};
|
|
695
777
|
var Payments = class extends BaseResource {
|
|
696
|
-
|
|
697
|
-
|
|
778
|
+
/** Expandable: `customer`, `subscription`. */
|
|
779
|
+
retrieve(id, options = {}) {
|
|
780
|
+
return this.get(`/v1/payments/${p(id)}`, options);
|
|
781
|
+
}
|
|
782
|
+
/**
|
|
783
|
+
* Fetch the provider's own record of this charge, live.
|
|
784
|
+
*
|
|
785
|
+
* Reads Mollie at request time rather than a stored copy, so it carries
|
|
786
|
+
* what BillKit deliberately does not keep: the card BIN, the iDEAL
|
|
787
|
+
* bank, the provider's own status string. Reading live means it can
|
|
788
|
+
* fail: a provider outage or a charge old enough to have aged out
|
|
789
|
+
* answers `200` with `available: false` and a short reason, so render
|
|
790
|
+
* the rest of the page regardless.
|
|
791
|
+
*/
|
|
792
|
+
retrieveProvider(id) {
|
|
793
|
+
return this.get(`/v1/payments/${p(id)}/provider`);
|
|
698
794
|
}
|
|
699
795
|
list(params = {}) {
|
|
700
796
|
return this.get("/v1/payments", params);
|
|
701
797
|
}
|
|
702
798
|
iter(options = {}) {
|
|
703
|
-
return paginate((
|
|
799
|
+
return paginate((page) => this.get("/v1/payments", page), {
|
|
800
|
+
pageSize: options.pageSize,
|
|
801
|
+
filters: { customer_id: options.customer_id }
|
|
802
|
+
});
|
|
704
803
|
}
|
|
705
804
|
};
|
|
706
805
|
var BillingPortalSessions = class extends BaseResource {
|
|
707
806
|
create(params) {
|
|
708
|
-
return this.
|
|
709
|
-
"/v1/billing_portal/sessions",
|
|
710
|
-
{
|
|
711
|
-
subscription_id: params.subscription_id,
|
|
712
|
-
return_url: params.return_url
|
|
713
|
-
},
|
|
714
|
-
{ idempotencyKey: params.idempotencyKey }
|
|
715
|
-
);
|
|
807
|
+
return this.post("/v1/billing_portal/sessions", params);
|
|
716
808
|
}
|
|
717
809
|
/** Kill an in-the-wild portal session. Idempotent. */
|
|
718
810
|
revoke(id, params = {}) {
|
|
719
|
-
return this.postEmpty(`/v1/billing_portal/sessions/${id}/revoke`, params);
|
|
811
|
+
return this.postEmpty(`/v1/billing_portal/sessions/${p(id)}/revoke`, params);
|
|
812
|
+
}
|
|
813
|
+
};
|
|
814
|
+
var ApiKeys = class extends BaseResource {
|
|
815
|
+
/**
|
|
816
|
+
* Issue a new key. The response's `secret` is the only time the full
|
|
817
|
+
* key exists outside the caller's own storage, so record it now.
|
|
818
|
+
*/
|
|
819
|
+
create(params = {}) {
|
|
820
|
+
return this.post("/v1/api_keys", params);
|
|
821
|
+
}
|
|
822
|
+
/**
|
|
823
|
+
* One key's metadata: prefix, label, scopes, `revoked_at`, and
|
|
824
|
+
* `last_used_at`, which is the field to read before revoking one.
|
|
825
|
+
*/
|
|
826
|
+
retrieve(id) {
|
|
827
|
+
return this.get(`/v1/api_keys/${p(id)}`);
|
|
828
|
+
}
|
|
829
|
+
/**
|
|
830
|
+
* Revoke a key so it stops working. Immediate and irreversible; issue a
|
|
831
|
+
* new key instead. Revoking an already-revoked key returns it
|
|
832
|
+
* unchanged, so a retry is safe, and a key may revoke itself, which is
|
|
833
|
+
* what you want when the leaked key is the one you are calling with.
|
|
834
|
+
*/
|
|
835
|
+
revoke(id, params = {}) {
|
|
836
|
+
return this.postEmpty(`/v1/api_keys/${p(id)}/revoke`, params);
|
|
837
|
+
}
|
|
838
|
+
/** List keys, newest first. Revoked ones are included; check `revoked_at`. */
|
|
839
|
+
list(params = {}) {
|
|
840
|
+
return this.get("/v1/api_keys", params);
|
|
841
|
+
}
|
|
842
|
+
iter(options = {}) {
|
|
843
|
+
return paginate((page) => this.get("/v1/api_keys", page), { pageSize: options.pageSize });
|
|
720
844
|
}
|
|
721
845
|
};
|
|
722
846
|
|
|
@@ -730,7 +854,7 @@ var BillKitError = class extends Error {
|
|
|
730
854
|
requestId;
|
|
731
855
|
rawBody;
|
|
732
856
|
constructor(message, options = {}) {
|
|
733
|
-
super(message);
|
|
857
|
+
super(message, options.cause === void 0 ? void 0 : { cause: options.cause });
|
|
734
858
|
this.type = options.type;
|
|
735
859
|
this.code = options.code;
|
|
736
860
|
this.param = options.param;
|
|
@@ -850,7 +974,7 @@ function sleep(ms) {
|
|
|
850
974
|
}
|
|
851
975
|
|
|
852
976
|
// src/version.ts
|
|
853
|
-
var VERSION = "0.
|
|
977
|
+
var VERSION = "0.7.1";
|
|
854
978
|
|
|
855
979
|
// src/transport.ts
|
|
856
980
|
var DEFAULT_BASE_URL = "https://api.billkit.eu";
|
|
@@ -878,9 +1002,8 @@ function buildUrl(baseUrl, path, query) {
|
|
|
878
1002
|
const url = new URL(baseUrl.replace(/\/$/, "") + normalised);
|
|
879
1003
|
if (query) {
|
|
880
1004
|
for (const [k, v] of Object.entries(query)) {
|
|
881
|
-
if (v
|
|
882
|
-
|
|
883
|
-
}
|
|
1005
|
+
if (v === null || v === void 0) continue;
|
|
1006
|
+
url.searchParams.set(k, Array.isArray(v) ? v.join(",") : String(v));
|
|
884
1007
|
}
|
|
885
1008
|
}
|
|
886
1009
|
return url.toString();
|
|
@@ -934,9 +1057,11 @@ function retryDelayMs(status, attempt, policy, retryAfterMs) {
|
|
|
934
1057
|
function connectionError(err, timeoutMs) {
|
|
935
1058
|
const e = err;
|
|
936
1059
|
if (e?.name === "TimeoutError" || e?.name === "AbortError") {
|
|
937
|
-
return new APIConnectionError(`BillKit request timed out after ${timeoutMs}ms
|
|
1060
|
+
return new APIConnectionError(`BillKit request timed out after ${timeoutMs}ms.`, {
|
|
1061
|
+
cause: err
|
|
1062
|
+
});
|
|
938
1063
|
}
|
|
939
|
-
return new APIConnectionError(e?.message ?? "Network request failed.");
|
|
1064
|
+
return new APIConnectionError(e?.message ?? "Network request failed.", { cause: err });
|
|
940
1065
|
}
|
|
941
1066
|
var Transport = class {
|
|
942
1067
|
apiKey;
|
|
@@ -1070,6 +1195,7 @@ function resolveApiKey(supplied) {
|
|
|
1070
1195
|
);
|
|
1071
1196
|
}
|
|
1072
1197
|
var BillKit = class {
|
|
1198
|
+
apiKeys;
|
|
1073
1199
|
customers;
|
|
1074
1200
|
products;
|
|
1075
1201
|
prices;
|
|
@@ -1093,6 +1219,7 @@ var BillKit = class {
|
|
|
1093
1219
|
...options,
|
|
1094
1220
|
apiKey: resolveApiKey(options.apiKey)
|
|
1095
1221
|
});
|
|
1222
|
+
this.apiKeys = new ApiKeys(transport);
|
|
1096
1223
|
this.customers = new Customers(transport);
|
|
1097
1224
|
this.products = new Products(transport);
|
|
1098
1225
|
this.prices = new Prices(transport);
|