TECHNICAL REFERENCE STACK · 10 COMPONENTS

Database-Backed Subscription Payment Webhook Foundation

A partial, self-hosted implementation foundation for subscription payment intake using Stripe API as the payment-provider candidate, an Express webhook service, PostgreSQL as the authoritative event and entitlement ledger, and database-backed recovery workers. The supplied catalogue establishes that Stripe API supports acceptance and management of online payments; subscription creation and all detailed webhook, signing, lifecycle, reconciliation,

Publication review2026-10-18 UTC
Latest official source retrieval2026-10-18 UTC
Validation levelReference architecture
↳
FROM THEORY TO IMPLEMENTATION

Executable examples and validation

No executable package has been validated for this architecture yet. The implementation sequence below is guidance, not a tested repository.

Validation badges are scoped to specific artifacts and recorded tests. They never certify a full stack unless that scope was actually tested.

01
TECHNICAL DESIGN

Architecture and implementation

Architecture

Run containerized Express application and recovery-worker processes, PostgreSQL, and Nginx on a deliberately managed DigitalOcean-hosted server deployment. Nginx exposes only the required HTTPS application and webhook endpoints and proxies to the application service; PostgreSQL is not publicly exposed. Let’s Encrypt is the certificate authority candidate, but an ACME client and challenge-routing design are not supplied by the catalogue and must be selected before relying on automated certificate issuance or renewal.

Authenticated application routes use Auth0 for user identity, subject to independently validating the application integration. The application, not the browser, owns the product/price offering mapping and provider API calls. It records a trusted mapping among internal account, expected provider customer, expected subscription, provider account, and environment. A webhook is eligible to affect an entitlement only when signature verification has passed under documented provider rules and its provider objects match that trusted mapping.

The webhook endpoint preserves the original request bytes as required by the selected provider procedure, performs provider-supported verification before interpreting the payload, and durably inserts a received-event record plus pending-work record in one PostgreSQL transaction. It acknowledges successful receipt only after that transaction commits; persistence failures receive a retryable failure response rather than a success acknowledgement. A unique provider event identifier prevents duplicate acceptance, but records retain explicit received, pending, processing, completed, failed, and reconciliation-required states.

A database-backed dispatcher finds due pending work and grants a time-bounded, fenced processing lease. Workers serialize entitlement decisions and reconciliation for the same subscription through the same subscription-scoped ownership mechanism. A worker atomically applies a documented event-specific entitlement decision, records the fencing token and outcome, and marks the event complete in one transaction. Lease expiry, ownership loss, contradictory state, stale events, unmapped provider objects, and uncertain ordering move work to retry or reconciliation-required rather than directly changing access. Reconciliation reads current provider state only after its provider contract and object-binding rules have been documented; it uses the same per-subscription serialization as webhook work to avoid race conditions.

Encrypted database backups and recovery artifacts are exported to Amazon S3 through a separately designed backup process. Sentry receives only tested, redacted operational telemetry; it must not ingest request bodies, authorization headers, signing material, payment-related data, or sensitive trace and breadcrumb fields.

Implementation sequence

  • Treat payment-provider evidence as a release gate. Retain current authoritative documentation and integration tests for the selected provider account and environment covering subscription creation, request idempotency, signature verification, raw-body requirements, replay or timestamp handling, event identifiers, delivery behavior, lifecycle semantics, provider-object retrieval, and reconciliation.
  • Define a server-controlled offering catalogue. Map each internal offering to approved provider references, prevent client-supplied provider prices or subscription targets from becoming authoritative, and retain an internal purchase-attempt identifier for creation-request idempotency.
  • Define the account authorization model using Auth0 as the identity candidate: validate authenticated user identity, authorize the requested internal account, and ensure only authorized actors can initiate or manage that account’s subscriptions. Establish trusted internal mappings to the expected provider customer, subscription, provider account, and environment.
  • Model PostgreSQL tables for provider events, provider-object mappings, purchase attempts, subscriptions, entitlements, pending work, processing leases, reconciliation cases, and append-only decision audit records. Enforce unique provider event identifiers and provider-object mappings where the documented model requires uniqueness.
  • Implement webhook acceptance so signature verification occurs under the provider-documented raw-request procedure before business interpretation. Commit the event receipt and pending-work record together, acknowledge only after commit, and return retryable failures when durable acceptance cannot be established.
  • Implement a dispatcher and workers that claim pending records using expiring leases with monotonically fenced ownership tokens. Require every completion and entitlement mutation to verify current lease ownership, and atomically record the decision, entitlement change, and terminal event state.
  • Create an explicit lifecycle decision matrix. For each documented provider event and current-state outcome, define whether it grants, preserves, restricts, revokes, retries, or requires reconciliation; unknown, stale, contradictory, or unmapped events must not directly alter access.
  • Implement reconciliation as a separately auditable process that uses documented provider current-state retrieval and the same subscription-scoped ownership path as webhooks. Test webhook-versus-reconciliation races, concurrent workers, duplicate delivery, delayed delivery, expired leases, worker termination, database rollback, and failure between acceptance and dispatch.
  • Deploy the selected self-managed mode with Docker on DigitalOcean: isolate database access from public ingress, define operator ownership for host patching, database operations, backup jobs, restore drills, incident handling, and upgrades. Require verified TLS for every remote database connection; do not expose PostgreSQL publicly.
  • Select an ACME client and either an HTTP-01 routing design or a DNS-01 credential model before using Let’s Encrypt. Document renewal scheduling, Nginx certificate reload behavior, least-privileged DNS access if applicable, and certificate-expiry monitoring.
  • Pin a tested compatibility matrix for a currently supported Node.js runtime and all application, provider SDK, database, Docker, Nginx, and monitoring dependencies. Load-test webhook bursts, hot-subscription contention, worker backlog, database connection pressure, and reconciliation latency before enabling entitlement automation.
  • Configure Sentry and all application logging with deny-by-default request-data capture. Test redaction for headers, bodies, query values, breadcrumbs, traces, exception context, webhook payloads, credentials, signing secrets, and payment-related fields before telemetry is accepted.

Security and operations

  • Webhook signature verification is necessary but insufficient for entitlement assignment. Check authenticated account authorization on application routes and verify each accepted webhook maps to the expected internal account, provider customer, subscription, provider account, and deployment environment.
  • Do not enable webhook-driven entitlement changes until the selected provider configuration’s verification procedure, raw-body handling, replay protections, subscription lifecycle semantics, current-state reconciliation, and creation idempotency behavior are evidenced by official documentation and tests.
  • Use stable server-generated idempotency keys for provider-side subscription or payment creation, tied to internal purchase-attempt records. Webhook deduplication does not prevent duplicate provider objects created by retried initiation requests.
  • Acknowledge delivery only after PostgreSQL durably accepts the event and pending work. Duplicate rows, pending events, failed events, and expired leases must not be treated as completed solely because an event identifier already exists.
  • Use fenced, expiring worker leases and one subscription-scoped serialization mechanism shared by webhook processing and reconciliation. Atomically validate lease ownership with entitlement updates and completion state to prevent an expired worker from committing stale effects.
  • Keep provider credentials, signing secrets, database credentials, and Sentry credentials outside source control, client code, logs, event records, and telemetry. The catalogue contains no dedicated secret-management product; select, restrict, rotate, and audit a secret-storage mechanism as an unresolved deployment control.
  • Restrict inbound network access to the HTTPS reverse proxy and administrative access paths that are explicitly required. Keep PostgreSQL private; require and verify TLS for remote database sessions rather than assuming encryption is present.
  • Back up PostgreSQL event, mapping, purchase-attempt, entitlement, lease, and recovery records. Encrypt backups before or during the selected backup workflow, restrict backup access, define retention and restoration owners, and perform restoration tests. S3 storage alone does not configure these controls.
  • Configure and test telemetry redaction before sending data to Sentry. Do not rely on monitoring defaults to remove credentials, webhook payloads, payment data, or sensitive user attributes.

Limitations

  • The catalogue establishes Stripe API as an online-payment API but does not itself establish the selected configuration’s detailed subscription, webhook signing, replay tolerance, retry, ordering, event identity, lifecycle, current-state lookup, or idempotency contract.
  • This is a self-managed PostgreSQL deployment on server infrastructure, not a managed database specification. Availability design, host patching, storage durability, database upgrades, backup scheduling, recovery objectives, and operational ownership require project decisions and testing.
  • No dedicated secret-management, network-policy, firewall-management, ACME-client, scheduler, or backup-orchestration product is supplied in the catalogue. The required controls for these capabilities remain implementation and operations gaps.
  • Auth0 provides identity capabilities in the catalogue, but the catalogue does not prove compatibility with the selected Express implementation or define account authorization, token validation, user provisioning, or mapping behavior.
  • The correctness of PostgreSQL locking, fencing, lease recovery, transaction boundaries, and reconciliation race handling depends on the application implementation and failure testing; it is not established merely by selecting PostgreSQL.
  • Let’s Encrypt does not supply an ACME client or selected HTTP-01/DNS-01 challenge workflow in the catalogue. Certificate automation and expiry alerting remain incomplete until those are designed and operated.
  • Sentry is a monitoring candidate, not proof of data scrubbing, retention, residency, alert ownership, or incident-response capability.
  • No supported version matrix, runtime support policy, capacity plan, performance result, availability target, pricing estimate, tax treatment, refund/dispute process, or regional eligibility determination is provided.

Alternatives to consider

  • Use PayPal Developer APIs (product 9) only after independently validating the relevant subscription, webhook verification, lifecycle, current-state reconciliation, provider-object binding, and idempotency requirements; retain the same database-backed event and entitlement controls.
  • Evaluate Paddle (product 8) where its merchant-of-record model is appropriate, but independently validate its subscription lifecycle, webhook verification, reconciliation, account mapping, and operational requirements before substitution.
  • Use FastAPI (product 21) with SQLAlchemy (product 89), or Django (product 22), for a Python implementation of the same PostgreSQL-backed acceptance, lease, entitlement, and reconciliation design; dependency compatibility and provider integration still require validation.
  • Use a separately operated Temporal deployment (product 92) only after specifying its hosting mode, persistence, authentication, networking, upgrades, backups, operational ownership, and database handoff failure behavior. Otherwise retain database-backed recovery workers.
  • Use RabbitMQ (product 91) for asynchronous dispatch only if durable publication, worker recovery, retry, dead-letter handling, lease fencing, and database transaction boundaries are explicitly designed and tested; it does not remove the PostgreSQL event-ledger requirement.

A reference architecture, not a tested deployment or guarantee of interoperability. Validate all external contracts, versions and prices before implementation.

02
PROVENANCE

Sources and review dates

Official pages are recorded with UTC retrieval timestamps. Retrieval confirms access to a page, not verification of every technical claim, price, or license.

Amazon S3Documentation · page retrieved
At publication2026-10-17
Latest retrieved2026-10-17
Source ↗
Auth0Documentation · page retrieved
At publication2026-10-17
Latest retrieved2026-10-17
Source ↗
DigitalOceanDocumentation · page retrieved
At publication2026-10-18
Latest retrieved2026-10-18
Source ↗
DockerDocumentation · page retrieved
At publication2026-10-17
Latest retrieved2026-10-17
Source ↗
ExpressDocumentation · page retrieved
At publication2026-10-18
Latest retrieved2026-10-18
Source ↗
Let's EncryptDocumentation · page retrieved
At publication2026-10-18
Latest retrieved2026-10-18
Source ↗
NginxDocumentation · page retrieved
At publication2026-10-18
Latest retrieved2026-10-18
Source ↗
PostgreSQLDocumentation · page retrieved
At publication2026-10-17
Latest retrieved2026-10-17
Source ↗
SentryDocumentation · page retrieved
At publication2026-10-18
Latest retrieved2026-10-18
Source ↗
Stripe APIDocumentation · page retrieved
At publication2026-10-17
Latest retrieved2026-10-17
Source ↗