// Node webhook receiver (any framework): read the RAW body, then verify before trusting it. import { verifyWebhook } from '@outlevo/sdk'; import { createServer } from 'node:http'; const seen = new Set(); // use your database in production: dedupe on event.id createServer(async (req, res) => { const chunks: Buffer[] = []; for await (const c of req) chunks.push(c as Buffer); const raw = Buffer.concat(chunks).toString('utf8'); try { const event = await verifyWebhook(raw, req.headers['outlevo-signature'] as string, process.env.OUTLEVO_WEBHOOK_SECRET!); if (!seen.has(event.id)) { seen.add(event.id); console.log(event.type, event.data); } res.writeHead(200).end('ok'); } catch { res.writeHead(400).end('bad signature'); } }).listen(3000);