@polar-sh/better-auth 0.1.1 → 1.0.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 +360 -60
- package/dist/index.cjs +644 -386
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1247 -253
- package/dist/index.d.ts +1247 -253
- package/dist/index.js +642 -385
- package/dist/index.js.map +1 -1
- package/package.json +6 -6
package/dist/index.js
CHANGED
|
@@ -1,379 +1,5 @@
|
|
|
1
|
-
// src/endpoints/checkout.ts
|
|
2
|
-
import { APIError, getSessionFromCtx } from "better-auth/api";
|
|
3
|
-
import { createAuthEndpoint } from "better-auth/plugins";
|
|
4
|
-
import { z } from "zod";
|
|
5
|
-
var checkout = (options) => createAuthEndpoint(
|
|
6
|
-
"/checkout",
|
|
7
|
-
{
|
|
8
|
-
method: "GET",
|
|
9
|
-
query: z.object({
|
|
10
|
-
products: z.union([z.array(z.string()), z.string()])
|
|
11
|
-
})
|
|
12
|
-
},
|
|
13
|
-
async (ctx) => {
|
|
14
|
-
if (!options.checkout?.enabled) {
|
|
15
|
-
throw new APIError("BAD_REQUEST", {
|
|
16
|
-
message: "Checkout is not enabled"
|
|
17
|
-
});
|
|
18
|
-
}
|
|
19
|
-
const products = ctx.query.products;
|
|
20
|
-
const session = await getSessionFromCtx(ctx);
|
|
21
|
-
try {
|
|
22
|
-
const checkout2 = await options.client.checkouts.create({
|
|
23
|
-
customerExternalId: session?.user.id,
|
|
24
|
-
products: Array.isArray(products) ? products : [products],
|
|
25
|
-
successUrl: options.checkout.successUrl ? new URL(options.checkout.successUrl, ctx.request?.url).toString() : void 0
|
|
26
|
-
});
|
|
27
|
-
return ctx.redirect(checkout2.url);
|
|
28
|
-
} catch (e) {
|
|
29
|
-
if (e instanceof Error) {
|
|
30
|
-
ctx.context.logger.error(
|
|
31
|
-
`Polar checkout creation failed. Error: ${e.message}`
|
|
32
|
-
);
|
|
33
|
-
}
|
|
34
|
-
throw new APIError("INTERNAL_SERVER_ERROR", {
|
|
35
|
-
message: "Checkout creation failed"
|
|
36
|
-
});
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
);
|
|
40
|
-
var checkoutWithSlug = (options) => createAuthEndpoint(
|
|
41
|
-
"/checkout/:slug",
|
|
42
|
-
{
|
|
43
|
-
method: "GET",
|
|
44
|
-
params: z.object({
|
|
45
|
-
slug: z.string()
|
|
46
|
-
})
|
|
47
|
-
},
|
|
48
|
-
async (ctx) => {
|
|
49
|
-
if (!options.checkout?.enabled) {
|
|
50
|
-
throw new APIError("BAD_REQUEST", {
|
|
51
|
-
message: "Checkout is not enabled"
|
|
52
|
-
});
|
|
53
|
-
}
|
|
54
|
-
const products = await (typeof options.checkout.products === "function" ? options.checkout.products() : options.checkout.products);
|
|
55
|
-
const productId = products.find(
|
|
56
|
-
(product) => product.slug === ctx.params?.["slug"]
|
|
57
|
-
)?.productId;
|
|
58
|
-
if (!productId) {
|
|
59
|
-
throw new APIError("BAD_REQUEST", {
|
|
60
|
-
message: "Product Id not found"
|
|
61
|
-
});
|
|
62
|
-
}
|
|
63
|
-
const session = await getSessionFromCtx(ctx);
|
|
64
|
-
try {
|
|
65
|
-
const checkout2 = await options.client.checkouts.create({
|
|
66
|
-
customerExternalId: session?.user.id,
|
|
67
|
-
products: [productId],
|
|
68
|
-
successUrl: options.checkout.successUrl ? new URL(options.checkout.successUrl, ctx.request?.url).toString() : void 0
|
|
69
|
-
});
|
|
70
|
-
return ctx.redirect(checkout2.url);
|
|
71
|
-
} catch (e) {
|
|
72
|
-
if (e instanceof Error) {
|
|
73
|
-
ctx.context.logger.error(
|
|
74
|
-
`Polar checkout creation failed. Error: ${e.message}`
|
|
75
|
-
);
|
|
76
|
-
}
|
|
77
|
-
throw new APIError("INTERNAL_SERVER_ERROR", {
|
|
78
|
-
message: "Checkout creation failed"
|
|
79
|
-
});
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
);
|
|
83
|
-
|
|
84
|
-
// src/endpoints/customerPortal.ts
|
|
85
|
-
import { APIError as APIError2, sessionMiddleware } from "better-auth/api";
|
|
86
|
-
import { createAuthEndpoint as createAuthEndpoint2 } from "better-auth/plugins";
|
|
87
|
-
var customerPortal = (options) => createAuthEndpoint2(
|
|
88
|
-
"/portal",
|
|
89
|
-
{
|
|
90
|
-
method: "GET",
|
|
91
|
-
use: [sessionMiddleware]
|
|
92
|
-
},
|
|
93
|
-
async (ctx) => {
|
|
94
|
-
if (!options.enableCustomerPortal) {
|
|
95
|
-
throw new APIError2("BAD_REQUEST", {
|
|
96
|
-
message: "Customer portal is not enabled"
|
|
97
|
-
});
|
|
98
|
-
}
|
|
99
|
-
if (!ctx.context.session?.user.id) {
|
|
100
|
-
throw new APIError2("BAD_REQUEST", {
|
|
101
|
-
message: "User not found"
|
|
102
|
-
});
|
|
103
|
-
}
|
|
104
|
-
try {
|
|
105
|
-
const customerSession = await options.client.customerSessions.create({
|
|
106
|
-
customerExternalId: ctx.context.session?.user.id
|
|
107
|
-
});
|
|
108
|
-
return ctx.redirect(customerSession.customerPortalUrl);
|
|
109
|
-
} catch (e) {
|
|
110
|
-
if (e instanceof Error) {
|
|
111
|
-
ctx.context.logger.error(
|
|
112
|
-
`Polar customer portal creation failed. Error: ${e.message}`
|
|
113
|
-
);
|
|
114
|
-
}
|
|
115
|
-
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
116
|
-
message: "Customer portal creation failed"
|
|
117
|
-
});
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
);
|
|
121
|
-
|
|
122
|
-
// src/endpoints/customerState.ts
|
|
123
|
-
import { APIError as APIError3, sessionMiddleware as sessionMiddleware2 } from "better-auth/api";
|
|
124
|
-
import { createAuthEndpoint as createAuthEndpoint3 } from "better-auth/plugins";
|
|
125
|
-
var customerState = (options) => createAuthEndpoint3(
|
|
126
|
-
"/state",
|
|
127
|
-
{
|
|
128
|
-
method: "GET",
|
|
129
|
-
use: [sessionMiddleware2]
|
|
130
|
-
},
|
|
131
|
-
async (ctx) => {
|
|
132
|
-
if (!ctx.context.session.user.id) {
|
|
133
|
-
throw new APIError3("BAD_REQUEST", {
|
|
134
|
-
message: "User not found"
|
|
135
|
-
});
|
|
136
|
-
}
|
|
137
|
-
try {
|
|
138
|
-
const state = await options.client.customers.getStateExternal({
|
|
139
|
-
externalId: ctx.context.session?.user.id
|
|
140
|
-
});
|
|
141
|
-
return ctx.json(state);
|
|
142
|
-
} catch (e) {
|
|
143
|
-
if (e instanceof Error) {
|
|
144
|
-
ctx.context.logger.error(
|
|
145
|
-
`Polar subscriptions list failed. Error: ${e.message}`
|
|
146
|
-
);
|
|
147
|
-
}
|
|
148
|
-
throw new APIError3("INTERNAL_SERVER_ERROR", {
|
|
149
|
-
message: "Subscriptions list failed"
|
|
150
|
-
});
|
|
151
|
-
}
|
|
152
|
-
}
|
|
153
|
-
);
|
|
154
|
-
|
|
155
|
-
// src/endpoints/webhooks.ts
|
|
156
|
-
import { validateEvent } from "@polar-sh/sdk/webhooks";
|
|
157
|
-
import { APIError as APIError4 } from "better-auth/api";
|
|
158
|
-
import { createAuthEndpoint as createAuthEndpoint4 } from "better-auth/plugins";
|
|
159
|
-
var webhooks = (options) => createAuthEndpoint4(
|
|
160
|
-
"/polar/webhooks",
|
|
161
|
-
{
|
|
162
|
-
method: "POST",
|
|
163
|
-
metadata: {
|
|
164
|
-
isAction: false
|
|
165
|
-
},
|
|
166
|
-
cloneRequest: true
|
|
167
|
-
},
|
|
168
|
-
async (ctx) => {
|
|
169
|
-
const { webhooks: webhooks2 } = options;
|
|
170
|
-
if (!webhooks2) {
|
|
171
|
-
throw new APIError4("NOT_FOUND", {
|
|
172
|
-
message: "Webhooks not enabled"
|
|
173
|
-
});
|
|
174
|
-
}
|
|
175
|
-
const {
|
|
176
|
-
secret,
|
|
177
|
-
onPayload,
|
|
178
|
-
onCheckoutCreated,
|
|
179
|
-
onCheckoutUpdated,
|
|
180
|
-
onOrderCreated,
|
|
181
|
-
onOrderRefunded,
|
|
182
|
-
onRefundCreated,
|
|
183
|
-
onRefundUpdated,
|
|
184
|
-
onSubscriptionCreated,
|
|
185
|
-
onSubscriptionUpdated,
|
|
186
|
-
onSubscriptionActive,
|
|
187
|
-
onSubscriptionCanceled,
|
|
188
|
-
onSubscriptionRevoked,
|
|
189
|
-
onSubscriptionUncanceled,
|
|
190
|
-
onProductCreated,
|
|
191
|
-
onProductUpdated,
|
|
192
|
-
onOrganizationUpdated,
|
|
193
|
-
onBenefitCreated,
|
|
194
|
-
onBenefitUpdated,
|
|
195
|
-
onBenefitGrantCreated,
|
|
196
|
-
onBenefitGrantUpdated,
|
|
197
|
-
onBenefitGrantRevoked,
|
|
198
|
-
onCustomerCreated,
|
|
199
|
-
onCustomerUpdated,
|
|
200
|
-
onCustomerDeleted,
|
|
201
|
-
onCustomerStateChanged
|
|
202
|
-
} = webhooks2;
|
|
203
|
-
if (!ctx.request?.body) {
|
|
204
|
-
throw new APIError4("INTERNAL_SERVER_ERROR");
|
|
205
|
-
}
|
|
206
|
-
const buf = await ctx.request.text();
|
|
207
|
-
let event;
|
|
208
|
-
try {
|
|
209
|
-
if (!secret) {
|
|
210
|
-
throw new APIError4("INTERNAL_SERVER_ERROR", {
|
|
211
|
-
message: "Polar webhook secret not found"
|
|
212
|
-
});
|
|
213
|
-
}
|
|
214
|
-
const headers = {
|
|
215
|
-
"webhook-id": ctx.request.headers.get("webhook-id"),
|
|
216
|
-
"webhook-timestamp": ctx.request.headers.get(
|
|
217
|
-
"webhook-timestamp"
|
|
218
|
-
),
|
|
219
|
-
"webhook-signature": ctx.request.headers.get(
|
|
220
|
-
"webhook-signature"
|
|
221
|
-
)
|
|
222
|
-
};
|
|
223
|
-
event = validateEvent(buf, headers, secret);
|
|
224
|
-
} catch (err) {
|
|
225
|
-
if (err instanceof Error) {
|
|
226
|
-
ctx.context.logger.error(`${err.message}`);
|
|
227
|
-
throw new APIError4("BAD_REQUEST", {
|
|
228
|
-
message: `Webhook Error: ${err.message}`
|
|
229
|
-
});
|
|
230
|
-
}
|
|
231
|
-
throw new APIError4("BAD_REQUEST", {
|
|
232
|
-
message: `Webhook Error: ${err}`
|
|
233
|
-
});
|
|
234
|
-
}
|
|
235
|
-
try {
|
|
236
|
-
if (onPayload) {
|
|
237
|
-
onPayload(event);
|
|
238
|
-
}
|
|
239
|
-
switch (event.type) {
|
|
240
|
-
case "checkout.created":
|
|
241
|
-
if (onCheckoutCreated) {
|
|
242
|
-
onCheckoutCreated(event);
|
|
243
|
-
}
|
|
244
|
-
break;
|
|
245
|
-
case "checkout.updated":
|
|
246
|
-
if (onCheckoutUpdated) {
|
|
247
|
-
onCheckoutUpdated(event);
|
|
248
|
-
}
|
|
249
|
-
break;
|
|
250
|
-
case "order.created":
|
|
251
|
-
if (onOrderCreated) {
|
|
252
|
-
onOrderCreated(event);
|
|
253
|
-
}
|
|
254
|
-
break;
|
|
255
|
-
case "subscription.created":
|
|
256
|
-
if (onSubscriptionCreated) {
|
|
257
|
-
onSubscriptionCreated(event);
|
|
258
|
-
}
|
|
259
|
-
break;
|
|
260
|
-
case "subscription.updated":
|
|
261
|
-
if (onSubscriptionUpdated) {
|
|
262
|
-
onSubscriptionUpdated(event);
|
|
263
|
-
}
|
|
264
|
-
break;
|
|
265
|
-
case "subscription.active":
|
|
266
|
-
if (onSubscriptionActive) {
|
|
267
|
-
onSubscriptionActive(event);
|
|
268
|
-
}
|
|
269
|
-
break;
|
|
270
|
-
case "subscription.canceled":
|
|
271
|
-
if (onSubscriptionCanceled) {
|
|
272
|
-
onSubscriptionCanceled(event);
|
|
273
|
-
}
|
|
274
|
-
break;
|
|
275
|
-
case "subscription.uncanceled":
|
|
276
|
-
if (onSubscriptionUncanceled) {
|
|
277
|
-
onSubscriptionUncanceled(event);
|
|
278
|
-
}
|
|
279
|
-
break;
|
|
280
|
-
case "subscription.revoked":
|
|
281
|
-
if (onSubscriptionRevoked) {
|
|
282
|
-
onSubscriptionRevoked(event);
|
|
283
|
-
}
|
|
284
|
-
break;
|
|
285
|
-
case "product.created":
|
|
286
|
-
if (onProductCreated) {
|
|
287
|
-
onProductCreated(event);
|
|
288
|
-
}
|
|
289
|
-
break;
|
|
290
|
-
case "product.updated":
|
|
291
|
-
if (onProductUpdated) {
|
|
292
|
-
onProductUpdated(event);
|
|
293
|
-
}
|
|
294
|
-
break;
|
|
295
|
-
case "organization.updated":
|
|
296
|
-
if (onOrganizationUpdated) {
|
|
297
|
-
onOrganizationUpdated(event);
|
|
298
|
-
}
|
|
299
|
-
break;
|
|
300
|
-
case "benefit.created":
|
|
301
|
-
if (onBenefitCreated) {
|
|
302
|
-
onBenefitCreated(event);
|
|
303
|
-
}
|
|
304
|
-
break;
|
|
305
|
-
case "benefit.updated":
|
|
306
|
-
if (onBenefitUpdated) {
|
|
307
|
-
onBenefitUpdated(event);
|
|
308
|
-
}
|
|
309
|
-
break;
|
|
310
|
-
case "benefit_grant.created":
|
|
311
|
-
if (onBenefitGrantCreated) {
|
|
312
|
-
onBenefitGrantCreated(event);
|
|
313
|
-
}
|
|
314
|
-
break;
|
|
315
|
-
case "benefit_grant.updated":
|
|
316
|
-
if (onBenefitGrantUpdated) {
|
|
317
|
-
onBenefitGrantUpdated(event);
|
|
318
|
-
}
|
|
319
|
-
break;
|
|
320
|
-
case "benefit_grant.revoked":
|
|
321
|
-
if (onBenefitGrantRevoked) {
|
|
322
|
-
onBenefitGrantRevoked(event);
|
|
323
|
-
}
|
|
324
|
-
break;
|
|
325
|
-
case "order.refunded":
|
|
326
|
-
if (onOrderRefunded) {
|
|
327
|
-
onOrderRefunded(event);
|
|
328
|
-
}
|
|
329
|
-
break;
|
|
330
|
-
case "refund.created":
|
|
331
|
-
if (onRefundCreated) {
|
|
332
|
-
onRefundCreated(event);
|
|
333
|
-
}
|
|
334
|
-
break;
|
|
335
|
-
case "refund.updated":
|
|
336
|
-
if (onRefundUpdated) {
|
|
337
|
-
onRefundUpdated(event);
|
|
338
|
-
}
|
|
339
|
-
break;
|
|
340
|
-
case "customer.created":
|
|
341
|
-
if (onCustomerCreated) {
|
|
342
|
-
onCustomerCreated(event);
|
|
343
|
-
}
|
|
344
|
-
break;
|
|
345
|
-
case "customer.updated":
|
|
346
|
-
if (onCustomerUpdated) {
|
|
347
|
-
onCustomerUpdated(event);
|
|
348
|
-
}
|
|
349
|
-
break;
|
|
350
|
-
case "customer.deleted":
|
|
351
|
-
if (onCustomerDeleted) {
|
|
352
|
-
onCustomerDeleted(event);
|
|
353
|
-
}
|
|
354
|
-
break;
|
|
355
|
-
case "customer.state_changed":
|
|
356
|
-
if (onCustomerStateChanged) {
|
|
357
|
-
onCustomerStateChanged(event);
|
|
358
|
-
}
|
|
359
|
-
break;
|
|
360
|
-
}
|
|
361
|
-
} catch (e) {
|
|
362
|
-
if (e instanceof Error) {
|
|
363
|
-
ctx.context.logger.error(`Polar webhook failed. Error: ${e.message}`);
|
|
364
|
-
} else {
|
|
365
|
-
ctx.context.logger.error(`Polar webhook failed. Error: ${e}`);
|
|
366
|
-
}
|
|
367
|
-
throw new APIError4("BAD_REQUEST", {
|
|
368
|
-
message: "Webhook error: See server logs for more information."
|
|
369
|
-
});
|
|
370
|
-
}
|
|
371
|
-
return ctx.json({ received: true });
|
|
372
|
-
}
|
|
373
|
-
);
|
|
374
|
-
|
|
375
1
|
// src/hooks/customer.ts
|
|
376
|
-
import { APIError
|
|
2
|
+
import { APIError } from "better-auth/api";
|
|
377
3
|
var onUserCreate = (options) => async (user, ctx) => {
|
|
378
4
|
if (ctx && options.createCustomerOnSignUp) {
|
|
379
5
|
try {
|
|
@@ -388,7 +14,8 @@ var onUserCreate = (options) => async (user, ctx) => {
|
|
|
388
14
|
await options.client.customers.update({
|
|
389
15
|
id: existingCustomer.id,
|
|
390
16
|
customerUpdate: {
|
|
391
|
-
externalId: user.id
|
|
17
|
+
externalId: user.id,
|
|
18
|
+
...params
|
|
392
19
|
}
|
|
393
20
|
});
|
|
394
21
|
}
|
|
@@ -402,11 +29,11 @@ var onUserCreate = (options) => async (user, ctx) => {
|
|
|
402
29
|
}
|
|
403
30
|
} catch (e) {
|
|
404
31
|
if (e instanceof Error) {
|
|
405
|
-
throw new
|
|
32
|
+
throw new APIError("INTERNAL_SERVER_ERROR", {
|
|
406
33
|
message: `Polar customer creation failed. Error: ${e.message}`
|
|
407
34
|
});
|
|
408
35
|
}
|
|
409
|
-
throw new
|
|
36
|
+
throw new APIError("INTERNAL_SERVER_ERROR", {
|
|
410
37
|
message: `Polar customer creation failed. Error: ${e}`
|
|
411
38
|
});
|
|
412
39
|
}
|
|
@@ -417,7 +44,7 @@ var onUserUpdate = (options) => async (user, ctx) => {
|
|
|
417
44
|
try {
|
|
418
45
|
await options.client.customers.updateExternal({
|
|
419
46
|
externalId: user.id,
|
|
420
|
-
|
|
47
|
+
customerUpdateExternalID: {
|
|
421
48
|
email: user.email,
|
|
422
49
|
name: user.name
|
|
423
50
|
}
|
|
@@ -434,16 +61,641 @@ var onUserUpdate = (options) => async (user, ctx) => {
|
|
|
434
61
|
}
|
|
435
62
|
};
|
|
436
63
|
|
|
64
|
+
// src/client.ts
|
|
65
|
+
var polarClient = () => {
|
|
66
|
+
return {
|
|
67
|
+
id: "polar-client",
|
|
68
|
+
$InferServerPlugin: {}
|
|
69
|
+
};
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
// src/plugins/portal.ts
|
|
73
|
+
import { APIError as APIError2 } from "better-auth/api";
|
|
74
|
+
import { sessionMiddleware } from "better-auth/api";
|
|
75
|
+
import { createAuthEndpoint } from "better-auth/plugins";
|
|
76
|
+
import { z } from "zod";
|
|
77
|
+
var portal = () => (polar2) => {
|
|
78
|
+
return {
|
|
79
|
+
portal: createAuthEndpoint(
|
|
80
|
+
"/customer/portal",
|
|
81
|
+
{
|
|
82
|
+
method: "GET",
|
|
83
|
+
use: [sessionMiddleware]
|
|
84
|
+
},
|
|
85
|
+
async (ctx) => {
|
|
86
|
+
if (!ctx.context.session?.user.id) {
|
|
87
|
+
throw new APIError2("BAD_REQUEST", {
|
|
88
|
+
message: "User not found"
|
|
89
|
+
});
|
|
90
|
+
}
|
|
91
|
+
try {
|
|
92
|
+
const customerSession = await polar2.customerSessions.create({
|
|
93
|
+
customerExternalId: ctx.context.session?.user.id
|
|
94
|
+
});
|
|
95
|
+
return ctx.json({
|
|
96
|
+
url: customerSession.customerPortalUrl,
|
|
97
|
+
redirect: true
|
|
98
|
+
});
|
|
99
|
+
} catch (e) {
|
|
100
|
+
if (e instanceof Error) {
|
|
101
|
+
ctx.context.logger.error(
|
|
102
|
+
`Polar customer portal creation failed. Error: ${e.message}`
|
|
103
|
+
);
|
|
104
|
+
}
|
|
105
|
+
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
106
|
+
message: "Customer portal creation failed"
|
|
107
|
+
});
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
),
|
|
111
|
+
state: createAuthEndpoint(
|
|
112
|
+
"/customer/state",
|
|
113
|
+
{
|
|
114
|
+
method: "GET",
|
|
115
|
+
use: [sessionMiddleware]
|
|
116
|
+
},
|
|
117
|
+
async (ctx) => {
|
|
118
|
+
if (!ctx.context.session.user.id) {
|
|
119
|
+
throw new APIError2("BAD_REQUEST", {
|
|
120
|
+
message: "User not found"
|
|
121
|
+
});
|
|
122
|
+
}
|
|
123
|
+
try {
|
|
124
|
+
const state = await polar2.customers.getStateExternal({
|
|
125
|
+
externalId: ctx.context.session?.user.id
|
|
126
|
+
});
|
|
127
|
+
return ctx.json(state);
|
|
128
|
+
} catch (e) {
|
|
129
|
+
if (e instanceof Error) {
|
|
130
|
+
ctx.context.logger.error(
|
|
131
|
+
`Polar subscriptions list failed. Error: ${e.message}`
|
|
132
|
+
);
|
|
133
|
+
}
|
|
134
|
+
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
135
|
+
message: "Subscriptions list failed"
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
),
|
|
140
|
+
benefits: createAuthEndpoint(
|
|
141
|
+
"/customer/benefits/list",
|
|
142
|
+
{
|
|
143
|
+
method: "GET",
|
|
144
|
+
query: z.object({
|
|
145
|
+
page: z.coerce.number().optional(),
|
|
146
|
+
limit: z.coerce.number().optional()
|
|
147
|
+
}).optional(),
|
|
148
|
+
use: [sessionMiddleware]
|
|
149
|
+
},
|
|
150
|
+
async (ctx) => {
|
|
151
|
+
if (!ctx.context.session.user.id) {
|
|
152
|
+
throw new APIError2("BAD_REQUEST", {
|
|
153
|
+
message: "User not found"
|
|
154
|
+
});
|
|
155
|
+
}
|
|
156
|
+
try {
|
|
157
|
+
const customerSession = await polar2.customerSessions.create({
|
|
158
|
+
customerExternalId: ctx.context.session?.user.id
|
|
159
|
+
});
|
|
160
|
+
const benefits = await polar2.customerPortal.benefitGrants.list(
|
|
161
|
+
{ customerSession: customerSession.token },
|
|
162
|
+
{
|
|
163
|
+
page: ctx.query?.page,
|
|
164
|
+
limit: ctx.query?.limit
|
|
165
|
+
}
|
|
166
|
+
);
|
|
167
|
+
return ctx.json(benefits);
|
|
168
|
+
} catch (e) {
|
|
169
|
+
if (e instanceof Error) {
|
|
170
|
+
ctx.context.logger.error(
|
|
171
|
+
`Polar benefits list failed. Error: ${e.message}`
|
|
172
|
+
);
|
|
173
|
+
}
|
|
174
|
+
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
175
|
+
message: "Benefits list failed"
|
|
176
|
+
});
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
),
|
|
180
|
+
subscriptions: createAuthEndpoint(
|
|
181
|
+
"/customer/subscriptions/list",
|
|
182
|
+
{
|
|
183
|
+
method: "GET",
|
|
184
|
+
query: z.object({
|
|
185
|
+
referenceId: z.string().optional(),
|
|
186
|
+
page: z.coerce.number().optional(),
|
|
187
|
+
limit: z.coerce.number().optional(),
|
|
188
|
+
active: z.boolean().optional()
|
|
189
|
+
}).optional(),
|
|
190
|
+
use: [sessionMiddleware]
|
|
191
|
+
},
|
|
192
|
+
async (ctx) => {
|
|
193
|
+
if (!ctx.context.session.user.id) {
|
|
194
|
+
throw new APIError2("BAD_REQUEST", {
|
|
195
|
+
message: "User not found"
|
|
196
|
+
});
|
|
197
|
+
}
|
|
198
|
+
if (ctx.query?.referenceId) {
|
|
199
|
+
try {
|
|
200
|
+
const subscriptions = await polar2.subscriptions.list({
|
|
201
|
+
page: ctx.query?.page,
|
|
202
|
+
limit: ctx.query?.limit,
|
|
203
|
+
active: ctx.query?.active,
|
|
204
|
+
metadata: {
|
|
205
|
+
referenceId: ctx.query?.referenceId
|
|
206
|
+
}
|
|
207
|
+
});
|
|
208
|
+
return ctx.json(subscriptions);
|
|
209
|
+
} catch (e) {
|
|
210
|
+
console.log(e);
|
|
211
|
+
if (e instanceof Error) {
|
|
212
|
+
ctx.context.logger.error(
|
|
213
|
+
`Polar subscriptions list with referenceId failed. Error: ${e.message}`
|
|
214
|
+
);
|
|
215
|
+
}
|
|
216
|
+
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
217
|
+
message: "Subscriptions list with referenceId failed"
|
|
218
|
+
});
|
|
219
|
+
}
|
|
220
|
+
}
|
|
221
|
+
try {
|
|
222
|
+
const customerSession = await polar2.customerSessions.create({
|
|
223
|
+
customerExternalId: ctx.context.session?.user.id
|
|
224
|
+
});
|
|
225
|
+
const subscriptions = await polar2.customerPortal.subscriptions.list(
|
|
226
|
+
{ customerSession: customerSession.token },
|
|
227
|
+
{
|
|
228
|
+
page: ctx.query?.page,
|
|
229
|
+
limit: ctx.query?.limit,
|
|
230
|
+
active: ctx.query?.active
|
|
231
|
+
}
|
|
232
|
+
);
|
|
233
|
+
return ctx.json(subscriptions);
|
|
234
|
+
} catch (e) {
|
|
235
|
+
if (e instanceof Error) {
|
|
236
|
+
ctx.context.logger.error(
|
|
237
|
+
`Polar subscriptions list failed. Error: ${e.message}`
|
|
238
|
+
);
|
|
239
|
+
}
|
|
240
|
+
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
241
|
+
message: "Polar subscriptions list failed"
|
|
242
|
+
});
|
|
243
|
+
}
|
|
244
|
+
}
|
|
245
|
+
),
|
|
246
|
+
orders: createAuthEndpoint(
|
|
247
|
+
"/customer/orders/list",
|
|
248
|
+
{
|
|
249
|
+
method: "GET",
|
|
250
|
+
query: z.object({
|
|
251
|
+
page: z.coerce.number().optional(),
|
|
252
|
+
limit: z.coerce.number().optional(),
|
|
253
|
+
productBillingType: z.enum(["recurring", "one_time"]).optional()
|
|
254
|
+
}).optional(),
|
|
255
|
+
use: [sessionMiddleware]
|
|
256
|
+
},
|
|
257
|
+
async (ctx) => {
|
|
258
|
+
if (!ctx.context.session.user.id) {
|
|
259
|
+
throw new APIError2("BAD_REQUEST", {
|
|
260
|
+
message: "User not found"
|
|
261
|
+
});
|
|
262
|
+
}
|
|
263
|
+
try {
|
|
264
|
+
const customerSession = await polar2.customerSessions.create({
|
|
265
|
+
customerExternalId: ctx.context.session?.user.id
|
|
266
|
+
});
|
|
267
|
+
const orders = await polar2.customerPortal.orders.list(
|
|
268
|
+
{ customerSession: customerSession.token },
|
|
269
|
+
{
|
|
270
|
+
page: ctx.query?.page,
|
|
271
|
+
limit: ctx.query?.limit,
|
|
272
|
+
productBillingType: ctx.query?.productBillingType
|
|
273
|
+
}
|
|
274
|
+
);
|
|
275
|
+
return ctx.json(orders);
|
|
276
|
+
} catch (e) {
|
|
277
|
+
if (e instanceof Error) {
|
|
278
|
+
ctx.context.logger.error(
|
|
279
|
+
`Polar orders list failed. Error: ${e.message}`
|
|
280
|
+
);
|
|
281
|
+
}
|
|
282
|
+
throw new APIError2("INTERNAL_SERVER_ERROR", {
|
|
283
|
+
message: "Orders list failed"
|
|
284
|
+
});
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
)
|
|
288
|
+
};
|
|
289
|
+
};
|
|
290
|
+
|
|
291
|
+
// src/plugins/checkout.ts
|
|
292
|
+
import { APIError as APIError3, getSessionFromCtx } from "better-auth/api";
|
|
293
|
+
import { createAuthEndpoint as createAuthEndpoint2 } from "better-auth/plugins";
|
|
294
|
+
import { z as z2 } from "zod";
|
|
295
|
+
var checkout = (checkoutOptions = {}) => (polar2) => {
|
|
296
|
+
return {
|
|
297
|
+
checkout: createAuthEndpoint2(
|
|
298
|
+
"/checkout",
|
|
299
|
+
{
|
|
300
|
+
method: "POST",
|
|
301
|
+
body: z2.object({
|
|
302
|
+
products: z2.union([z2.array(z2.string()), z2.string()]).optional(),
|
|
303
|
+
slug: z2.string().optional(),
|
|
304
|
+
referenceId: z2.string().optional(),
|
|
305
|
+
customFieldData: z2.record(
|
|
306
|
+
z2.string(),
|
|
307
|
+
z2.union([z2.string(), z2.number(), z2.boolean()])
|
|
308
|
+
).optional(),
|
|
309
|
+
metadata: z2.record(
|
|
310
|
+
z2.string(),
|
|
311
|
+
z2.union([z2.string(), z2.number(), z2.boolean()])
|
|
312
|
+
).optional()
|
|
313
|
+
})
|
|
314
|
+
},
|
|
315
|
+
async (ctx) => {
|
|
316
|
+
const session = await getSessionFromCtx(ctx);
|
|
317
|
+
let productIds = [];
|
|
318
|
+
if (ctx.body.slug) {
|
|
319
|
+
const resolvedProducts = await (typeof checkoutOptions.products === "function" ? checkoutOptions.products() : checkoutOptions.products);
|
|
320
|
+
const productId = resolvedProducts?.find(
|
|
321
|
+
(product) => product.slug === ctx.body.slug
|
|
322
|
+
)?.productId;
|
|
323
|
+
if (!productId) {
|
|
324
|
+
throw new APIError3("BAD_REQUEST", {
|
|
325
|
+
message: "Product not found"
|
|
326
|
+
});
|
|
327
|
+
}
|
|
328
|
+
productIds = [productId];
|
|
329
|
+
} else {
|
|
330
|
+
productIds = Array.isArray(ctx.body.products) ? ctx.body.products.filter((id) => id !== void 0) : [ctx.body.products].filter((id) => id !== void 0);
|
|
331
|
+
}
|
|
332
|
+
if (checkoutOptions.authenticatedUsersOnly && !session?.user.id) {
|
|
333
|
+
throw new APIError3("UNAUTHORIZED", {
|
|
334
|
+
message: "You must be logged in to checkout"
|
|
335
|
+
});
|
|
336
|
+
}
|
|
337
|
+
try {
|
|
338
|
+
const checkout2 = await polar2.checkouts.create({
|
|
339
|
+
customerExternalId: session?.user.id,
|
|
340
|
+
products: productIds,
|
|
341
|
+
successUrl: checkoutOptions.successUrl ? new URL(
|
|
342
|
+
checkoutOptions.successUrl,
|
|
343
|
+
ctx.request?.url
|
|
344
|
+
).toString() : void 0,
|
|
345
|
+
metadata: ctx.body.referenceId ? {
|
|
346
|
+
referenceId: ctx.body.referenceId,
|
|
347
|
+
...ctx.body.metadata
|
|
348
|
+
} : ctx.body.metadata,
|
|
349
|
+
customFieldData: ctx.body.customFieldData
|
|
350
|
+
});
|
|
351
|
+
return ctx.json({
|
|
352
|
+
url: checkout2.url,
|
|
353
|
+
redirect: true
|
|
354
|
+
});
|
|
355
|
+
} catch (e) {
|
|
356
|
+
if (e instanceof Error) {
|
|
357
|
+
ctx.context.logger.error(
|
|
358
|
+
`Polar checkout creation failed. Error: ${e.message}`
|
|
359
|
+
);
|
|
360
|
+
}
|
|
361
|
+
throw new APIError3("INTERNAL_SERVER_ERROR", {
|
|
362
|
+
message: "Checkout creation failed"
|
|
363
|
+
});
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
)
|
|
367
|
+
};
|
|
368
|
+
};
|
|
369
|
+
|
|
370
|
+
// src/plugins/usage.ts
|
|
371
|
+
import {
|
|
372
|
+
APIError as APIError4,
|
|
373
|
+
createAuthEndpoint as createAuthEndpoint3,
|
|
374
|
+
sessionMiddleware as sessionMiddleware2
|
|
375
|
+
} from "better-auth/api";
|
|
376
|
+
import { z as z3 } from "zod";
|
|
377
|
+
var usage = (_usageOptions) => (polar2) => {
|
|
378
|
+
return {
|
|
379
|
+
meters: createAuthEndpoint3(
|
|
380
|
+
"/usage/meters/list",
|
|
381
|
+
{
|
|
382
|
+
method: "GET",
|
|
383
|
+
use: [sessionMiddleware2],
|
|
384
|
+
query: z3.object({
|
|
385
|
+
page: z3.coerce.number().optional(),
|
|
386
|
+
limit: z3.coerce.number().optional()
|
|
387
|
+
})
|
|
388
|
+
},
|
|
389
|
+
async (ctx) => {
|
|
390
|
+
if (!ctx.context.session.user.id) {
|
|
391
|
+
throw new APIError4("BAD_REQUEST", {
|
|
392
|
+
message: "User not found"
|
|
393
|
+
});
|
|
394
|
+
}
|
|
395
|
+
try {
|
|
396
|
+
const customerSession = await polar2.customerSessions.create({
|
|
397
|
+
customerExternalId: ctx.context.session.user.id
|
|
398
|
+
});
|
|
399
|
+
const customerMeters = await polar2.customerPortal.customerMeters.list(
|
|
400
|
+
{ customerSession: customerSession.token },
|
|
401
|
+
{
|
|
402
|
+
page: ctx.query?.page,
|
|
403
|
+
limit: ctx.query?.limit
|
|
404
|
+
}
|
|
405
|
+
);
|
|
406
|
+
return ctx.json(customerMeters);
|
|
407
|
+
} catch (e) {
|
|
408
|
+
if (e instanceof Error) {
|
|
409
|
+
ctx.context.logger.error(
|
|
410
|
+
`Polar meters list failed. Error: ${e.message}`
|
|
411
|
+
);
|
|
412
|
+
}
|
|
413
|
+
throw new APIError4("INTERNAL_SERVER_ERROR", {
|
|
414
|
+
message: "Meters list failed"
|
|
415
|
+
});
|
|
416
|
+
}
|
|
417
|
+
}
|
|
418
|
+
),
|
|
419
|
+
ingestion: createAuthEndpoint3(
|
|
420
|
+
"/usage/ingest",
|
|
421
|
+
{
|
|
422
|
+
method: "POST",
|
|
423
|
+
body: z3.object({
|
|
424
|
+
event: z3.string(),
|
|
425
|
+
metadata: z3.record(
|
|
426
|
+
z3.string(),
|
|
427
|
+
z3.union([z3.string(), z3.number(), z3.boolean()])
|
|
428
|
+
)
|
|
429
|
+
}),
|
|
430
|
+
use: [sessionMiddleware2]
|
|
431
|
+
},
|
|
432
|
+
async (ctx) => {
|
|
433
|
+
if (!ctx.context.session.user.id) {
|
|
434
|
+
throw new APIError4("BAD_REQUEST", {
|
|
435
|
+
message: "User not found"
|
|
436
|
+
});
|
|
437
|
+
}
|
|
438
|
+
try {
|
|
439
|
+
const ingestion = await polar2.events.ingest({
|
|
440
|
+
events: [
|
|
441
|
+
{
|
|
442
|
+
name: ctx.body.event,
|
|
443
|
+
metadata: ctx.body.metadata,
|
|
444
|
+
externalCustomerId: ctx.context.session.user.id
|
|
445
|
+
}
|
|
446
|
+
]
|
|
447
|
+
});
|
|
448
|
+
return ctx.json(ingestion);
|
|
449
|
+
} catch (e) {
|
|
450
|
+
if (e instanceof Error) {
|
|
451
|
+
ctx.context.logger.error(
|
|
452
|
+
`Polar ingestion failed. Error: ${e.message}`
|
|
453
|
+
);
|
|
454
|
+
}
|
|
455
|
+
throw new APIError4("INTERNAL_SERVER_ERROR", {
|
|
456
|
+
message: "Ingestion failed"
|
|
457
|
+
});
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
)
|
|
461
|
+
};
|
|
462
|
+
};
|
|
463
|
+
|
|
464
|
+
// src/plugins/webhooks.ts
|
|
465
|
+
import { validateEvent } from "@polar-sh/sdk/webhooks.js";
|
|
466
|
+
import { APIError as APIError5, createAuthEndpoint as createAuthEndpoint4 } from "better-auth/api";
|
|
467
|
+
var webhooks = (options) => (_polar) => {
|
|
468
|
+
return {
|
|
469
|
+
polarWebhooks: createAuthEndpoint4(
|
|
470
|
+
"/polar/webhooks",
|
|
471
|
+
{
|
|
472
|
+
method: "POST",
|
|
473
|
+
metadata: {
|
|
474
|
+
isAction: false
|
|
475
|
+
},
|
|
476
|
+
cloneRequest: true
|
|
477
|
+
},
|
|
478
|
+
async (ctx) => {
|
|
479
|
+
const {
|
|
480
|
+
secret,
|
|
481
|
+
onPayload,
|
|
482
|
+
onCheckoutCreated,
|
|
483
|
+
onCheckoutUpdated,
|
|
484
|
+
onOrderCreated,
|
|
485
|
+
onOrderPaid,
|
|
486
|
+
onOrderRefunded,
|
|
487
|
+
onRefundCreated,
|
|
488
|
+
onRefundUpdated,
|
|
489
|
+
onSubscriptionCreated,
|
|
490
|
+
onSubscriptionUpdated,
|
|
491
|
+
onSubscriptionActive,
|
|
492
|
+
onSubscriptionCanceled,
|
|
493
|
+
onSubscriptionRevoked,
|
|
494
|
+
onSubscriptionUncanceled,
|
|
495
|
+
onProductCreated,
|
|
496
|
+
onProductUpdated,
|
|
497
|
+
onOrganizationUpdated,
|
|
498
|
+
onBenefitCreated,
|
|
499
|
+
onBenefitUpdated,
|
|
500
|
+
onBenefitGrantCreated,
|
|
501
|
+
onBenefitGrantUpdated,
|
|
502
|
+
onBenefitGrantRevoked,
|
|
503
|
+
onCustomerCreated,
|
|
504
|
+
onCustomerUpdated,
|
|
505
|
+
onCustomerDeleted,
|
|
506
|
+
onCustomerStateChanged
|
|
507
|
+
} = options;
|
|
508
|
+
if (!ctx.request?.body) {
|
|
509
|
+
throw new APIError5("INTERNAL_SERVER_ERROR");
|
|
510
|
+
}
|
|
511
|
+
const buf = await ctx.request.text();
|
|
512
|
+
let event;
|
|
513
|
+
try {
|
|
514
|
+
if (!secret) {
|
|
515
|
+
throw new APIError5("INTERNAL_SERVER_ERROR", {
|
|
516
|
+
message: "Polar webhook secret not found"
|
|
517
|
+
});
|
|
518
|
+
}
|
|
519
|
+
const headers = {
|
|
520
|
+
"webhook-id": ctx.request.headers.get("webhook-id"),
|
|
521
|
+
"webhook-timestamp": ctx.request.headers.get(
|
|
522
|
+
"webhook-timestamp"
|
|
523
|
+
),
|
|
524
|
+
"webhook-signature": ctx.request.headers.get(
|
|
525
|
+
"webhook-signature"
|
|
526
|
+
)
|
|
527
|
+
};
|
|
528
|
+
event = validateEvent(buf, headers, secret);
|
|
529
|
+
} catch (err) {
|
|
530
|
+
if (err instanceof Error) {
|
|
531
|
+
ctx.context.logger.error(`${err.message}`);
|
|
532
|
+
throw new APIError5("BAD_REQUEST", {
|
|
533
|
+
message: `Webhook Error: ${err.message}`
|
|
534
|
+
});
|
|
535
|
+
}
|
|
536
|
+
throw new APIError5("BAD_REQUEST", {
|
|
537
|
+
message: `Webhook Error: ${err}`
|
|
538
|
+
});
|
|
539
|
+
}
|
|
540
|
+
try {
|
|
541
|
+
if (onPayload) {
|
|
542
|
+
onPayload(event);
|
|
543
|
+
}
|
|
544
|
+
switch (event.type) {
|
|
545
|
+
case "checkout.created":
|
|
546
|
+
if (onCheckoutCreated) {
|
|
547
|
+
onCheckoutCreated(event);
|
|
548
|
+
}
|
|
549
|
+
break;
|
|
550
|
+
case "checkout.updated":
|
|
551
|
+
if (onCheckoutUpdated) {
|
|
552
|
+
onCheckoutUpdated(event);
|
|
553
|
+
}
|
|
554
|
+
break;
|
|
555
|
+
case "order.created":
|
|
556
|
+
if (onOrderCreated) {
|
|
557
|
+
onOrderCreated(event);
|
|
558
|
+
}
|
|
559
|
+
break;
|
|
560
|
+
case "order.paid":
|
|
561
|
+
if (onOrderPaid) {
|
|
562
|
+
onOrderPaid(event);
|
|
563
|
+
}
|
|
564
|
+
break;
|
|
565
|
+
case "subscription.created":
|
|
566
|
+
if (onSubscriptionCreated) {
|
|
567
|
+
onSubscriptionCreated(event);
|
|
568
|
+
}
|
|
569
|
+
break;
|
|
570
|
+
case "subscription.updated":
|
|
571
|
+
if (onSubscriptionUpdated) {
|
|
572
|
+
onSubscriptionUpdated(event);
|
|
573
|
+
}
|
|
574
|
+
break;
|
|
575
|
+
case "subscription.active":
|
|
576
|
+
if (onSubscriptionActive) {
|
|
577
|
+
onSubscriptionActive(event);
|
|
578
|
+
}
|
|
579
|
+
break;
|
|
580
|
+
case "subscription.canceled":
|
|
581
|
+
if (onSubscriptionCanceled) {
|
|
582
|
+
onSubscriptionCanceled(event);
|
|
583
|
+
}
|
|
584
|
+
break;
|
|
585
|
+
case "subscription.uncanceled":
|
|
586
|
+
if (onSubscriptionUncanceled) {
|
|
587
|
+
onSubscriptionUncanceled(event);
|
|
588
|
+
}
|
|
589
|
+
break;
|
|
590
|
+
case "subscription.revoked":
|
|
591
|
+
if (onSubscriptionRevoked) {
|
|
592
|
+
onSubscriptionRevoked(event);
|
|
593
|
+
}
|
|
594
|
+
break;
|
|
595
|
+
case "product.created":
|
|
596
|
+
if (onProductCreated) {
|
|
597
|
+
onProductCreated(event);
|
|
598
|
+
}
|
|
599
|
+
break;
|
|
600
|
+
case "product.updated":
|
|
601
|
+
if (onProductUpdated) {
|
|
602
|
+
onProductUpdated(event);
|
|
603
|
+
}
|
|
604
|
+
break;
|
|
605
|
+
case "organization.updated":
|
|
606
|
+
if (onOrganizationUpdated) {
|
|
607
|
+
onOrganizationUpdated(event);
|
|
608
|
+
}
|
|
609
|
+
break;
|
|
610
|
+
case "benefit.created":
|
|
611
|
+
if (onBenefitCreated) {
|
|
612
|
+
onBenefitCreated(event);
|
|
613
|
+
}
|
|
614
|
+
break;
|
|
615
|
+
case "benefit.updated":
|
|
616
|
+
if (onBenefitUpdated) {
|
|
617
|
+
onBenefitUpdated(event);
|
|
618
|
+
}
|
|
619
|
+
break;
|
|
620
|
+
case "benefit_grant.created":
|
|
621
|
+
if (onBenefitGrantCreated) {
|
|
622
|
+
onBenefitGrantCreated(event);
|
|
623
|
+
}
|
|
624
|
+
break;
|
|
625
|
+
case "benefit_grant.updated":
|
|
626
|
+
if (onBenefitGrantUpdated) {
|
|
627
|
+
onBenefitGrantUpdated(event);
|
|
628
|
+
}
|
|
629
|
+
break;
|
|
630
|
+
case "benefit_grant.revoked":
|
|
631
|
+
if (onBenefitGrantRevoked) {
|
|
632
|
+
onBenefitGrantRevoked(event);
|
|
633
|
+
}
|
|
634
|
+
break;
|
|
635
|
+
case "order.refunded":
|
|
636
|
+
if (onOrderRefunded) {
|
|
637
|
+
onOrderRefunded(event);
|
|
638
|
+
}
|
|
639
|
+
break;
|
|
640
|
+
case "refund.created":
|
|
641
|
+
if (onRefundCreated) {
|
|
642
|
+
onRefundCreated(event);
|
|
643
|
+
}
|
|
644
|
+
break;
|
|
645
|
+
case "refund.updated":
|
|
646
|
+
if (onRefundUpdated) {
|
|
647
|
+
onRefundUpdated(event);
|
|
648
|
+
}
|
|
649
|
+
break;
|
|
650
|
+
case "customer.created":
|
|
651
|
+
if (onCustomerCreated) {
|
|
652
|
+
onCustomerCreated(event);
|
|
653
|
+
}
|
|
654
|
+
break;
|
|
655
|
+
case "customer.updated":
|
|
656
|
+
if (onCustomerUpdated) {
|
|
657
|
+
onCustomerUpdated(event);
|
|
658
|
+
}
|
|
659
|
+
break;
|
|
660
|
+
case "customer.deleted":
|
|
661
|
+
if (onCustomerDeleted) {
|
|
662
|
+
onCustomerDeleted(event);
|
|
663
|
+
}
|
|
664
|
+
break;
|
|
665
|
+
case "customer.state_changed":
|
|
666
|
+
if (onCustomerStateChanged) {
|
|
667
|
+
onCustomerStateChanged(event);
|
|
668
|
+
}
|
|
669
|
+
break;
|
|
670
|
+
}
|
|
671
|
+
} catch (e) {
|
|
672
|
+
if (e instanceof Error) {
|
|
673
|
+
ctx.context.logger.error(
|
|
674
|
+
`Polar webhook failed. Error: ${e.message}`
|
|
675
|
+
);
|
|
676
|
+
} else {
|
|
677
|
+
ctx.context.logger.error(`Polar webhook failed. Error: ${e}`);
|
|
678
|
+
}
|
|
679
|
+
throw new APIError5("BAD_REQUEST", {
|
|
680
|
+
message: "Webhook error: See server logs for more information."
|
|
681
|
+
});
|
|
682
|
+
}
|
|
683
|
+
return ctx.json({ received: true });
|
|
684
|
+
}
|
|
685
|
+
)
|
|
686
|
+
};
|
|
687
|
+
};
|
|
688
|
+
|
|
437
689
|
// src/index.ts
|
|
438
690
|
var polar = (options) => {
|
|
691
|
+
const plugins = options.use.map((use) => use(options.client)).reduce((acc, plugin) => {
|
|
692
|
+
Object.assign(acc, plugin);
|
|
693
|
+
return acc;
|
|
694
|
+
}, {});
|
|
439
695
|
return {
|
|
440
696
|
id: "polar",
|
|
441
697
|
endpoints: {
|
|
442
|
-
|
|
443
|
-
polarCheckoutWithSlug: checkoutWithSlug(options),
|
|
444
|
-
polarWebhooks: webhooks(options),
|
|
445
|
-
polarCustomerPortal: customerPortal(options),
|
|
446
|
-
polarCustomerState: customerState(options)
|
|
698
|
+
...plugins
|
|
447
699
|
},
|
|
448
700
|
init() {
|
|
449
701
|
return {
|
|
@@ -464,6 +716,11 @@ var polar = (options) => {
|
|
|
464
716
|
};
|
|
465
717
|
};
|
|
466
718
|
export {
|
|
467
|
-
|
|
719
|
+
checkout,
|
|
720
|
+
polar,
|
|
721
|
+
polarClient,
|
|
722
|
+
portal,
|
|
723
|
+
usage,
|
|
724
|
+
webhooks
|
|
468
725
|
};
|
|
469
726
|
//# sourceMappingURL=index.js.map
|