---
title: "Stripe webhook receiver (signature-verified)"
method: POST
path: "/api/v1/billing/webhook"
tags: ["Billing"]
---

# Stripe webhook receiver (signature-verified)

`POST /api/v1/billing/webhook`

## Request

- Base URL: `https://tamperlens.com` (the document declares no server; this is the origin it was published from)
- URL: `https://tamperlens.com/api/v1/billing/webhook`
- Auth: none declared

Handles checkout.session.completed, checkout.session.async_payment_succeeded, checkout.session.async_payment_failed, customer.subscription.updated and customer.subscription.deleted. Fulfilment is gated on payment_status, so a delayed method (boleto) fulfils on async_payment_succeeded, not on the earlier completed. Idempotent: each plan handler assigns an absolute state, so replays converge; a credit-pack purchase is a delta deduplicated by Checkout Session id. A storage failure returns 500 so Stripe re-delivers (safe under idempotency).

## Response `200`

Default Response

- object

## Other responses

- `400`: Default Response
- `429`: Default Response
- `500`: Default Response
- `503`: Default Response

---

[API](https://skmtc.dev/tamperlens/apis/tamperlens-api.md) · [All operations](https://skmtc.dev/tamperlens/apis/tamperlens-api/llms.txt) · [OpenAPI document](https://skmtc.dev/tamperlens/apis/tamperlens-api/revisions/e1b7ae64347b?raw)
