import { loadStripe } from "@stripe/stripe-js"; import { CreateFormOptions, GatewayType, PaymentForm, PaymentHubParams, PaymentIntent, StripeFormCreateOptions, } from "./types"; export class PaymentHub { private publishableKey: string; private host: string; constructor(params: PaymentHubParams) { this.publishableKey = params.publishableKey; this.host = params.apiHost; } async getPaymentIntent(paymentIntentId: string): Promise { const url = new URL( `${this.host}/client/payment-intents/${paymentIntentId}` ); url.searchParams.append("publishableKey", this.publishableKey); const response = await fetch(url.toString()); if (!response.ok) { throw new Error( `[PAYMENT-HUB] Error getting Payment Intent. Status - ${response.status}. ${response.statusText}` ); } return response.json(); } async createForm(paymentIntentId: string, options: CreateFormOptions) { const paymentIntent = await this.getPaymentIntent(paymentIntentId); switch (paymentIntent.gatewayType) { case GatewayType.STRIPE: return this.createStripeForm( paymentIntent.gatewayPaymentIntent, options ); default: throw new Error(`Not supported gateway ${paymentIntent.gatewayType}`); } } private async createStripeForm( stripeOptions: StripeFormCreateOptions, options: CreateFormOptions ): Promise { const stripe = await loadStripe(stripeOptions.stripePublishableKey); if (!stripe) { throw new Error( `Invalid publishable key ${stripeOptions.stripePublishableKey}` ); } const elements = stripe.elements({ clientSecret: stripeOptions.stripePaymentIntentSecret, }); const paymentElement = elements.create("payment"); paymentElement.mount(this.getContainerById(options.containerElementId)); paymentElement.on("change", function (event) { options.onChange({ isValid: event.complete, paymentMethodType: event.value.type, }); }); return { confirmPayment: async () => { await stripe.confirmPayment({ elements, redirect: 'if_required' }); }, }; } private getContainerById(elementId: string) { const element = document.getElementById(elementId); if (!element) { throw new Error(`Element by id ${elementId} not found`); } return element; } }