-
Notifications
You must be signed in to change notification settings - Fork 769
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add Next.js App Router webhook example that leverages Route Handlers (#…
- Loading branch information
1 parent
04f409b
commit 54d423e
Showing
1 changed file
with
69 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
import {Stripe} from 'stripe'; | ||
import {NextResponse} from 'next/server'; | ||
import {headers} from 'next/headers'; | ||
|
||
const stripe = new Stripe(process.env.STRIPE_SECRET_KEY as string); | ||
|
||
export async function POST(req: Request) { | ||
let event: Stripe.Event; | ||
|
||
try { | ||
const stripeSignature = (await headers()).get('stripe-signature'); | ||
|
||
event = stripe.webhooks.constructEvent( | ||
await req.text(), | ||
stripeSignature as string, | ||
process.env.STRIPE_WEBHOOK_SECRET as string | ||
); | ||
} catch (err) { | ||
const errorMessage = err instanceof Error ? err.message : 'Unknown error'; | ||
// On error, log and return the error message. | ||
if (err! instanceof Error) console.log(err); | ||
console.log(`❌ Error message: ${errorMessage}`); | ||
return NextResponse.json( | ||
{message: `Webhook Error: ${errorMessage}`}, | ||
{status: 400} | ||
); | ||
} | ||
|
||
// Successfully constructed event. | ||
console.log('✅ Success:', event.id); | ||
|
||
const permittedEvents: string[] = [ | ||
'checkout.session.completed', | ||
'payment_intent.succeeded', | ||
'payment_intent.payment_failed', | ||
]; | ||
|
||
if (permittedEvents.includes(event.type)) { | ||
let data; | ||
|
||
try { | ||
switch (event.type) { | ||
case 'checkout.session.completed': | ||
data = event.data.object as Stripe.Checkout.Session; | ||
console.log(`💰 CheckoutSession status: ${data.payment_status}`); | ||
break; | ||
case 'payment_intent.payment_failed': | ||
data = event.data.object as Stripe.PaymentIntent; | ||
console.log(`❌ Payment failed: ${data.last_payment_error?.message}`); | ||
break; | ||
case 'payment_intent.succeeded': | ||
data = event.data.object as Stripe.PaymentIntent; | ||
console.log(`💰 PaymentIntent status: ${data.status}`); | ||
break; | ||
default: | ||
throw new Error(`Unhandled event: ${event.type}`); | ||
} | ||
} catch (error) { | ||
console.log(error); | ||
return NextResponse.json( | ||
{message: 'Webhook handler failed'}, | ||
{status: 500} | ||
); | ||
} | ||
} | ||
|
||
// Return a response to acknowledge receipt of the event. | ||
return NextResponse.json({message: 'Received'}, {status: 200}); | ||
} |