Subscription webhook
updatedSubscriptionWebhook.ts
updatedSubscriptionWebhook.tsimport { firestore, admin } from "../utils/firebase"
import stripe, { Stripe } from "../utils/stripe"
import * as express from "express"
const router = express.Router()
router.post("/", (req: any, res) => {
let event
try {
// check stripe event signature
event = stripe.webhooks.constructEvent(
req.rawBody,
req.headers["stripe-signature"],
process.env.YOUR_WEBHOOK_SIGNING_SECRET // visible on the Stripe Dashboard (https:
)
} catch (error) {
reportError(error, { request: req, details: "stripe-signature check error" }, req)
return res.status(400).send({ error })
}
if (!event || !event.type || !event.data?.object) return res.status(400).send({ event, error: "Missing data" })
const {
status,
customer: stripeCustomerId,
id: subscriptionId,
trial_end: trialEnd,
current_period_end: periodEnd,
cancel_at_period_end: cancelAtPeriodEnd
} = event.data.object
const { id: plan } = event.data.object?.plan
return stripe.customers
.retrieve(stripeCustomerId)
.then((customer): any => {
if (customer.deleted) {
// if customer is deleted, delete subscription
return firestore
.collection("users")
.where("subscription.stripeCustomerId", "==", stripeCustomerId)
.get()
.then((querySnapshot) => {
if (querySnapshot.empty) {
throw Error("user not found")
}
// get first matching user
const matchingUser = querySnapshot.docs[0]
const userId = matchingUser.id
return firestore.collection("users").doc(userId).set(
{
subscription: admin.firestore.FieldValue.delete() // delete subscription if customer is deleted
},
{ merge: true }
)
})
.then(
() => `The subscription's owner was deleted so the subscription has been removed from the user.`
)
}
// if customer is not deleted, update or add subscription
return firestore
.collection("users")
.where("email", "==", (customer as Stripe.Customer).email)
.get()
.then((querySnapshot) => {
if (querySnapshot.empty) {
throw Error("user not found")
}
// get first matching user
const matchingUser = querySnapshot.docs[0]
const userId = matchingUser.id
const subscription = {
stripeCustomerId,
id: subscriptionId,
status,
plan,
trialEnd,
periodEnd,
cancelAtPeriodEnd
}
return firestore.collection("users").doc(userId).set(
{
subscription
},
{ merge: true }
)
})
.then(() => `The subscription was updated in firebase.`)
})
.then((status) => res.status(200).send({ status }))
.catch((error) => {
console.error(`>> WEBHOOK ERROR: ${error}`)
res.status(400).send({ event, error })
})
})
export default router
Last updated