@waffo/pancake-ts 0.1.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/dist/index.cjs ADDED
@@ -0,0 +1,757 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/index.ts
21
+ var index_exports = {};
22
+ __export(index_exports, {
23
+ BillingPeriod: () => BillingPeriod,
24
+ CheckoutSessionProductType: () => CheckoutSessionProductType,
25
+ EntityStatus: () => EntityStatus,
26
+ Environment: () => Environment,
27
+ ErrorLayer: () => ErrorLayer,
28
+ MediaType: () => MediaType,
29
+ OnetimeOrderStatus: () => OnetimeOrderStatus,
30
+ PaymentStatus: () => PaymentStatus,
31
+ ProductVersionStatus: () => ProductVersionStatus,
32
+ RefundStatus: () => RefundStatus,
33
+ RefundTicketStatus: () => RefundTicketStatus,
34
+ StoreRole: () => StoreRole,
35
+ SubscriptionOrderStatus: () => SubscriptionOrderStatus,
36
+ TaxCategory: () => TaxCategory,
37
+ WaffoPancake: () => WaffoPancake,
38
+ WaffoPancakeError: () => WaffoPancakeError,
39
+ WebhookEventType: () => WebhookEventType,
40
+ verifyWebhook: () => verifyWebhook
41
+ });
42
+ module.exports = __toCommonJS(index_exports);
43
+
44
+ // src/http-client.ts
45
+ var import_node_crypto2 = require("crypto");
46
+
47
+ // src/errors.ts
48
+ var WaffoPancakeError = class extends Error {
49
+ status;
50
+ errors;
51
+ constructor(status, errors) {
52
+ const rootCause = errors[0]?.message ?? "Unknown error";
53
+ super(rootCause);
54
+ this.name = "WaffoPancakeError";
55
+ this.status = status;
56
+ this.errors = errors;
57
+ }
58
+ };
59
+
60
+ // src/signing.ts
61
+ var import_node_crypto = require("crypto");
62
+ function signRequest(method, path, timestamp, body, privateKey) {
63
+ const bodyHash = (0, import_node_crypto.createHash)("sha256").update(body).digest("hex");
64
+ const canonicalRequest = `${method}
65
+ ${path}
66
+ ${timestamp}
67
+ ${bodyHash}`;
68
+ const sign = (0, import_node_crypto.createSign)("sha256");
69
+ sign.update(canonicalRequest);
70
+ return sign.sign(privateKey, "base64");
71
+ }
72
+
73
+ // src/http-client.ts
74
+ var DEFAULT_BASE_URL = "https://waffo-pancake-auth-service.vercel.app";
75
+ var HttpClient = class {
76
+ merchantId;
77
+ privateKey;
78
+ baseUrl;
79
+ _fetch;
80
+ constructor(config) {
81
+ this.merchantId = config.merchantId;
82
+ this.privateKey = config.privateKey;
83
+ this.baseUrl = (config.baseUrl ?? DEFAULT_BASE_URL).replace(/\/+$/, "");
84
+ this._fetch = config.fetch ?? fetch;
85
+ }
86
+ /**
87
+ * Send a signed POST request and return the parsed `data` field.
88
+ *
89
+ * Behavior:
90
+ * - Generates a deterministic `X-Idempotency-Key` from `merchantId + path + body` (same request produces same key)
91
+ * - Auto-builds RSA-SHA256 signature (`X-Merchant-Id` / `X-Timestamp` / `X-Signature`)
92
+ * - Unwraps the response envelope: returns `data` on success, throws `WaffoPancakeError` on failure
93
+ *
94
+ * @param path - API path (e.g. `/v1/actions/store/create-store`)
95
+ * @param body - Request body object
96
+ * @returns Parsed `data` field from the response
97
+ * @throws {WaffoPancakeError} When the API returns errors
98
+ */
99
+ async post(path, body) {
100
+ const bodyStr = JSON.stringify(body);
101
+ const timestamp = Math.floor(Date.now() / 1e3).toString();
102
+ const signature = signRequest("POST", path, timestamp, bodyStr, this.privateKey);
103
+ const response = await this._fetch(`${this.baseUrl}${path}`, {
104
+ method: "POST",
105
+ headers: {
106
+ "Content-Type": "application/json",
107
+ "X-Merchant-Id": this.merchantId,
108
+ "X-Timestamp": timestamp,
109
+ "X-Signature": signature,
110
+ "X-Idempotency-Key": (0, import_node_crypto2.createHash)("sha256").update(`${this.merchantId}:${path}:${bodyStr}`).digest("hex")
111
+ },
112
+ body: bodyStr
113
+ });
114
+ const result = await response.json();
115
+ if ("errors" in result && result.errors) {
116
+ throw new WaffoPancakeError(response.status, result.errors);
117
+ }
118
+ return result.data;
119
+ }
120
+ };
121
+
122
+ // src/resources/auth.ts
123
+ var AuthResource = class {
124
+ constructor(http) {
125
+ this.http = http;
126
+ }
127
+ /**
128
+ * Issue a session token for a buyer.
129
+ *
130
+ * @param params - Token issuance parameters
131
+ * @returns Issued session token with expiration
132
+ *
133
+ * @example
134
+ * const { token, expiresAt } = await client.auth.issueSessionToken({
135
+ * storeId: "store_xxx",
136
+ * buyerIdentity: "customer@example.com",
137
+ * });
138
+ */
139
+ async issueSessionToken(params) {
140
+ return this.http.post("/v1/actions/auth/issue-session-token", params);
141
+ }
142
+ };
143
+
144
+ // src/resources/checkout.ts
145
+ var CheckoutResource = class {
146
+ constructor(http) {
147
+ this.http = http;
148
+ }
149
+ /**
150
+ * Create a checkout session. Returns a URL to redirect the customer to.
151
+ *
152
+ * @param params - Checkout session parameters
153
+ * @returns Session ID, checkout URL, and expiration
154
+ *
155
+ * @example
156
+ * const session = await client.checkout.createSession({
157
+ * storeId: "store_xxx",
158
+ * productId: "prod_xxx",
159
+ * productType: "onetime",
160
+ * currency: "USD",
161
+ * buyerEmail: "customer@example.com",
162
+ * });
163
+ * // Redirect to session.checkoutUrl
164
+ */
165
+ async createSession(params) {
166
+ return this.http.post("/v1/actions/checkout/create-session", params);
167
+ }
168
+ };
169
+
170
+ // src/resources/graphql.ts
171
+ var GraphQLResource = class {
172
+ constructor(http) {
173
+ this.http = http;
174
+ }
175
+ /**
176
+ * Execute a GraphQL query (Query only, no Mutations).
177
+ *
178
+ * @param params - GraphQL query and optional variables
179
+ * @returns GraphQL response with data and optional errors
180
+ *
181
+ * @example
182
+ * const result = await client.graphql.query<{ stores: Array<{ id: string; name: string }> }>({
183
+ * query: `query { stores { id name status } }`,
184
+ * });
185
+ * console.log(result.data?.stores);
186
+ *
187
+ * @example
188
+ * const result = await client.graphql.query({
189
+ * query: `query ($id: ID!) { onetimeProduct(id: $id) { id name prices } }`,
190
+ * variables: { id: "prod_xxx" },
191
+ * });
192
+ */
193
+ async query(params) {
194
+ return this.http.post("/v1/graphql", params);
195
+ }
196
+ };
197
+
198
+ // src/resources/onetime-products.ts
199
+ var OnetimeProductsResource = class {
200
+ constructor(http) {
201
+ this.http = http;
202
+ }
203
+ /**
204
+ * Create a one-time product with multi-currency pricing.
205
+ *
206
+ * @param params - Product creation parameters
207
+ * @returns Created product detail
208
+ *
209
+ * @example
210
+ * const { product } = await client.onetimeProducts.create({
211
+ * storeId: "store_xxx",
212
+ * name: "E-Book",
213
+ * prices: { USD: { amount: 2900, taxIncluded: false, taxCategory: "digital_goods" } },
214
+ * });
215
+ */
216
+ async create(params) {
217
+ return this.http.post("/v1/actions/onetime-product/create-product", params);
218
+ }
219
+ /**
220
+ * Update a one-time product. Creates a new version; skips if unchanged.
221
+ *
222
+ * @param params - Product update parameters (all content fields required)
223
+ * @returns Updated product detail
224
+ *
225
+ * @example
226
+ * const { product } = await client.onetimeProducts.update({
227
+ * id: "prod_xxx",
228
+ * name: "E-Book v2",
229
+ * prices: { USD: { amount: 3900, taxIncluded: false, taxCategory: "digital_goods" } },
230
+ * });
231
+ */
232
+ async update(params) {
233
+ return this.http.post("/v1/actions/onetime-product/update-product", params);
234
+ }
235
+ /**
236
+ * Publish a one-time product's test version to production.
237
+ *
238
+ * @param params - Product to publish
239
+ * @returns Published product detail
240
+ *
241
+ * @example
242
+ * const { product } = await client.onetimeProducts.publish({ id: "prod_xxx" });
243
+ */
244
+ async publish(params) {
245
+ return this.http.post("/v1/actions/onetime-product/publish-product", params);
246
+ }
247
+ /**
248
+ * Update a one-time product's status (active/inactive).
249
+ *
250
+ * @param params - Status update parameters
251
+ * @returns Updated product detail
252
+ *
253
+ * @example
254
+ * const { product } = await client.onetimeProducts.updateStatus({
255
+ * id: "prod_xxx",
256
+ * status: ProductVersionStatus.Inactive,
257
+ * });
258
+ */
259
+ async updateStatus(params) {
260
+ return this.http.post("/v1/actions/onetime-product/update-status", params);
261
+ }
262
+ };
263
+
264
+ // src/resources/orders.ts
265
+ var OrdersResource = class {
266
+ constructor(http) {
267
+ this.http = http;
268
+ }
269
+ /**
270
+ * Cancel a subscription order.
271
+ *
272
+ * - pending -> canceled (immediate)
273
+ * - active/trialing -> canceling (PSP cancel, webhook updates later)
274
+ *
275
+ * @param params - Order to cancel
276
+ * @returns Order ID and resulting status
277
+ *
278
+ * @example
279
+ * const { orderId, status } = await client.orders.cancelSubscription({
280
+ * orderId: "order_xxx",
281
+ * });
282
+ * // status: "canceled" or "canceling"
283
+ */
284
+ async cancelSubscription(params) {
285
+ return this.http.post("/v1/actions/subscription-order/cancel-order", params);
286
+ }
287
+ };
288
+
289
+ // src/resources/store-merchants.ts
290
+ var StoreMerchantsResource = class {
291
+ constructor(http) {
292
+ this.http = http;
293
+ }
294
+ /**
295
+ * Add a merchant to a store.
296
+ *
297
+ * @param params - Merchant addition parameters
298
+ * @returns Added merchant details
299
+ *
300
+ * @example
301
+ * const result = await client.storeMerchants.add({
302
+ * storeId: "store_xxx",
303
+ * email: "member@example.com",
304
+ * role: "admin",
305
+ * });
306
+ */
307
+ async add(params) {
308
+ return this.http.post("/v1/actions/store-merchant/add-merchant", params);
309
+ }
310
+ /**
311
+ * Remove a merchant from a store.
312
+ *
313
+ * @param params - Merchant removal parameters
314
+ * @returns Removal confirmation
315
+ *
316
+ * @example
317
+ * const result = await client.storeMerchants.remove({
318
+ * storeId: "store_xxx",
319
+ * merchantId: "merchant_xxx",
320
+ * });
321
+ */
322
+ async remove(params) {
323
+ return this.http.post("/v1/actions/store-merchant/remove-merchant", params);
324
+ }
325
+ /**
326
+ * Update a merchant's role in a store.
327
+ *
328
+ * @param params - Role update parameters
329
+ * @returns Updated role details
330
+ *
331
+ * @example
332
+ * const result = await client.storeMerchants.updateRole({
333
+ * storeId: "store_xxx",
334
+ * merchantId: "merchant_xxx",
335
+ * role: "member",
336
+ * });
337
+ */
338
+ async updateRole(params) {
339
+ return this.http.post("/v1/actions/store-merchant/update-role", params);
340
+ }
341
+ };
342
+
343
+ // src/resources/stores.ts
344
+ var StoresResource = class {
345
+ constructor(http) {
346
+ this.http = http;
347
+ }
348
+ /**
349
+ * Create a new store. Slug is auto-generated from the name.
350
+ *
351
+ * @param params - Store creation parameters
352
+ * @returns Created store entity
353
+ *
354
+ * @example
355
+ * const { store } = await client.stores.create({ name: "My Store" });
356
+ */
357
+ async create(params) {
358
+ return this.http.post("/v1/actions/store/create-store", params);
359
+ }
360
+ /**
361
+ * Update an existing store's settings.
362
+ *
363
+ * @param params - Fields to update (only provided fields are changed)
364
+ * @returns Updated store entity
365
+ *
366
+ * @example
367
+ * const { store } = await client.stores.update({
368
+ * id: "store_xxx",
369
+ * name: "Updated Name",
370
+ * supportEmail: "help@example.com",
371
+ * });
372
+ */
373
+ async update(params) {
374
+ return this.http.post("/v1/actions/store/update-store", params);
375
+ }
376
+ /**
377
+ * Soft-delete a store. Only the owner can delete.
378
+ *
379
+ * @param params - Store to delete
380
+ * @returns Deleted store entity (with `deletedAt` set)
381
+ *
382
+ * @example
383
+ * const { store } = await client.stores.delete({ id: "store_xxx" });
384
+ */
385
+ async delete(params) {
386
+ return this.http.post("/v1/actions/store/delete-store", params);
387
+ }
388
+ };
389
+
390
+ // src/resources/subscription-product-groups.ts
391
+ var SubscriptionProductGroupsResource = class {
392
+ constructor(http) {
393
+ this.http = http;
394
+ }
395
+ /**
396
+ * Create a subscription product group for shared-trial or plan switching.
397
+ *
398
+ * @param params - Group creation parameters
399
+ * @returns Created group entity
400
+ *
401
+ * @example
402
+ * const { group } = await client.subscriptionProductGroups.create({
403
+ * storeId: "store_xxx",
404
+ * name: "Pro Plans",
405
+ * rules: { sharedTrial: true },
406
+ * productIds: ["prod_aaa", "prod_bbb"],
407
+ * });
408
+ */
409
+ async create(params) {
410
+ return this.http.post("/v1/actions/subscription-product-group/create-group", params);
411
+ }
412
+ /**
413
+ * Update a subscription product group. `productIds` is a full replacement.
414
+ *
415
+ * @param params - Group update parameters
416
+ * @returns Updated group entity
417
+ *
418
+ * @example
419
+ * const { group } = await client.subscriptionProductGroups.update({
420
+ * id: "group_xxx",
421
+ * productIds: ["prod_aaa", "prod_bbb", "prod_ccc"],
422
+ * });
423
+ */
424
+ async update(params) {
425
+ return this.http.post("/v1/actions/subscription-product-group/update-group", params);
426
+ }
427
+ /**
428
+ * Hard-delete a subscription product group.
429
+ *
430
+ * @param params - Group to delete
431
+ * @returns Deleted group entity
432
+ *
433
+ * @example
434
+ * const { group } = await client.subscriptionProductGroups.delete({ id: "group_xxx" });
435
+ */
436
+ async delete(params) {
437
+ return this.http.post("/v1/actions/subscription-product-group/delete-group", params);
438
+ }
439
+ /**
440
+ * Publish a test-environment group to production (upsert).
441
+ *
442
+ * @param params - Group to publish
443
+ * @returns Published group entity
444
+ *
445
+ * @example
446
+ * const { group } = await client.subscriptionProductGroups.publish({ id: "group_xxx" });
447
+ */
448
+ async publish(params) {
449
+ return this.http.post("/v1/actions/subscription-product-group/publish-group", params);
450
+ }
451
+ };
452
+
453
+ // src/resources/subscription-products.ts
454
+ var SubscriptionProductsResource = class {
455
+ constructor(http) {
456
+ this.http = http;
457
+ }
458
+ /**
459
+ * Create a subscription product with billing period and multi-currency pricing.
460
+ *
461
+ * @param params - Product creation parameters
462
+ * @returns Created product detail
463
+ *
464
+ * @example
465
+ * const { product } = await client.subscriptionProducts.create({
466
+ * storeId: "store_xxx",
467
+ * name: "Pro Plan",
468
+ * billingPeriod: "monthly",
469
+ * prices: { USD: { amount: 999, taxIncluded: false, taxCategory: "saas" } },
470
+ * });
471
+ */
472
+ async create(params) {
473
+ return this.http.post("/v1/actions/subscription-product/create-product", params);
474
+ }
475
+ /**
476
+ * Update a subscription product. Creates a new version; skips if unchanged.
477
+ *
478
+ * @param params - Product update parameters (all content fields required)
479
+ * @returns Updated product detail
480
+ *
481
+ * @example
482
+ * const { product } = await client.subscriptionProducts.update({
483
+ * id: "prod_xxx",
484
+ * name: "Pro Plan v2",
485
+ * billingPeriod: "monthly",
486
+ * prices: { USD: { amount: 1499, taxIncluded: false, taxCategory: "saas" } },
487
+ * });
488
+ */
489
+ async update(params) {
490
+ return this.http.post("/v1/actions/subscription-product/update-product", params);
491
+ }
492
+ /**
493
+ * Publish a subscription product's test version to production.
494
+ *
495
+ * @param params - Product to publish
496
+ * @returns Published product detail
497
+ *
498
+ * @example
499
+ * const { product } = await client.subscriptionProducts.publish({ id: "prod_xxx" });
500
+ */
501
+ async publish(params) {
502
+ return this.http.post("/v1/actions/subscription-product/publish-product", params);
503
+ }
504
+ /**
505
+ * Update a subscription product's status (active/inactive).
506
+ *
507
+ * @param params - Status update parameters
508
+ * @returns Updated product detail
509
+ *
510
+ * @example
511
+ * const { product } = await client.subscriptionProducts.updateStatus({
512
+ * id: "prod_xxx",
513
+ * status: ProductVersionStatus.Active,
514
+ * });
515
+ */
516
+ async updateStatus(params) {
517
+ return this.http.post("/v1/actions/subscription-product/update-status", params);
518
+ }
519
+ };
520
+
521
+ // src/client.ts
522
+ var WaffoPancake = class {
523
+ http;
524
+ auth;
525
+ stores;
526
+ storeMerchants;
527
+ onetimeProducts;
528
+ subscriptionProducts;
529
+ subscriptionProductGroups;
530
+ orders;
531
+ checkout;
532
+ graphql;
533
+ constructor(config) {
534
+ this.http = new HttpClient(config);
535
+ this.auth = new AuthResource(this.http);
536
+ this.stores = new StoresResource(this.http);
537
+ this.storeMerchants = new StoreMerchantsResource(this.http);
538
+ this.onetimeProducts = new OnetimeProductsResource(this.http);
539
+ this.subscriptionProducts = new SubscriptionProductsResource(this.http);
540
+ this.subscriptionProductGroups = new SubscriptionProductGroupsResource(this.http);
541
+ this.orders = new OrdersResource(this.http);
542
+ this.checkout = new CheckoutResource(this.http);
543
+ this.graphql = new GraphQLResource(this.http);
544
+ }
545
+ };
546
+
547
+ // src/webhooks.ts
548
+ var import_node_crypto3 = require("crypto");
549
+ var DEFAULT_TOLERANCE_MS = 5 * 60 * 1e3;
550
+ var TEST_PUBLIC_KEY = `-----BEGIN PUBLIC KEY-----
551
+ MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAxnmRY6yMMA3lVqmAU6ZG
552
+ b1sjL/+r/z6E+ZjkXaDAKiqOhk9rpazni0bNsGXwmftTPk9jy2wn+j6JHODD/WH/
553
+ SCnSfvKkLIjy4Hk7BuCgB174C0ydan7J+KgXLkOwgCAxxB68t2tezldwo74ZpXgn
554
+ F49opzMvQ9prEwIAWOE+kV9iK6gx/AckSMtHIHpUesoPDkldpmFHlB2qpf1vsFTZ
555
+ 5kD6DmGl+2GIVK01aChy2lk8pLv0yUMu18v44sLkO5M44TkGPJD9qG09wrvVG2wp
556
+ OTVCn1n5pP8P+HRLcgzbUB3OlZVfdFurn6EZwtyL4ZD9kdkQ4EZE/9inKcp3c1h4
557
+ xwIDAQAB
558
+ -----END PUBLIC KEY-----`;
559
+ var PROD_PUBLIC_KEY = `-----BEGIN PUBLIC KEY-----
560
+ MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAz+xApdTIb4ua+DgZKQ54
561
+ iBsD82ybyhGCLRETONW4Jgbb3A8DUM1LqBk6r/CmTOCHqLalTQHNigvP3R5zkDNX
562
+ iRJz6gA4MJ/+8K0+mnEE2RISQzN+Qu65TNd6svb+INm/kMaftY4uIXr6y6kchtTJ
563
+ dwnQhcKdAL2v7h7IFnkVelQsKxDdb2PqX8xX/qwd01iXvMcpCCaXovUwZsxH2QN5
564
+ ZKBTseJivbhUeyJCco4fdUyxOMHe2ybCVhyvim2uxAl1nkvL5L8RCWMCAV55LLo0
565
+ 9OhmLahz/DYNu13YLVP6dvIT09ZFBYU6Owj1NxdinTynlJCFS9VYwBgmftosSE1U
566
+ dwIDAQAB
567
+ -----END PUBLIC KEY-----`;
568
+ function parseSignatureHeader(header) {
569
+ let t = "";
570
+ let v1 = "";
571
+ for (const pair of header.split(",")) {
572
+ const eqIdx = pair.indexOf("=");
573
+ if (eqIdx === -1) continue;
574
+ const key = pair.slice(0, eqIdx).trim();
575
+ const value = pair.slice(eqIdx + 1).trim();
576
+ if (key === "t") t = value;
577
+ else if (key === "v1") v1 = value;
578
+ }
579
+ return { t, v1 };
580
+ }
581
+ function rsaVerify(signatureInput, v1, publicKey) {
582
+ const verifier = (0, import_node_crypto3.createVerify)("RSA-SHA256");
583
+ verifier.update(signatureInput);
584
+ return verifier.verify(publicKey, v1, "base64");
585
+ }
586
+ function verifyWebhook(payload, signatureHeader, options) {
587
+ if (!signatureHeader) {
588
+ throw new Error("Missing X-Waffo-Signature header");
589
+ }
590
+ const { t, v1 } = parseSignatureHeader(signatureHeader);
591
+ if (!t || !v1) {
592
+ throw new Error("Malformed X-Waffo-Signature header: missing t or v1");
593
+ }
594
+ const toleranceMs = options?.toleranceMs ?? DEFAULT_TOLERANCE_MS;
595
+ if (toleranceMs > 0) {
596
+ const timestampMs = Number(t);
597
+ if (Number.isNaN(timestampMs)) {
598
+ throw new Error("Invalid timestamp in X-Waffo-Signature header");
599
+ }
600
+ if (Math.abs(Date.now() - timestampMs) > toleranceMs) {
601
+ throw new Error("Webhook timestamp outside tolerance window (possible replay attack)");
602
+ }
603
+ }
604
+ const signatureInput = `${t}.${payload}`;
605
+ const env = options?.environment;
606
+ if (env === "test") {
607
+ if (!rsaVerify(signatureInput, v1, TEST_PUBLIC_KEY)) {
608
+ throw new Error("Invalid webhook signature (test key)");
609
+ }
610
+ } else if (env === "prod") {
611
+ if (!rsaVerify(signatureInput, v1, PROD_PUBLIC_KEY)) {
612
+ throw new Error("Invalid webhook signature (prod key)");
613
+ }
614
+ } else {
615
+ const prodValid = rsaVerify(signatureInput, v1, PROD_PUBLIC_KEY);
616
+ if (!prodValid) {
617
+ const testValid = rsaVerify(signatureInput, v1, TEST_PUBLIC_KEY);
618
+ if (!testValid) {
619
+ throw new Error("Invalid webhook signature (tried both prod and test keys)");
620
+ }
621
+ }
622
+ }
623
+ return JSON.parse(payload);
624
+ }
625
+
626
+ // src/types.ts
627
+ var Environment = /* @__PURE__ */ ((Environment2) => {
628
+ Environment2["Test"] = "test";
629
+ Environment2["Prod"] = "prod";
630
+ return Environment2;
631
+ })(Environment || {});
632
+ var TaxCategory = /* @__PURE__ */ ((TaxCategory2) => {
633
+ TaxCategory2["DigitalGoods"] = "digital_goods";
634
+ TaxCategory2["SaaS"] = "saas";
635
+ TaxCategory2["Software"] = "software";
636
+ TaxCategory2["Ebook"] = "ebook";
637
+ TaxCategory2["OnlineCourse"] = "online_course";
638
+ TaxCategory2["Consulting"] = "consulting";
639
+ TaxCategory2["ProfessionalService"] = "professional_service";
640
+ return TaxCategory2;
641
+ })(TaxCategory || {});
642
+ var BillingPeriod = /* @__PURE__ */ ((BillingPeriod2) => {
643
+ BillingPeriod2["Weekly"] = "weekly";
644
+ BillingPeriod2["Monthly"] = "monthly";
645
+ BillingPeriod2["Quarterly"] = "quarterly";
646
+ BillingPeriod2["Yearly"] = "yearly";
647
+ return BillingPeriod2;
648
+ })(BillingPeriod || {});
649
+ var ProductVersionStatus = /* @__PURE__ */ ((ProductVersionStatus2) => {
650
+ ProductVersionStatus2["Active"] = "active";
651
+ ProductVersionStatus2["Inactive"] = "inactive";
652
+ return ProductVersionStatus2;
653
+ })(ProductVersionStatus || {});
654
+ var EntityStatus = /* @__PURE__ */ ((EntityStatus2) => {
655
+ EntityStatus2["Active"] = "active";
656
+ EntityStatus2["Inactive"] = "inactive";
657
+ EntityStatus2["Suspended"] = "suspended";
658
+ return EntityStatus2;
659
+ })(EntityStatus || {});
660
+ var StoreRole = /* @__PURE__ */ ((StoreRole2) => {
661
+ StoreRole2["Owner"] = "owner";
662
+ StoreRole2["Admin"] = "admin";
663
+ StoreRole2["Member"] = "member";
664
+ return StoreRole2;
665
+ })(StoreRole || {});
666
+ var OnetimeOrderStatus = /* @__PURE__ */ ((OnetimeOrderStatus2) => {
667
+ OnetimeOrderStatus2["Pending"] = "pending";
668
+ OnetimeOrderStatus2["Completed"] = "completed";
669
+ OnetimeOrderStatus2["Canceled"] = "canceled";
670
+ return OnetimeOrderStatus2;
671
+ })(OnetimeOrderStatus || {});
672
+ var SubscriptionOrderStatus = /* @__PURE__ */ ((SubscriptionOrderStatus2) => {
673
+ SubscriptionOrderStatus2["Pending"] = "pending";
674
+ SubscriptionOrderStatus2["Active"] = "active";
675
+ SubscriptionOrderStatus2["Canceling"] = "canceling";
676
+ SubscriptionOrderStatus2["Canceled"] = "canceled";
677
+ SubscriptionOrderStatus2["PastDue"] = "past_due";
678
+ SubscriptionOrderStatus2["Expired"] = "expired";
679
+ return SubscriptionOrderStatus2;
680
+ })(SubscriptionOrderStatus || {});
681
+ var PaymentStatus = /* @__PURE__ */ ((PaymentStatus2) => {
682
+ PaymentStatus2["Pending"] = "pending";
683
+ PaymentStatus2["Succeeded"] = "succeeded";
684
+ PaymentStatus2["Failed"] = "failed";
685
+ PaymentStatus2["Canceled"] = "canceled";
686
+ return PaymentStatus2;
687
+ })(PaymentStatus || {});
688
+ var RefundTicketStatus = /* @__PURE__ */ ((RefundTicketStatus2) => {
689
+ RefundTicketStatus2["Pending"] = "pending";
690
+ RefundTicketStatus2["Approved"] = "approved";
691
+ RefundTicketStatus2["Rejected"] = "rejected";
692
+ RefundTicketStatus2["Processing"] = "processing";
693
+ RefundTicketStatus2["Succeeded"] = "succeeded";
694
+ RefundTicketStatus2["Failed"] = "failed";
695
+ return RefundTicketStatus2;
696
+ })(RefundTicketStatus || {});
697
+ var RefundStatus = /* @__PURE__ */ ((RefundStatus2) => {
698
+ RefundStatus2["Succeeded"] = "succeeded";
699
+ RefundStatus2["Failed"] = "failed";
700
+ return RefundStatus2;
701
+ })(RefundStatus || {});
702
+ var MediaType = /* @__PURE__ */ ((MediaType2) => {
703
+ MediaType2["Image"] = "image";
704
+ MediaType2["Video"] = "video";
705
+ return MediaType2;
706
+ })(MediaType || {});
707
+ var CheckoutSessionProductType = /* @__PURE__ */ ((CheckoutSessionProductType2) => {
708
+ CheckoutSessionProductType2["Onetime"] = "onetime";
709
+ CheckoutSessionProductType2["Subscription"] = "subscription";
710
+ return CheckoutSessionProductType2;
711
+ })(CheckoutSessionProductType || {});
712
+ var ErrorLayer = /* @__PURE__ */ ((ErrorLayer2) => {
713
+ ErrorLayer2["Gateway"] = "gateway";
714
+ ErrorLayer2["User"] = "user";
715
+ ErrorLayer2["Store"] = "store";
716
+ ErrorLayer2["Product"] = "product";
717
+ ErrorLayer2["Order"] = "order";
718
+ ErrorLayer2["GraphQL"] = "graphql";
719
+ ErrorLayer2["Resource"] = "resource";
720
+ ErrorLayer2["Email"] = "email";
721
+ return ErrorLayer2;
722
+ })(ErrorLayer || {});
723
+ var WebhookEventType = /* @__PURE__ */ ((WebhookEventType2) => {
724
+ WebhookEventType2["OrderCompleted"] = "order.completed";
725
+ WebhookEventType2["SubscriptionActivated"] = "subscription.activated";
726
+ WebhookEventType2["SubscriptionPaymentSucceeded"] = "subscription.payment_succeeded";
727
+ WebhookEventType2["SubscriptionCanceling"] = "subscription.canceling";
728
+ WebhookEventType2["SubscriptionUncanceled"] = "subscription.uncanceled";
729
+ WebhookEventType2["SubscriptionUpdated"] = "subscription.updated";
730
+ WebhookEventType2["SubscriptionCanceled"] = "subscription.canceled";
731
+ WebhookEventType2["SubscriptionPastDue"] = "subscription.past_due";
732
+ WebhookEventType2["RefundSucceeded"] = "refund.succeeded";
733
+ WebhookEventType2["RefundFailed"] = "refund.failed";
734
+ return WebhookEventType2;
735
+ })(WebhookEventType || {});
736
+ // Annotate the CommonJS export names for ESM import in node:
737
+ 0 && (module.exports = {
738
+ BillingPeriod,
739
+ CheckoutSessionProductType,
740
+ EntityStatus,
741
+ Environment,
742
+ ErrorLayer,
743
+ MediaType,
744
+ OnetimeOrderStatus,
745
+ PaymentStatus,
746
+ ProductVersionStatus,
747
+ RefundStatus,
748
+ RefundTicketStatus,
749
+ StoreRole,
750
+ SubscriptionOrderStatus,
751
+ TaxCategory,
752
+ WaffoPancake,
753
+ WaffoPancakeError,
754
+ WebhookEventType,
755
+ verifyWebhook
756
+ });
757
+ //# sourceMappingURL=index.cjs.map