spatie/laravel-webhook-client
Receive webhooks in Laravel apps with signature verification, payload storage, and queued processing. Handle incoming HTTP calls securely and dispatch jobs so your app processes webhook events reliably.
InvalidWebhookSignatureEvent. That means "did we verify the payload?" stops being a code-review question and becomes an architectural property you can assert to security and in a SOC 2 / vendor-review questionnaire.webhook_calls (headers too, or * for all), and queue-dispatch exceptions are captured on the record. That gives support and on-call a queryable source of truth for "the provider says they sent it, we say we never got it," and a concrete replay path — re-dispatch the job from the stored model rather than asking the partner to resend.delete_after_days (default 30) makes retention an explicit, reviewable setting rather than an accident of never deleting rows. Webhook payloads frequently contain PII, so this is a lever you can point at legal/DPO review.WebhookProfile lets you decline event types you don't care about before they're stored — so noise reduction, cost control, and "we only process what's on the roadmap" become a small class rather than a data-cleanup backlog item.Consider it when most of the following hold:
webhook_calls table is a usable v1.sync driver, so a synchronous-only deployment is a real adoption blocker.SignatureValidator per provider that doesn't. Budget that as per-integration work, not zero — Stripe's timestamped t=,v1= scheme, Shopify's base64 variant, and prefixed headers all need custom validators.Look elsewhere, or build around it, when:
laravel-webhook-server package, and worth evaluating as a pair so outbound and inbound don't diverge stylistically.For executives: Inbound webhooks are the connective tissue of our partner integrations, and today each one is hand-built — verification, logging, retry handling, and error capture reimplemented slightly differently every time. This package makes that a solved, standardized path. The business consequence is that integration work shifts from "build an ingestion pipeline" to "implement one provider's rules," which is where the actual differentiation is. It also gives us, by default, two things we currently lack: proof that every payload was cryptographically verified, and a durable record of every payload received that support and on-call can act on. It's MIT-licensed with a mature, actively released codebase, so there's no vendor commitment and no lock-in — the exit cost is low because the core is small and the extension points are ours.
For engineering: This replaces the ad-hoc webhook controller with a five-stage pipeline you configure, not fork: verify signature → apply a profile filter → persist to webhook_calls → dispatch a queued job → return a response. Each stage is an interface (SignatureValidator, WebhookProfile, RespondsToWebhook) plus a swappable Eloquent model and job base class, so provider-specific logic lives in our code and framework concerns stay in the package. Signature failures never touch the database and emit an event we can alert on; queue-dispatch exceptions are persisted on the record instead of vanishing. Register the route with Route::webhooks(...) and exclude it from CSRF. The one hard prerequisite is a real queue driver — do not ship this on sync, since the whole design premise is acknowledging fast and processing later. Two caveats to plan for rather than discover: provider signature schemes that aren't plain HMAC-SHA256-over-body need a custom validator, and deduplication/idempotency is not built in — if a provider can deliver the same event twice, we own that in the profile or the job. Treat webhook_calls as PII-bearing and confirm the retention window with legal before launch.
How can I help you explore Laravel packages today?