@garuhq/node 0.7.0 → 0.10.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/README.md +88 -0
- package/dist/index.cjs +33 -7
- package/dist/index.d.cts +56 -11
- package/dist/index.d.ts +56 -11
- package/dist/index.js +33 -7
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -165,6 +165,94 @@ const customer = await garu.customers.create({
|
|
|
165
165
|
const { data, meta } = await garu.customers.list({ search: 'maria', limit: 10 });
|
|
166
166
|
```
|
|
167
167
|
|
|
168
|
+
## Products
|
|
169
|
+
|
|
170
|
+
Discover products and customize the per-product portal experience (B2B2C).
|
|
171
|
+
|
|
172
|
+
`portalConfig.*` methods accept `productId` as either the product UUID (preferred — same identifier returned by `list()` and webhook payloads) or the legacy numeric id (Garu v0.10.0+).
|
|
173
|
+
|
|
174
|
+
| Method | Description |
|
|
175
|
+
| ----------------------------------- | ----------------------------------------------------------------- |
|
|
176
|
+
| `list(params?)` | Paginated list of products for the seller. |
|
|
177
|
+
| `get(uuid)` | Fetch a single product by UUID — same id used by charges. |
|
|
178
|
+
| `portalConfig.get(productId)` | Read per-product portal customization. Returns `null` if unset. |
|
|
179
|
+
| `portalConfig.set(productId, p)` | Upsert with merge — only fields present are written. |
|
|
180
|
+
| `portalConfig.patch(productId, p)` | Same merge semantics as `set` — alias for HTTP-PATCH callers. |
|
|
181
|
+
| `portalConfig.clear(productId)` | Remove the customization; product falls back to seller config. |
|
|
182
|
+
|
|
183
|
+
```ts
|
|
184
|
+
// SaaS de coaching: per-coach branding under one Seller account
|
|
185
|
+
await garu.products.portalConfig.set('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f', {
|
|
186
|
+
businessName: 'Coach Maria — Corrida & Trilha',
|
|
187
|
+
primaryColor: '#257264',
|
|
188
|
+
logoUrl: 'https://cdn.exemplo.com/coaches/maria.png',
|
|
189
|
+
});
|
|
190
|
+
|
|
191
|
+
// Pass `null` on a field to inherit from the seller-level config
|
|
192
|
+
await garu.products.portalConfig.patch('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f', {
|
|
193
|
+
primaryColor: null,
|
|
194
|
+
});
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
## Scheduled charges
|
|
198
|
+
|
|
199
|
+
Bill an existing customer on a future date — one-time or recurring with card tokenization. The Garu drives email reminders, dunning, retries, and the lifecycle state machine.
|
|
200
|
+
|
|
201
|
+
| Method | Description |
|
|
202
|
+
| --------------------------------------------- | -------------------------------------------------------------------------- |
|
|
203
|
+
| `create(params)` | Create one-time or recurring schedule. Auto-attaches `X-Idempotency-Key`. |
|
|
204
|
+
| `list(params?)` | Paginated list with status / type / dueFrom / dueTo / customerId filters. |
|
|
205
|
+
| `get(id)` | Detail bundle: charge + event timeline + linked transactions. |
|
|
206
|
+
| `markPaid(id, params)` | Mark cycle paid (off-Garu reconciliation). |
|
|
207
|
+
| `postpone(id, params)` | Move the next cycle's due date forward. |
|
|
208
|
+
| `pause(id, params?)` / `resume(id)` | Suspend / re-enable a series. |
|
|
209
|
+
| `cancelRecurrence(id, params?)` | Hard-stop future cycles (recurring only). |
|
|
210
|
+
| `cancelAtPeriodEnd(id, { enabled })` | Stripe-style soft-cancel; reversible. |
|
|
211
|
+
| `changePaymentMethod(id, params)` | Swap the saved card. |
|
|
212
|
+
| `clearPaymentMethod(id)` | Remove the saved card; future cycles email-with-link. |
|
|
213
|
+
| `listAttempts(id, params?)` | Per-attempt billing log — every silent-charge / retry / mark-paid (v0.8.2).|
|
|
214
|
+
|
|
215
|
+
```ts
|
|
216
|
+
// Recurring with 7-day trial
|
|
217
|
+
const series = await garu.scheduledCharges.create({
|
|
218
|
+
customerId: 42,
|
|
219
|
+
productId: 17,
|
|
220
|
+
amount: 49.9,
|
|
221
|
+
type: 'recurring',
|
|
222
|
+
dueDate: '2026-06-01',
|
|
223
|
+
methods: ['card', 'pix'],
|
|
224
|
+
recurrence: { interval: 'monthly' },
|
|
225
|
+
trialDays: 7,
|
|
226
|
+
});
|
|
227
|
+
|
|
228
|
+
// Audit why cycle 3 failed (v0.8.2)
|
|
229
|
+
const { data } = await garu.scheduledCharges.listAttempts(series.id, {
|
|
230
|
+
cycleNumber: 3,
|
|
231
|
+
});
|
|
232
|
+
const declines = data.filter((a) => a.status === 'declined');
|
|
233
|
+
// → each declines[i].failureCode is one of GaruFailureCode (insufficient_funds,
|
|
234
|
+
// card_expired, card_declined, ...)
|
|
235
|
+
```
|
|
236
|
+
|
|
237
|
+
## Failure codes (v0.8.0)
|
|
238
|
+
|
|
239
|
+
Every `transaction.payment.failed`, `scheduled_charge.cycle_failed`, and `listAttempts()` row carries:
|
|
240
|
+
|
|
241
|
+
- `failureCode` — canonical `GaruFailureCode` enum (10 values, gateway-independent)
|
|
242
|
+
- `failureReason` — human-readable PT-BR
|
|
243
|
+
- `gatewayFailureCode` — raw code from Celcoin (ABECS for forensics)
|
|
244
|
+
|
|
245
|
+
```ts
|
|
246
|
+
import type { GaruFailureCode } from '@garuhq/node';
|
|
247
|
+
|
|
248
|
+
const PERMANENT: GaruFailureCode[] = ['card_expired', 'card_canceled', 'fraud_suspected'];
|
|
249
|
+
function shouldAskForNewCard(code: GaruFailureCode): boolean {
|
|
250
|
+
return PERMANENT.includes(code);
|
|
251
|
+
}
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
Full table at [docs.garu.com.br/api-reference/webhooks/codigos-de-falha](https://docs.garu.com.br/api-reference/webhooks/codigos-de-falha).
|
|
255
|
+
|
|
168
256
|
## Meta
|
|
169
257
|
|
|
170
258
|
Discover available payment methods and webhook events. No authentication required.
|
package/dist/index.cjs
CHANGED
|
@@ -475,11 +475,11 @@ var ProductPortalConfigResource = class {
|
|
|
475
475
|
* portal config).
|
|
476
476
|
*
|
|
477
477
|
* @example
|
|
478
|
-
* const cfg = await garu.products.portalConfig.get(
|
|
478
|
+
* const cfg = await garu.products.portalConfig.get('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
479
479
|
*/
|
|
480
480
|
async get(productId) {
|
|
481
481
|
return this.http.call(
|
|
482
|
-
(signal) => this.http.client.GET(`/api/products/${productId}/portal-config`, {
|
|
482
|
+
(signal) => this.http.client.GET(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
483
483
|
signal
|
|
484
484
|
}).then((r) => r)
|
|
485
485
|
);
|
|
@@ -491,7 +491,7 @@ var ProductPortalConfigResource = class {
|
|
|
491
491
|
* value. Use `clear` to reset everything.
|
|
492
492
|
*
|
|
493
493
|
* @example
|
|
494
|
-
* await garu.products.portalConfig.set(
|
|
494
|
+
* await garu.products.portalConfig.set('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f', {
|
|
495
495
|
* businessName: 'Coach Maria — Corrida & Trilha',
|
|
496
496
|
* primaryColor: '#257264',
|
|
497
497
|
* logoUrl: 'https://cdn.atletia.com.br/coaches/maria.png'
|
|
@@ -499,7 +499,7 @@ var ProductPortalConfigResource = class {
|
|
|
499
499
|
*/
|
|
500
500
|
async set(productId, params) {
|
|
501
501
|
return this.http.call(
|
|
502
|
-
(signal) => this.http.client.POST(`/api/products/${productId}/portal-config`, {
|
|
502
|
+
(signal) => this.http.client.POST(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
503
503
|
body: params,
|
|
504
504
|
signal
|
|
505
505
|
}).then((r) => r)
|
|
@@ -508,7 +508,7 @@ var ProductPortalConfigResource = class {
|
|
|
508
508
|
/** Same merge semantics as `set` — alias for HTTP-PATCH-prefering callers. */
|
|
509
509
|
async patch(productId, params) {
|
|
510
510
|
return this.http.call(
|
|
511
|
-
(signal) => this.http.client.PATCH(`/api/products/${productId}/portal-config`, {
|
|
511
|
+
(signal) => this.http.client.PATCH(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
512
512
|
body: params,
|
|
513
513
|
signal
|
|
514
514
|
}).then((r) => r)
|
|
@@ -520,11 +520,11 @@ var ProductPortalConfigResource = class {
|
|
|
520
520
|
* deleted, `{ removed: false }` when there was nothing to remove.
|
|
521
521
|
*
|
|
522
522
|
* @example
|
|
523
|
-
* await garu.products.portalConfig.clear(
|
|
523
|
+
* await garu.products.portalConfig.clear('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
524
524
|
*/
|
|
525
525
|
async clear(productId) {
|
|
526
526
|
return this.http.call(
|
|
527
|
-
(signal) => this.http.client.DELETE(`/api/products/${productId}/portal-config`, {
|
|
527
|
+
(signal) => this.http.client.DELETE(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
528
528
|
signal
|
|
529
529
|
}).then((r) => r)
|
|
530
530
|
);
|
|
@@ -802,6 +802,32 @@ var ScheduledCharges = class {
|
|
|
802
802
|
}).then((r) => r)
|
|
803
803
|
);
|
|
804
804
|
}
|
|
805
|
+
/**
|
|
806
|
+
* Per-attempt billing log for the series (SPEC §4.2). One row per
|
|
807
|
+
* logical billing event — cycle 1 interactive charge, every silent
|
|
808
|
+
* charge attempt, every retry, every manual mark-paid. Carries the
|
|
809
|
+
* canonical `failureCode` for declines so you can audit billing
|
|
810
|
+
* outcomes without cross-referencing Transactions.
|
|
811
|
+
*
|
|
812
|
+
* @example
|
|
813
|
+
* const { data } = await garu.scheduledCharges.listAttempts('sch_abc', {
|
|
814
|
+
* cycleNumber: 3
|
|
815
|
+
* });
|
|
816
|
+
* const declines = data.filter((a) => a.status === 'declined');
|
|
817
|
+
*/
|
|
818
|
+
async listAttempts(id, params = {}) {
|
|
819
|
+
const qs = new URLSearchParams();
|
|
820
|
+
if (params.page !== void 0) qs.set("page", String(params.page));
|
|
821
|
+
if (params.limit !== void 0) qs.set("limit", String(params.limit));
|
|
822
|
+
if (params.cycleNumber !== void 0) qs.set("cycleNumber", String(params.cycleNumber));
|
|
823
|
+
const query = qs.toString();
|
|
824
|
+
const url = `/api/scheduled-charges/${id}/attempts${query ? `?${query}` : ""}`;
|
|
825
|
+
return this.http.call(
|
|
826
|
+
(signal) => this.http.client.GET(url, { signal }).then(
|
|
827
|
+
(r) => r
|
|
828
|
+
)
|
|
829
|
+
);
|
|
830
|
+
}
|
|
805
831
|
};
|
|
806
832
|
var webhooks = {
|
|
807
833
|
verify(params) {
|
package/dist/index.d.cts
CHANGED
|
@@ -354,6 +354,33 @@ interface ScheduledChargeDetail {
|
|
|
354
354
|
transactions: ScheduledChargeLinkedTransaction[];
|
|
355
355
|
}
|
|
356
356
|
type ScheduledChargeList = PaginatedList<ScheduledChargeRecord>;
|
|
357
|
+
/** Source of a billing attempt — see SPEC §3.1. */
|
|
358
|
+
type ScheduledChargeAttemptSource = 'cycle1_interactive' | 'silent_charge' | 'card_retry' | 'manual_mark_paid' | 'fallback_pix';
|
|
359
|
+
type ScheduledChargeAttemptStatus = 'pending' | 'succeeded' | 'declined' | 'canceled' | 'errored';
|
|
360
|
+
interface ScheduledChargeAttempt {
|
|
361
|
+
id: number;
|
|
362
|
+
cycleId: string;
|
|
363
|
+
cycleNumber: number;
|
|
364
|
+
attemptNumber: number;
|
|
365
|
+
attemptedAt: string;
|
|
366
|
+
source: ScheduledChargeAttemptSource;
|
|
367
|
+
paymentMethod: 'card' | 'pix' | 'boleto' | 'manual';
|
|
368
|
+
paymentMethodId: number | null;
|
|
369
|
+
cardLast4: string | null;
|
|
370
|
+
cardBrand: string | null;
|
|
371
|
+
status: ScheduledChargeAttemptStatus;
|
|
372
|
+
failureCode: GaruFailureCode | null;
|
|
373
|
+
failureReason: string | null;
|
|
374
|
+
gatewayFailureCode: string | null;
|
|
375
|
+
gatewayChargeId: number | null;
|
|
376
|
+
transactionId: number | null;
|
|
377
|
+
}
|
|
378
|
+
type ScheduledChargeAttemptList = PaginatedList<ScheduledChargeAttempt>;
|
|
379
|
+
interface ListScheduledChargeAttemptsParams {
|
|
380
|
+
page?: number;
|
|
381
|
+
limit?: number;
|
|
382
|
+
cycleNumber?: number;
|
|
383
|
+
}
|
|
357
384
|
interface CreateScheduledChargeParams {
|
|
358
385
|
customerId: number;
|
|
359
386
|
/**
|
|
@@ -749,9 +776,13 @@ declare class Meta {
|
|
|
749
776
|
}
|
|
750
777
|
|
|
751
778
|
/**
|
|
752
|
-
* Per-product portal customization
|
|
753
|
-
*
|
|
754
|
-
*
|
|
779
|
+
* Per-product portal customization. Used by B2B2C platforms that model
|
|
780
|
+
* their professionals/coaches as Products under a single seller and want
|
|
781
|
+
* per-product branding on the customer payment + portal pages.
|
|
782
|
+
*
|
|
783
|
+
* `productId` accepts either the product UUID (preferred — same identifier
|
|
784
|
+
* returned by `garu.products.list()` and webhook payloads) or the legacy
|
|
785
|
+
* numeric id. UUID support added in Garu v0.10.0.
|
|
755
786
|
*/
|
|
756
787
|
declare class ProductPortalConfigResource {
|
|
757
788
|
private readonly http;
|
|
@@ -762,9 +793,9 @@ declare class ProductPortalConfigResource {
|
|
|
762
793
|
* portal config).
|
|
763
794
|
*
|
|
764
795
|
* @example
|
|
765
|
-
* const cfg = await garu.products.portalConfig.get(
|
|
796
|
+
* const cfg = await garu.products.portalConfig.get('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
766
797
|
*/
|
|
767
|
-
get(productId: number): Promise<ProductPortalConfig | null>;
|
|
798
|
+
get(productId: string | number): Promise<ProductPortalConfig | null>;
|
|
768
799
|
/**
|
|
769
800
|
* Create or merge the portal customization (idempotent upsert). Both
|
|
770
801
|
* `set` and `patch` have the same merge semantics — only fields present
|
|
@@ -772,24 +803,24 @@ declare class ProductPortalConfigResource {
|
|
|
772
803
|
* value. Use `clear` to reset everything.
|
|
773
804
|
*
|
|
774
805
|
* @example
|
|
775
|
-
* await garu.products.portalConfig.set(
|
|
806
|
+
* await garu.products.portalConfig.set('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f', {
|
|
776
807
|
* businessName: 'Coach Maria — Corrida & Trilha',
|
|
777
808
|
* primaryColor: '#257264',
|
|
778
809
|
* logoUrl: 'https://cdn.atletia.com.br/coaches/maria.png'
|
|
779
810
|
* });
|
|
780
811
|
*/
|
|
781
|
-
set(productId: number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
812
|
+
set(productId: string | number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
782
813
|
/** Same merge semantics as `set` — alias for HTTP-PATCH-prefering callers. */
|
|
783
|
-
patch(productId: number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
814
|
+
patch(productId: string | number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
784
815
|
/**
|
|
785
816
|
* Remove the per-product config. The product falls back to the
|
|
786
817
|
* seller-level portal config. Returns `{ removed: true }` when a row was
|
|
787
818
|
* deleted, `{ removed: false }` when there was nothing to remove.
|
|
788
819
|
*
|
|
789
820
|
* @example
|
|
790
|
-
* await garu.products.portalConfig.clear(
|
|
821
|
+
* await garu.products.portalConfig.clear('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
791
822
|
*/
|
|
792
|
-
clear(productId: number): Promise<{
|
|
823
|
+
clear(productId: string | number): Promise<{
|
|
793
824
|
removed: boolean;
|
|
794
825
|
}>;
|
|
795
826
|
}
|
|
@@ -971,6 +1002,20 @@ declare class ScheduledCharges {
|
|
|
971
1002
|
* await garu.scheduledCharges.clearPaymentMethod('sch_abc123');
|
|
972
1003
|
*/
|
|
973
1004
|
clearPaymentMethod(id: string): Promise<ScheduledChargeRecord>;
|
|
1005
|
+
/**
|
|
1006
|
+
* Per-attempt billing log for the series (SPEC §4.2). One row per
|
|
1007
|
+
* logical billing event — cycle 1 interactive charge, every silent
|
|
1008
|
+
* charge attempt, every retry, every manual mark-paid. Carries the
|
|
1009
|
+
* canonical `failureCode` for declines so you can audit billing
|
|
1010
|
+
* outcomes without cross-referencing Transactions.
|
|
1011
|
+
*
|
|
1012
|
+
* @example
|
|
1013
|
+
* const { data } = await garu.scheduledCharges.listAttempts('sch_abc', {
|
|
1014
|
+
* cycleNumber: 3
|
|
1015
|
+
* });
|
|
1016
|
+
* const declines = data.filter((a) => a.status === 'declined');
|
|
1017
|
+
*/
|
|
1018
|
+
listAttempts(id: string, params?: ListScheduledChargeAttemptsParams): Promise<ScheduledChargeAttemptList>;
|
|
974
1019
|
}
|
|
975
1020
|
|
|
976
1021
|
interface GaruOptions {
|
|
@@ -1071,4 +1116,4 @@ declare class GaruServerError extends GaruAPIError {
|
|
|
1071
1116
|
constructor(message: string, status: number, requestId: string | null, body: unknown);
|
|
1072
1117
|
}
|
|
1073
1118
|
|
|
1074
|
-
export { type CancelAtPeriodEndScheduledChargeParams, type CancelRecurrenceScheduledChargeParams, type CardInfo, type ChangePaymentMethodScheduledChargeParams, type Charge, type ChargeList, type ChargeStatus, type CreateChargeParams, type CreateCustomerParams, type CreateScheduledChargeParams, type Customer, type CustomerList, type CustomerRecord, type FailurePayload, Garu, GaruAPIError, GaruAuthenticationError, GaruConnectionError, GaruError, type GaruErrorCode, type GaruFailureCode, GaruNotFoundError, type GaruOptions, GaruPermissionError, GaruRateLimitError, GaruServerError, GaruSignatureVerificationError, GaruValidationError, type ListChargesParams, type ListCustomersParams, type ListProductsParams, type ListScheduledChargesParams, type MarkPaidScheduledChargeParams, type MetaFeatures, type MetaResponse, type PaginatedList, type PauseScheduledChargeParams, type PaymentMethod, type PaymentMethodExpiredPayload, type PaymentMethodExpiringPayload, type PostponeScheduledChargeParams, type Product, type ProductList, type ProductPortalConfig, type RecurrenceConfig, type RecurrenceInterval, type RefundChargeParams, type ScheduledChargeActor, type ScheduledChargeDetail, type ScheduledChargeEvent, type ScheduledChargeEventType, type ScheduledChargeLinkedTransaction, type ScheduledChargeList, type ScheduledChargeRecord, type ScheduledChargeStatus, type ScheduledChargeType, type ScheduledPaymentMethod, type SetProductPortalConfigParams, type UpdateCustomerParams, type VerifiedWebhook, type VerifyWebhookParams, type WirePaymentMethodId, webhooks };
|
|
1119
|
+
export { type CancelAtPeriodEndScheduledChargeParams, type CancelRecurrenceScheduledChargeParams, type CardInfo, type ChangePaymentMethodScheduledChargeParams, type Charge, type ChargeList, type ChargeStatus, type CreateChargeParams, type CreateCustomerParams, type CreateScheduledChargeParams, type Customer, type CustomerList, type CustomerRecord, type FailurePayload, Garu, GaruAPIError, GaruAuthenticationError, GaruConnectionError, GaruError, type GaruErrorCode, type GaruFailureCode, GaruNotFoundError, type GaruOptions, GaruPermissionError, GaruRateLimitError, GaruServerError, GaruSignatureVerificationError, GaruValidationError, type ListChargesParams, type ListCustomersParams, type ListProductsParams, type ListScheduledChargeAttemptsParams, type ListScheduledChargesParams, type MarkPaidScheduledChargeParams, type MetaFeatures, type MetaResponse, type PaginatedList, type PauseScheduledChargeParams, type PaymentMethod, type PaymentMethodExpiredPayload, type PaymentMethodExpiringPayload, type PostponeScheduledChargeParams, type Product, type ProductList, type ProductPortalConfig, type RecurrenceConfig, type RecurrenceInterval, type RefundChargeParams, type ScheduledChargeActor, type ScheduledChargeAttempt, type ScheduledChargeAttemptList, type ScheduledChargeAttemptSource, type ScheduledChargeAttemptStatus, type ScheduledChargeDetail, type ScheduledChargeEvent, type ScheduledChargeEventType, type ScheduledChargeLinkedTransaction, type ScheduledChargeList, type ScheduledChargeRecord, type ScheduledChargeStatus, type ScheduledChargeType, type ScheduledPaymentMethod, type SetProductPortalConfigParams, type UpdateCustomerParams, type VerifiedWebhook, type VerifyWebhookParams, type WirePaymentMethodId, webhooks };
|
package/dist/index.d.ts
CHANGED
|
@@ -354,6 +354,33 @@ interface ScheduledChargeDetail {
|
|
|
354
354
|
transactions: ScheduledChargeLinkedTransaction[];
|
|
355
355
|
}
|
|
356
356
|
type ScheduledChargeList = PaginatedList<ScheduledChargeRecord>;
|
|
357
|
+
/** Source of a billing attempt — see SPEC §3.1. */
|
|
358
|
+
type ScheduledChargeAttemptSource = 'cycle1_interactive' | 'silent_charge' | 'card_retry' | 'manual_mark_paid' | 'fallback_pix';
|
|
359
|
+
type ScheduledChargeAttemptStatus = 'pending' | 'succeeded' | 'declined' | 'canceled' | 'errored';
|
|
360
|
+
interface ScheduledChargeAttempt {
|
|
361
|
+
id: number;
|
|
362
|
+
cycleId: string;
|
|
363
|
+
cycleNumber: number;
|
|
364
|
+
attemptNumber: number;
|
|
365
|
+
attemptedAt: string;
|
|
366
|
+
source: ScheduledChargeAttemptSource;
|
|
367
|
+
paymentMethod: 'card' | 'pix' | 'boleto' | 'manual';
|
|
368
|
+
paymentMethodId: number | null;
|
|
369
|
+
cardLast4: string | null;
|
|
370
|
+
cardBrand: string | null;
|
|
371
|
+
status: ScheduledChargeAttemptStatus;
|
|
372
|
+
failureCode: GaruFailureCode | null;
|
|
373
|
+
failureReason: string | null;
|
|
374
|
+
gatewayFailureCode: string | null;
|
|
375
|
+
gatewayChargeId: number | null;
|
|
376
|
+
transactionId: number | null;
|
|
377
|
+
}
|
|
378
|
+
type ScheduledChargeAttemptList = PaginatedList<ScheduledChargeAttempt>;
|
|
379
|
+
interface ListScheduledChargeAttemptsParams {
|
|
380
|
+
page?: number;
|
|
381
|
+
limit?: number;
|
|
382
|
+
cycleNumber?: number;
|
|
383
|
+
}
|
|
357
384
|
interface CreateScheduledChargeParams {
|
|
358
385
|
customerId: number;
|
|
359
386
|
/**
|
|
@@ -749,9 +776,13 @@ declare class Meta {
|
|
|
749
776
|
}
|
|
750
777
|
|
|
751
778
|
/**
|
|
752
|
-
* Per-product portal customization
|
|
753
|
-
*
|
|
754
|
-
*
|
|
779
|
+
* Per-product portal customization. Used by B2B2C platforms that model
|
|
780
|
+
* their professionals/coaches as Products under a single seller and want
|
|
781
|
+
* per-product branding on the customer payment + portal pages.
|
|
782
|
+
*
|
|
783
|
+
* `productId` accepts either the product UUID (preferred — same identifier
|
|
784
|
+
* returned by `garu.products.list()` and webhook payloads) or the legacy
|
|
785
|
+
* numeric id. UUID support added in Garu v0.10.0.
|
|
755
786
|
*/
|
|
756
787
|
declare class ProductPortalConfigResource {
|
|
757
788
|
private readonly http;
|
|
@@ -762,9 +793,9 @@ declare class ProductPortalConfigResource {
|
|
|
762
793
|
* portal config).
|
|
763
794
|
*
|
|
764
795
|
* @example
|
|
765
|
-
* const cfg = await garu.products.portalConfig.get(
|
|
796
|
+
* const cfg = await garu.products.portalConfig.get('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
766
797
|
*/
|
|
767
|
-
get(productId: number): Promise<ProductPortalConfig | null>;
|
|
798
|
+
get(productId: string | number): Promise<ProductPortalConfig | null>;
|
|
768
799
|
/**
|
|
769
800
|
* Create or merge the portal customization (idempotent upsert). Both
|
|
770
801
|
* `set` and `patch` have the same merge semantics — only fields present
|
|
@@ -772,24 +803,24 @@ declare class ProductPortalConfigResource {
|
|
|
772
803
|
* value. Use `clear` to reset everything.
|
|
773
804
|
*
|
|
774
805
|
* @example
|
|
775
|
-
* await garu.products.portalConfig.set(
|
|
806
|
+
* await garu.products.portalConfig.set('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f', {
|
|
776
807
|
* businessName: 'Coach Maria — Corrida & Trilha',
|
|
777
808
|
* primaryColor: '#257264',
|
|
778
809
|
* logoUrl: 'https://cdn.atletia.com.br/coaches/maria.png'
|
|
779
810
|
* });
|
|
780
811
|
*/
|
|
781
|
-
set(productId: number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
812
|
+
set(productId: string | number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
782
813
|
/** Same merge semantics as `set` — alias for HTTP-PATCH-prefering callers. */
|
|
783
|
-
patch(productId: number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
814
|
+
patch(productId: string | number, params: SetProductPortalConfigParams): Promise<ProductPortalConfig>;
|
|
784
815
|
/**
|
|
785
816
|
* Remove the per-product config. The product falls back to the
|
|
786
817
|
* seller-level portal config. Returns `{ removed: true }` when a row was
|
|
787
818
|
* deleted, `{ removed: false }` when there was nothing to remove.
|
|
788
819
|
*
|
|
789
820
|
* @example
|
|
790
|
-
* await garu.products.portalConfig.clear(
|
|
821
|
+
* await garu.products.portalConfig.clear('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
791
822
|
*/
|
|
792
|
-
clear(productId: number): Promise<{
|
|
823
|
+
clear(productId: string | number): Promise<{
|
|
793
824
|
removed: boolean;
|
|
794
825
|
}>;
|
|
795
826
|
}
|
|
@@ -971,6 +1002,20 @@ declare class ScheduledCharges {
|
|
|
971
1002
|
* await garu.scheduledCharges.clearPaymentMethod('sch_abc123');
|
|
972
1003
|
*/
|
|
973
1004
|
clearPaymentMethod(id: string): Promise<ScheduledChargeRecord>;
|
|
1005
|
+
/**
|
|
1006
|
+
* Per-attempt billing log for the series (SPEC §4.2). One row per
|
|
1007
|
+
* logical billing event — cycle 1 interactive charge, every silent
|
|
1008
|
+
* charge attempt, every retry, every manual mark-paid. Carries the
|
|
1009
|
+
* canonical `failureCode` for declines so you can audit billing
|
|
1010
|
+
* outcomes without cross-referencing Transactions.
|
|
1011
|
+
*
|
|
1012
|
+
* @example
|
|
1013
|
+
* const { data } = await garu.scheduledCharges.listAttempts('sch_abc', {
|
|
1014
|
+
* cycleNumber: 3
|
|
1015
|
+
* });
|
|
1016
|
+
* const declines = data.filter((a) => a.status === 'declined');
|
|
1017
|
+
*/
|
|
1018
|
+
listAttempts(id: string, params?: ListScheduledChargeAttemptsParams): Promise<ScheduledChargeAttemptList>;
|
|
974
1019
|
}
|
|
975
1020
|
|
|
976
1021
|
interface GaruOptions {
|
|
@@ -1071,4 +1116,4 @@ declare class GaruServerError extends GaruAPIError {
|
|
|
1071
1116
|
constructor(message: string, status: number, requestId: string | null, body: unknown);
|
|
1072
1117
|
}
|
|
1073
1118
|
|
|
1074
|
-
export { type CancelAtPeriodEndScheduledChargeParams, type CancelRecurrenceScheduledChargeParams, type CardInfo, type ChangePaymentMethodScheduledChargeParams, type Charge, type ChargeList, type ChargeStatus, type CreateChargeParams, type CreateCustomerParams, type CreateScheduledChargeParams, type Customer, type CustomerList, type CustomerRecord, type FailurePayload, Garu, GaruAPIError, GaruAuthenticationError, GaruConnectionError, GaruError, type GaruErrorCode, type GaruFailureCode, GaruNotFoundError, type GaruOptions, GaruPermissionError, GaruRateLimitError, GaruServerError, GaruSignatureVerificationError, GaruValidationError, type ListChargesParams, type ListCustomersParams, type ListProductsParams, type ListScheduledChargesParams, type MarkPaidScheduledChargeParams, type MetaFeatures, type MetaResponse, type PaginatedList, type PauseScheduledChargeParams, type PaymentMethod, type PaymentMethodExpiredPayload, type PaymentMethodExpiringPayload, type PostponeScheduledChargeParams, type Product, type ProductList, type ProductPortalConfig, type RecurrenceConfig, type RecurrenceInterval, type RefundChargeParams, type ScheduledChargeActor, type ScheduledChargeDetail, type ScheduledChargeEvent, type ScheduledChargeEventType, type ScheduledChargeLinkedTransaction, type ScheduledChargeList, type ScheduledChargeRecord, type ScheduledChargeStatus, type ScheduledChargeType, type ScheduledPaymentMethod, type SetProductPortalConfigParams, type UpdateCustomerParams, type VerifiedWebhook, type VerifyWebhookParams, type WirePaymentMethodId, webhooks };
|
|
1119
|
+
export { type CancelAtPeriodEndScheduledChargeParams, type CancelRecurrenceScheduledChargeParams, type CardInfo, type ChangePaymentMethodScheduledChargeParams, type Charge, type ChargeList, type ChargeStatus, type CreateChargeParams, type CreateCustomerParams, type CreateScheduledChargeParams, type Customer, type CustomerList, type CustomerRecord, type FailurePayload, Garu, GaruAPIError, GaruAuthenticationError, GaruConnectionError, GaruError, type GaruErrorCode, type GaruFailureCode, GaruNotFoundError, type GaruOptions, GaruPermissionError, GaruRateLimitError, GaruServerError, GaruSignatureVerificationError, GaruValidationError, type ListChargesParams, type ListCustomersParams, type ListProductsParams, type ListScheduledChargeAttemptsParams, type ListScheduledChargesParams, type MarkPaidScheduledChargeParams, type MetaFeatures, type MetaResponse, type PaginatedList, type PauseScheduledChargeParams, type PaymentMethod, type PaymentMethodExpiredPayload, type PaymentMethodExpiringPayload, type PostponeScheduledChargeParams, type Product, type ProductList, type ProductPortalConfig, type RecurrenceConfig, type RecurrenceInterval, type RefundChargeParams, type ScheduledChargeActor, type ScheduledChargeAttempt, type ScheduledChargeAttemptList, type ScheduledChargeAttemptSource, type ScheduledChargeAttemptStatus, type ScheduledChargeDetail, type ScheduledChargeEvent, type ScheduledChargeEventType, type ScheduledChargeLinkedTransaction, type ScheduledChargeList, type ScheduledChargeRecord, type ScheduledChargeStatus, type ScheduledChargeType, type ScheduledPaymentMethod, type SetProductPortalConfigParams, type UpdateCustomerParams, type VerifiedWebhook, type VerifyWebhookParams, type WirePaymentMethodId, webhooks };
|
package/dist/index.js
CHANGED
|
@@ -469,11 +469,11 @@ var ProductPortalConfigResource = class {
|
|
|
469
469
|
* portal config).
|
|
470
470
|
*
|
|
471
471
|
* @example
|
|
472
|
-
* const cfg = await garu.products.portalConfig.get(
|
|
472
|
+
* const cfg = await garu.products.portalConfig.get('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
473
473
|
*/
|
|
474
474
|
async get(productId) {
|
|
475
475
|
return this.http.call(
|
|
476
|
-
(signal) => this.http.client.GET(`/api/products/${productId}/portal-config`, {
|
|
476
|
+
(signal) => this.http.client.GET(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
477
477
|
signal
|
|
478
478
|
}).then((r) => r)
|
|
479
479
|
);
|
|
@@ -485,7 +485,7 @@ var ProductPortalConfigResource = class {
|
|
|
485
485
|
* value. Use `clear` to reset everything.
|
|
486
486
|
*
|
|
487
487
|
* @example
|
|
488
|
-
* await garu.products.portalConfig.set(
|
|
488
|
+
* await garu.products.portalConfig.set('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f', {
|
|
489
489
|
* businessName: 'Coach Maria — Corrida & Trilha',
|
|
490
490
|
* primaryColor: '#257264',
|
|
491
491
|
* logoUrl: 'https://cdn.atletia.com.br/coaches/maria.png'
|
|
@@ -493,7 +493,7 @@ var ProductPortalConfigResource = class {
|
|
|
493
493
|
*/
|
|
494
494
|
async set(productId, params) {
|
|
495
495
|
return this.http.call(
|
|
496
|
-
(signal) => this.http.client.POST(`/api/products/${productId}/portal-config`, {
|
|
496
|
+
(signal) => this.http.client.POST(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
497
497
|
body: params,
|
|
498
498
|
signal
|
|
499
499
|
}).then((r) => r)
|
|
@@ -502,7 +502,7 @@ var ProductPortalConfigResource = class {
|
|
|
502
502
|
/** Same merge semantics as `set` — alias for HTTP-PATCH-prefering callers. */
|
|
503
503
|
async patch(productId, params) {
|
|
504
504
|
return this.http.call(
|
|
505
|
-
(signal) => this.http.client.PATCH(`/api/products/${productId}/portal-config`, {
|
|
505
|
+
(signal) => this.http.client.PATCH(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
506
506
|
body: params,
|
|
507
507
|
signal
|
|
508
508
|
}).then((r) => r)
|
|
@@ -514,11 +514,11 @@ var ProductPortalConfigResource = class {
|
|
|
514
514
|
* deleted, `{ removed: false }` when there was nothing to remove.
|
|
515
515
|
*
|
|
516
516
|
* @example
|
|
517
|
-
* await garu.products.portalConfig.clear(
|
|
517
|
+
* await garu.products.portalConfig.clear('b3f2c1e8-6e4a-4b9f-9d1c-2a1f6c3d4e5f');
|
|
518
518
|
*/
|
|
519
519
|
async clear(productId) {
|
|
520
520
|
return this.http.call(
|
|
521
|
-
(signal) => this.http.client.DELETE(`/api/products/${productId}/portal-config`, {
|
|
521
|
+
(signal) => this.http.client.DELETE(`/api/products/${encodeURIComponent(String(productId))}/portal-config`, {
|
|
522
522
|
signal
|
|
523
523
|
}).then((r) => r)
|
|
524
524
|
);
|
|
@@ -796,6 +796,32 @@ var ScheduledCharges = class {
|
|
|
796
796
|
}).then((r) => r)
|
|
797
797
|
);
|
|
798
798
|
}
|
|
799
|
+
/**
|
|
800
|
+
* Per-attempt billing log for the series (SPEC §4.2). One row per
|
|
801
|
+
* logical billing event — cycle 1 interactive charge, every silent
|
|
802
|
+
* charge attempt, every retry, every manual mark-paid. Carries the
|
|
803
|
+
* canonical `failureCode` for declines so you can audit billing
|
|
804
|
+
* outcomes without cross-referencing Transactions.
|
|
805
|
+
*
|
|
806
|
+
* @example
|
|
807
|
+
* const { data } = await garu.scheduledCharges.listAttempts('sch_abc', {
|
|
808
|
+
* cycleNumber: 3
|
|
809
|
+
* });
|
|
810
|
+
* const declines = data.filter((a) => a.status === 'declined');
|
|
811
|
+
*/
|
|
812
|
+
async listAttempts(id, params = {}) {
|
|
813
|
+
const qs = new URLSearchParams();
|
|
814
|
+
if (params.page !== void 0) qs.set("page", String(params.page));
|
|
815
|
+
if (params.limit !== void 0) qs.set("limit", String(params.limit));
|
|
816
|
+
if (params.cycleNumber !== void 0) qs.set("cycleNumber", String(params.cycleNumber));
|
|
817
|
+
const query = qs.toString();
|
|
818
|
+
const url = `/api/scheduled-charges/${id}/attempts${query ? `?${query}` : ""}`;
|
|
819
|
+
return this.http.call(
|
|
820
|
+
(signal) => this.http.client.GET(url, { signal }).then(
|
|
821
|
+
(r) => r
|
|
822
|
+
)
|
|
823
|
+
);
|
|
824
|
+
}
|
|
799
825
|
};
|
|
800
826
|
var webhooks = {
|
|
801
827
|
verify(params) {
|