feat: Stripe webhook idempotency to prevent duplicate event processing #62

Closed
pook wants to merge 1 commit from feat/webhook-idempotency into main
Owner

Summary

  • Adds idempotency_keys table (event_id PK + processed_at timestamp) to track processed Stripe webhook events
  • Webhook handler checks for duplicate event.id before processing; returns 200 immediately for duplicates
  • New events are recorded after successful processing; stale records purged hourly (48h retention)
  • 11 unit tests verify duplicate detection, handler skip behavior, and purge logic

Files changed

  • packages/api/src/db/schema.ts — new idempotency_keys table
  • packages/api/src/services/idempotency.ts — new service (isDuplicate, markProcessed, purge)
  • packages/api/src/routes/billing.ts — idempotency guard in webhook handler
  • packages/api/src/index.ts — hourly purge scheduler
  • packages/api/tests/unit/idempotency.test.ts — 11 unit tests

Test plan

  • 11 unit tests pass (bun test packages/api/tests/unit/idempotency.test.ts)
  • Run db:push to create the idempotency_keys table in staging
  • Send duplicate Stripe test webhook and verify no side effects

🤖 Generated with Claude Code

## Summary - Adds `idempotency_keys` table (event_id PK + processed_at timestamp) to track processed Stripe webhook events - Webhook handler checks for duplicate `event.id` before processing; returns 200 immediately for duplicates - New events are recorded after successful processing; stale records purged hourly (48h retention) - 11 unit tests verify duplicate detection, handler skip behavior, and purge logic ## Files changed - `packages/api/src/db/schema.ts` — new `idempotency_keys` table - `packages/api/src/services/idempotency.ts` — new service (isDuplicate, markProcessed, purge) - `packages/api/src/routes/billing.ts` — idempotency guard in webhook handler - `packages/api/src/index.ts` — hourly purge scheduler - `packages/api/tests/unit/idempotency.test.ts` — 11 unit tests ## Test plan - [x] 11 unit tests pass (`bun test packages/api/tests/unit/idempotency.test.ts`) - [ ] Run `db:push` to create the idempotency_keys table in staging - [ ] Send duplicate Stripe test webhook and verify no side effects 🤖 Generated with [Claude Code](https://claude.com/claude-code)
feat: add Stripe webhook idempotency to prevent duplicate event processing
Some checks are pending
agent-worker/pr-tests Running PR tests...
5966d8a699
Duplicate Stripe webhook deliveries could corrupt payment state or
unlock documents twice. This adds an idempotency_keys table to track
processed event IDs, skipping duplicates with a 200 response, and
purging stale records every hour (48h retention).

Closes #53 (idempotency concern)

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Author
Owner

⚠️ No Test Suite Detected

Commit: 5966d8a6

No test script found in package.json. Add a test script to enable automated testing.

## ⚠️ No Test Suite Detected **Commit:** `5966d8a6` No `test` script found in `package.json`. Add a test script to enable automated testing.
Author
Owner

Closed 2026-04-10 during pipeline triage.

Merge conflicts with current main were blocking the CEO agent's backlog view. The compliancebot repo had ~60 open PRs and 141 open agent-task issues. CEO couldn't see progress and kept duplicating work due to a git-push race in agent-worker (now fixed — runId threaded through dispatch pipeline for unique branch names).

Reopen / resubmit against current main if the work is still relevant. Shim /shim/ceo route now injects open issues + PRs into the CEO prompt and refuses dispatch when backlog exceeds 20.

Closed 2026-04-10 during pipeline triage. Merge conflicts with current main were blocking the CEO agent's backlog view. The compliancebot repo had ~60 open PRs and 141 open agent-task issues. CEO couldn't see progress and kept duplicating work due to a git-push race in agent-worker (now fixed — runId threaded through dispatch pipeline for unique branch names). Reopen / resubmit against current main if the work is still relevant. Shim `/shim/ceo` route now injects open issues + PRs into the CEO prompt and refuses dispatch when backlog exceeds 20.
pook closed this pull request 2026-04-10 15:08:21 -04:00
Author
Owner

Duplicate of #68 — consolidated stale issue cleanup

Duplicate of #68 — consolidated stale issue cleanup
Some checks are pending
agent-worker/pr-tests Running PR tests...

Pull request closed

Sign in to join this conversation.
No reviewers
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
pook/compliancebot!62
No description provided.