@dotted-labs/ngx-supabase-stripe 0.4.1 → 0.5.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.
|
@@ -24,6 +24,11 @@ function provideStripeConfig(config) {
|
|
|
24
24
|
];
|
|
25
25
|
}
|
|
26
26
|
|
|
27
|
+
/**
|
|
28
|
+
* Optional shared browser `SupabaseClient` (e.g. the same instance passed to ngx-supabase-auth).
|
|
29
|
+
* When provided, {@link SupabaseClientService} uses it instead of creating a new client.
|
|
30
|
+
*/
|
|
31
|
+
const SUPABASE_BROWSER_CLIENT = new InjectionToken('SUPABASE_BROWSER_CLIENT');
|
|
27
32
|
const SUPABASE_CONFIG = new InjectionToken('SUPABASE_CONFIG');
|
|
28
33
|
/**
|
|
29
34
|
* Provides the Supabase configuration
|
|
@@ -60,9 +65,12 @@ function provideNgxSupabaseStripeConfig(config) {
|
|
|
60
65
|
|
|
61
66
|
class SupabaseClientService {
|
|
62
67
|
config = inject(SUPABASE_CONFIG);
|
|
68
|
+
browserClient = inject(SUPABASE_BROWSER_CLIENT, { optional: true });
|
|
63
69
|
client;
|
|
64
70
|
constructor() {
|
|
65
|
-
this.client =
|
|
71
|
+
this.client =
|
|
72
|
+
this.browserClient ??
|
|
73
|
+
createClient(this.config.supabaseUrl, this.config.supabaseKey);
|
|
66
74
|
console.log('🚀 [SupabaseClientService]: this.client', this.client);
|
|
67
75
|
}
|
|
68
76
|
/**
|
|
@@ -324,6 +332,48 @@ class StripeClientService {
|
|
|
324
332
|
this.stripe = loadStripe(this.config.publishableKey);
|
|
325
333
|
console.log('🔌 [StripeClientService]: Loaded Stripe Client from @stripe/stripe-js');
|
|
326
334
|
}
|
|
335
|
+
/**
|
|
336
|
+
* Edge functions use JWT verification (e.g. getClaims). Requires a logged-in Supabase Auth user.
|
|
337
|
+
*/
|
|
338
|
+
async resolveFunctionsAuth() {
|
|
339
|
+
const client = this.supabase.getClient();
|
|
340
|
+
const { data: sessionData, error: sessionError } = await client.auth.getSession();
|
|
341
|
+
if (sessionError) {
|
|
342
|
+
return { ok: false, error: new Error(sessionError.message) };
|
|
343
|
+
}
|
|
344
|
+
let accessToken = sessionData.session?.access_token;
|
|
345
|
+
if (!accessToken) {
|
|
346
|
+
const { data: refreshed, error: refreshError } = await client.auth.refreshSession();
|
|
347
|
+
if (refreshError) {
|
|
348
|
+
return { ok: false, error: new Error(refreshError.message) };
|
|
349
|
+
}
|
|
350
|
+
accessToken = refreshed.session?.access_token;
|
|
351
|
+
}
|
|
352
|
+
if (!accessToken) {
|
|
353
|
+
return {
|
|
354
|
+
ok: false,
|
|
355
|
+
error: new Error('No Supabase Auth session. Sign in before checkout (e.g. signInWithPassword, signInWithOAuth, or magic link).'),
|
|
356
|
+
};
|
|
357
|
+
}
|
|
358
|
+
return { ok: true, headers: { Authorization: `Bearer ${accessToken}` } };
|
|
359
|
+
}
|
|
360
|
+
async invokeWithAuth(name, options = {}) {
|
|
361
|
+
const auth = await this.resolveFunctionsAuth();
|
|
362
|
+
if (!auth.ok) {
|
|
363
|
+
return { data: null, error: auth.error };
|
|
364
|
+
}
|
|
365
|
+
const { data, error } = await this.supabase.getClient().functions.invoke(name, {
|
|
366
|
+
...options,
|
|
367
|
+
headers: {
|
|
368
|
+
...options.headers,
|
|
369
|
+
...auth.headers,
|
|
370
|
+
},
|
|
371
|
+
});
|
|
372
|
+
if (error) {
|
|
373
|
+
return { data: null, error: error };
|
|
374
|
+
}
|
|
375
|
+
return { data, error: null };
|
|
376
|
+
}
|
|
327
377
|
/**
|
|
328
378
|
* Get the Stripe instance
|
|
329
379
|
*/
|
|
@@ -373,20 +423,19 @@ class StripeClientService {
|
|
|
373
423
|
*/
|
|
374
424
|
async createCheckoutSession(priceId, resultPagePath, customer) {
|
|
375
425
|
try {
|
|
376
|
-
const { data, error } = await this.
|
|
377
|
-
.functions.invoke('checkout_session', {
|
|
426
|
+
const { data, error } = await this.invokeWithAuth('checkout_session', {
|
|
378
427
|
body: {
|
|
379
428
|
priceId,
|
|
380
429
|
resultPagePath,
|
|
381
|
-
customer
|
|
382
|
-
}
|
|
430
|
+
customer,
|
|
431
|
+
},
|
|
383
432
|
});
|
|
384
433
|
if (error) {
|
|
385
434
|
throw error;
|
|
386
435
|
}
|
|
387
436
|
return {
|
|
388
437
|
clientSecret: data?.client_secret ?? null,
|
|
389
|
-
error: null
|
|
438
|
+
error: null,
|
|
390
439
|
};
|
|
391
440
|
}
|
|
392
441
|
catch (error) {
|
|
@@ -399,13 +448,12 @@ class StripeClientService {
|
|
|
399
448
|
*/
|
|
400
449
|
async createSubscription(priceId, returnPath, customer) {
|
|
401
450
|
try {
|
|
402
|
-
const { data, error } = await this.
|
|
403
|
-
.functions.invoke('create_subscription', {
|
|
451
|
+
const { data, error } = await this.invokeWithAuth('create_subscription', {
|
|
404
452
|
body: {
|
|
405
453
|
priceId,
|
|
406
454
|
resultPagePath: returnPath,
|
|
407
|
-
customer
|
|
408
|
-
}
|
|
455
|
+
customer,
|
|
456
|
+
},
|
|
409
457
|
});
|
|
410
458
|
if (error) {
|
|
411
459
|
throw error;
|
|
@@ -423,12 +471,11 @@ class StripeClientService {
|
|
|
423
471
|
*/
|
|
424
472
|
async updateSubscription(subscriptionId, params) {
|
|
425
473
|
try {
|
|
426
|
-
const { data, error } = await this.
|
|
427
|
-
.functions.invoke('update_subscription', {
|
|
474
|
+
const { data, error } = await this.invokeWithAuth('update_subscription', {
|
|
428
475
|
body: {
|
|
429
476
|
subscriptionId,
|
|
430
|
-
params
|
|
431
|
-
}
|
|
477
|
+
params,
|
|
478
|
+
},
|
|
432
479
|
});
|
|
433
480
|
if (error) {
|
|
434
481
|
throw error;
|
|
@@ -445,11 +492,10 @@ class StripeClientService {
|
|
|
445
492
|
*/
|
|
446
493
|
async getSubscription(subscriptionId) {
|
|
447
494
|
try {
|
|
448
|
-
const { data, error } = await this.
|
|
449
|
-
.functions.invoke('get_subscription', {
|
|
495
|
+
const { data, error } = await this.invokeWithAuth('get_subscription', {
|
|
450
496
|
body: {
|
|
451
|
-
subscriptionId
|
|
452
|
-
}
|
|
497
|
+
subscriptionId,
|
|
498
|
+
},
|
|
453
499
|
});
|
|
454
500
|
if (error) {
|
|
455
501
|
throw error;
|
|
@@ -465,8 +511,7 @@ class StripeClientService {
|
|
|
465
511
|
*/
|
|
466
512
|
async listSubscriptions() {
|
|
467
513
|
try {
|
|
468
|
-
const { data, error } = await this.
|
|
469
|
-
.functions.invoke('list_subscriptions');
|
|
514
|
+
const { data, error } = await this.invokeWithAuth('list_subscriptions');
|
|
470
515
|
if (error) {
|
|
471
516
|
throw error;
|
|
472
517
|
}
|
|
@@ -482,11 +527,10 @@ class StripeClientService {
|
|
|
482
527
|
*/
|
|
483
528
|
async cancelSubscription(subscriptionId) {
|
|
484
529
|
try {
|
|
485
|
-
const { data, error } = await this.
|
|
486
|
-
.functions.invoke('cancel_subscription', {
|
|
530
|
+
const { data, error } = await this.invokeWithAuth('cancel_subscription', {
|
|
487
531
|
body: {
|
|
488
|
-
subscriptionId
|
|
489
|
-
}
|
|
532
|
+
subscriptionId,
|
|
533
|
+
},
|
|
490
534
|
});
|
|
491
535
|
if (error) {
|
|
492
536
|
throw error;
|
|
@@ -504,12 +548,11 @@ class StripeClientService {
|
|
|
504
548
|
*/
|
|
505
549
|
async resumeSubscription(subscriptionId, params) {
|
|
506
550
|
try {
|
|
507
|
-
const { data, error } = await this.
|
|
508
|
-
.functions.invoke('resume_subscription', {
|
|
551
|
+
const { data, error } = await this.invokeWithAuth('resume_subscription', {
|
|
509
552
|
body: {
|
|
510
553
|
subscriptionId,
|
|
511
|
-
params
|
|
512
|
-
}
|
|
554
|
+
params,
|
|
555
|
+
},
|
|
513
556
|
});
|
|
514
557
|
if (error) {
|
|
515
558
|
throw error;
|
|
@@ -526,11 +569,10 @@ class StripeClientService {
|
|
|
526
569
|
*/
|
|
527
570
|
async getCheckoutSessionStatus(sessionId) {
|
|
528
571
|
try {
|
|
529
|
-
const { data, error } = await this.
|
|
530
|
-
.functions.invoke('session_status', {
|
|
572
|
+
const { data, error } = await this.invokeWithAuth('session_status', {
|
|
531
573
|
body: {
|
|
532
|
-
sessionId
|
|
533
|
-
}
|
|
574
|
+
sessionId,
|
|
575
|
+
},
|
|
534
576
|
});
|
|
535
577
|
if (error) {
|
|
536
578
|
throw error;
|
|
@@ -549,12 +591,11 @@ class StripeClientService {
|
|
|
549
591
|
*/
|
|
550
592
|
async createPortalSession(customerId, returnUrl) {
|
|
551
593
|
try {
|
|
552
|
-
const { data, error } = await this.
|
|
553
|
-
.functions.invoke('create_portal_session', {
|
|
594
|
+
const { data, error } = await this.invokeWithAuth('create_portal_session', {
|
|
554
595
|
body: {
|
|
555
596
|
customerId,
|
|
556
|
-
returnUrl
|
|
557
|
-
}
|
|
597
|
+
returnUrl,
|
|
598
|
+
},
|
|
558
599
|
});
|
|
559
600
|
if (error) {
|
|
560
601
|
throw error;
|
|
@@ -571,11 +612,10 @@ class StripeClientService {
|
|
|
571
612
|
*/
|
|
572
613
|
async createCustomer(customerEmail) {
|
|
573
614
|
try {
|
|
574
|
-
const { data, error } = await this.
|
|
575
|
-
.functions.invoke('create_customer', {
|
|
615
|
+
const { data, error } = await this.invokeWithAuth('create_customer', {
|
|
576
616
|
body: {
|
|
577
|
-
customerEmail
|
|
578
|
-
}
|
|
617
|
+
customerEmail,
|
|
618
|
+
},
|
|
579
619
|
});
|
|
580
620
|
if (error) {
|
|
581
621
|
throw error;
|
|
@@ -588,9 +628,8 @@ class StripeClientService {
|
|
|
588
628
|
}
|
|
589
629
|
async getCustomerPaymentMethods(customerId) {
|
|
590
630
|
try {
|
|
591
|
-
const { data, error } = await this.
|
|
592
|
-
|
|
593
|
-
body: { customerId }
|
|
631
|
+
const { data, error } = await this.invokeWithAuth('customer_payment_methods', {
|
|
632
|
+
body: { customerId },
|
|
594
633
|
});
|
|
595
634
|
if (error) {
|
|
596
635
|
throw error;
|
|
@@ -603,9 +642,8 @@ class StripeClientService {
|
|
|
603
642
|
}
|
|
604
643
|
async getCustomerPaymentMethod(customerId, paymentMethodId) {
|
|
605
644
|
try {
|
|
606
|
-
const { data, error } = await this.
|
|
607
|
-
|
|
608
|
-
body: { customerId, paymentMethodId }
|
|
645
|
+
const { data, error } = await this.invokeWithAuth('customer_payment_method', {
|
|
646
|
+
body: { customerId, paymentMethodId },
|
|
609
647
|
});
|
|
610
648
|
if (error) {
|
|
611
649
|
throw error;
|
|
@@ -1320,6 +1358,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.0", ngImpor
|
|
|
1320
1358
|
class EmbeddedCheckoutComponent {
|
|
1321
1359
|
checkoutStore = inject(CheckoutStore);
|
|
1322
1360
|
customerStore = inject(CustomerStore);
|
|
1361
|
+
stripeConfig = inject(STRIPE_CONFIG);
|
|
1323
1362
|
priceId = input.required(...(ngDevMode ? [{ debugName: "priceId" }] : []));
|
|
1324
1363
|
returnPagePath = input('/return', ...(ngDevMode ? [{ debugName: "returnPagePath" }] : []));
|
|
1325
1364
|
customer = computed(() => this.customerStore.customer().data, ...(ngDevMode ? [{ debugName: "customer" }] : []));
|
|
@@ -1327,8 +1366,10 @@ class EmbeddedCheckoutComponent {
|
|
|
1327
1366
|
this.createCheckoutSession();
|
|
1328
1367
|
}
|
|
1329
1368
|
createCheckoutSession() {
|
|
1330
|
-
const
|
|
1331
|
-
|
|
1369
|
+
const base = (this.stripeConfig.embeddedCheckoutBaseUrl?.trim() ||
|
|
1370
|
+
(typeof window !== 'undefined' ? window.location.origin : '')).replace(/\/$/, '');
|
|
1371
|
+
const path = this.returnPagePath();
|
|
1372
|
+
const returnPath = path.startsWith('/') ? `${base}${path}` : `${base}/${path}`;
|
|
1332
1373
|
// Create the checkout session
|
|
1333
1374
|
this.checkoutStore.createCheckoutSession({
|
|
1334
1375
|
priceId: this.priceId(),
|
|
@@ -1527,6 +1568,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.0", ngImpor
|
|
|
1527
1568
|
class EmbeddedSubscriptionComponent {
|
|
1528
1569
|
subscriptionsStore = inject(SubscriptionsStore);
|
|
1529
1570
|
customerStore = inject(CustomerStore);
|
|
1571
|
+
stripeConfig = inject(STRIPE_CONFIG);
|
|
1530
1572
|
priceId = input.required(...(ngDevMode ? [{ debugName: "priceId" }] : []));
|
|
1531
1573
|
returnPagePath = input('/subscription-return', ...(ngDevMode ? [{ debugName: "returnPagePath" }] : []));
|
|
1532
1574
|
customer = computed(() => this.customerStore.customer().data, ...(ngDevMode ? [{ debugName: "customer" }] : []));
|
|
@@ -1534,8 +1576,10 @@ class EmbeddedSubscriptionComponent {
|
|
|
1534
1576
|
this.createSubscription();
|
|
1535
1577
|
}
|
|
1536
1578
|
createSubscription() {
|
|
1537
|
-
const
|
|
1538
|
-
|
|
1579
|
+
const base = (this.stripeConfig.embeddedCheckoutBaseUrl?.trim() ||
|
|
1580
|
+
(typeof window !== 'undefined' ? window.location.origin : '')).replace(/\/$/, '');
|
|
1581
|
+
const path = this.returnPagePath();
|
|
1582
|
+
const returnPath = path.startsWith('/') ? `${base}${path}` : `${base}/${path}`;
|
|
1539
1583
|
this.subscriptionsStore.createSubscription(this.priceId(), returnPath, this.customer());
|
|
1540
1584
|
}
|
|
1541
1585
|
ngOnDestroy() {
|
|
@@ -2005,5 +2049,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.2.0", ngImpor
|
|
|
2005
2049
|
* Generated bundle index. Do not edit.
|
|
2006
2050
|
*/
|
|
2007
2051
|
|
|
2008
|
-
export { CheckoutStore, Currency, CustomerDashboardComponent, CustomerStore, EmbeddedCheckoutComponent, EmbeddedSubscriptionComponent, PaymentIntentsListComponent, PaymentIntentsTableComponent, PortalAccountStore, ProductItemButtonComponent, ProductListComponent, ProductsStore, ReturnPageComponent, STRIPE_CONFIG, SUPABASE_CONFIG, StripeClientService, SubscriptionCardComponent, SubscriptionReturnPageComponent, SubscriptionsListComponent, SubscriptionsStore, SupabaseClientService, parsePaymentIntent, parseProduct, parseSubscription, provideNgxSupabaseStripeConfig, provideStripeConfig, provideSupabaseConfig };
|
|
2052
|
+
export { CheckoutStore, Currency, CustomerDashboardComponent, CustomerStore, EmbeddedCheckoutComponent, EmbeddedSubscriptionComponent, PaymentIntentsListComponent, PaymentIntentsTableComponent, PortalAccountStore, ProductItemButtonComponent, ProductListComponent, ProductsStore, ReturnPageComponent, STRIPE_CONFIG, SUPABASE_BROWSER_CLIENT, SUPABASE_CONFIG, StripeClientService, SubscriptionCardComponent, SubscriptionReturnPageComponent, SubscriptionsListComponent, SubscriptionsStore, SupabaseClientService, parsePaymentIntent, parseProduct, parseSubscription, provideNgxSupabaseStripeConfig, provideStripeConfig, provideSupabaseConfig };
|
|
2009
2053
|
//# sourceMappingURL=dotted-labs-ngx-supabase-stripe.mjs.map
|