Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add getPurchaseInfo to Payment providers #1466

Conversation

jbranchaud
Copy link
Contributor

This is the first part of adding a functional interface to payment
providers so that other packages and apps can generically do payments
actions.

purchase

This is the first part of adding a functional interface to payment
providers so that other packages and apps can generically do payments
actions.
Copy link

vercel bot commented Mar 21, 2024

The latest updates on your projects. Learn more about Vercel for Git ↗︎

Name Status Preview Comments Updated (UTC)
badass-turbo ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
colt-steele ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
devrel-fyi ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
epic-web ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
pro-aws ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
pro-nextjs ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
skill-stack-docs ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
testing-javascript ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm
total-typescript-turbo ✅ Ready (Inspect) Visit Preview 💬 Add feedback Mar 22, 2024 3:21pm

just in TJS for now, the only place we are using the Stripe Provider at
the moment
@@ -7,7 +7,7 @@ import {
} from '@skillrecordings/commerce-server'
import {nextAuthOptions} from '../auth/[...nextauth]'

const paymentOptions = defaultPaymentOptions({
export const paymentOptions = defaultPaymentOptions({
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

export the paymentOptions so that other pages in TJS can use them

Comment on lines -38 to +41
const purchaseInfo = await stripeData({
checkoutSessionId: session_id as string,
})
const purchaseInfo = await paymentProvider.getPurchaseInfo(session_id)
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

replace stripeData call with getPurchaseInfo via the payment provider

Comment on lines -29 to +31
const {stripeChargeId} = await stripeData({
checkoutSessionId: session_id as string,
})
if (session_id && paymentProvider) {
const {chargeIdentifier} = await paymentProvider.getPurchaseInfo(session_id)
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

replace stripeData call with getPurchaseInfo via the payment provider

const token = await getToken({req})
const {getPurchaseDetails} = getSdk()

const paymentProvider = paymentOptions.providers.stripe
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We are still defaulting to stripe here. I need to figure out how we are going to differentiate in general when they land on the welcome page that they were directed here via a Stripe vs Paypal purchase so that we look up purchase info with the correct provider.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we have some control over the callback url with stripe so

success_url: `http://yoursite.com/order/success?session_id={CHECKOUT_SESSION_ID}&provider=${provider}`

would probably work

lemonsqueezy has similar (didn't look to closely) https://docs.lemonsqueezy.com/help/products/button-link-variables

usedCouponId: z.string().optional(),
})

export const PurchaseInfoSchema = z.object({
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

get types flowing for the purchase info

Comment on lines +30 to +32
type PaymentProviderFunctionality = {
getPurchaseInfo: (checkoutSessionId: string) => Promise<PurchaseInfo>
}
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the first piece of payment functionality moving into the umbrella of payment providers, additional pieces will be added to this type which the different payment providers conform to

@@ -23,19 +61,6 @@ export type PaymentOptions = {
}
}

// define providers here for now,
// but eventually they can go in a `providers/` directory
export const StripeProvider: StripeProviderFunction = (config) => {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Now that this is expanding, moving it to its own module

const {stripeCtx} = options

const purchaseInfo = await stripeData({checkoutSessionId, stripeCtx})
const purchaseInfo = await options.paymentProvider.getPurchaseInfo(
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

using the payment provider in here to getPurchaseInfo, though you'll notice above that the stripeData function still exists. that is because many of the apps still rely on it. once I've configured payment providers in each of those apps, they will be able to switch over to the new implementation and we can ditch stripeData.

Comment on lines 95 to 104
const {
stripeCustomerId,
customerIdentifier,
email,
name,
stripeProductId,
stripeChargeId,
stripeCouponId,
productIdentifier,
chargeIdentifier,
couponIdentifier,
quantity,
stripeChargeAmount,
chargeAmount,
metadata,
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

account for some variable renaming from purchaseInfo because we are trying this as provider agnostic info

Comment on lines +34 to +44
const getStripeClient = (paymentOptions: PaymentOptions | undefined) => {
return paymentOptions?.providers.stripe?.paymentClient
}

const constructFallbackStripePaymentOptions = (
stripe: Stripe,
): PaymentOptions => {
return defaultPaymentOptions({
stripeProvider: StripeProvider({defaultStripeClient: stripe}),
})
}
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this module processes stripe webhooks, so it can reach directly for the stripe client.

since most of the apps are still using the stripe module instead of configuring payment providers, this other helper function makes it easy to fallback on that client while conforming to the new provider-based API

const token = await getToken({req})
const {getPurchaseDetails} = getSdk()

const paymentProvider = paymentOptions.providers.stripe
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we have some control over the callback url with stripe so

success_url: `http://yoursite.com/order/success?session_id={CHECKOUT_SESSION_ID}&provider=${provider}`

would probably work

lemonsqueezy has similar (didn't look to closely) https://docs.lemonsqueezy.com/help/products/button-link-variables

@joelhooks joelhooks self-requested a review March 21, 2024 23:21
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants