Skip to content

Instantly share code, notes, and snippets.

@bmorrisondev
Created February 11, 2025 16:00
Show Gist options
  • Select an option

  • Save bmorrisondev/5f9f2b2ae5026b81d4bc09abb11c2fea to your computer and use it in GitHub Desktop.

Select an option

Save bmorrisondev/5f9f2b2ae5026b81d4bc09abb11c2fea to your computer and use it in GitHub Desktop.
A Convex HTTP API to handle Clerk web-hooks
// convex/http.ts
import { httpRouter } from "convex/server";
import { httpAction } from "./_generated/server";
import { createWebhooksHandler } from "@brianmmdev/clerk-webhooks-handler";
import { api } from "./_generated/api";
// define the webhook handler
const handleClerkWebhook = httpAction(async (ctx, request) => {
const handler = createWebhooksHandler({
onUserCreated: async user => {
const twitterAcct = user.external_accounts.find(el => el.provider === "oauth_x")
let name = ""
if(user.first_name) name += user.first_name
if(user.last_name) name += ` ${user.last_name}`
if(name === "") name = twitterAcct?.username as string
await ctx.runMutation(api.users.upsertUser, {
userId: user.id,
imgPath: twitterAcct?.image_url as string,
name,
handle: twitterAcct?.username as string
})
},
onUserUpdated: async user => {
const twitterAcct = user.external_accounts.find(el => el.provider === "oauth_x")
let name = ""
if(user.first_name) name += user.first_name
if(user.last_name) name += ` ${user.last_name}`
if(name === "") name = twitterAcct?.username as string
await ctx.runMutation(api.users.upsertUser, {
userId: user.id,
imgPath: twitterAcct?.image_url as string,
name,
handle: twitterAcct?.username as string
})
}
})
return await handler.POST(request)
});
// define the http router
const http = httpRouter()
// define the webhook route
http.route({
path: '/clerk-users-webhook',
method: 'POST',
handler: handleClerkWebhook,
})
export default http
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment