Product Decisions This Supports
Channel strategy & roadmap
- Adding web push as a first-class notification channel. This library is the delivery engine for anything you'd promise as "notify the user on desktop/mobile web": time-sensitive alerts, transactional status changes, price/stock triggers, chat and collaboration pings, and re-engagement nudges.
- PWA vs. native app bets. It de-risks a "web-first, app-later" roadmap: you can ship a re-engagement loop on the web without committing to App Store/Play Store release cycles, review queues, or a mobile team. If the roadmap is PWA-first, push is table stakes — this package is the cheapest path to it.
- Channel mix / cost reduction. Concrete input to build-vs-buy-vs-email-vs-SMS modelling: web push has no per-message vendor fee, so it is the natural substitute for low-urgency SMS and for lifecycle email that underperforms on mobile. Quantify the swap in the business case, not in the PRD.
- Notification preference center. The per-message options exposed here (
TTL, urgency, topic) are product levers, not technical trivia: topic collapses duplicate alerts into one ("your ride is 3 min away" replaces three), urgency is a battery/OS-visible choice on mobile, and TTL is the dial between "must arrive even if they're offline" and "only worth showing live." That mapping is a PM decision you can actually spec.
- Segment-level policy. Because options can be set globally, per flush, or per notification, you can ship tiered policies: high-urgency TTL-1-day for security alerts, TTL-0 for social noise, batched "digest" topics for everything else.
Build vs. buy
- Buy the protocol, build the product. Encryption, VAPID JWT signing, RFC 8030/8292 compliance, and multi-vendor endpoint quirks (Chrome/FCM, Firefox/autopush, Safari) are undifferentiated, high-risk engineering. This package is MIT-licensed and has been maintained across PHP 5.6 → 8.2, with a release dated 2026-07-23 — a credible "buy" (in the free sense) on the hard part.
- Do not buy a push SaaS reflexively. Sending to push services directly via VAPID means subscriptions and payloads stay in your own database — a genuine privacy/procurement talking point, and it removes a per-subscriber vendor line item. Trade-off: you also own deliverability, template, scheduling, and analytics tooling that a vendor would bundle.
- The real build decision is the wrapper. You still need: a
push_subscriptions table, subscription lifecycle (register/refresh/invalidate), a Laravel notification channel, retry/backoff, templating, quiet hours, and a send-time preference check. That layer is product-visible and worth owning; scope it as its own epic rather than sneaking it into "integrate the library."
Operational and lifecycle decisions this surfaces
- Expiry handling is a product requirement, not housekeeping. The library reports per-endpoint failure and an
isSubscriptionExpired() flag. Someone must decide the prune policy — this becomes a scheduled job and a metric (subscription decay rate), and it directly determines whether your "reachable audience" number in the dashboard is honest.
- Payload budget is a design constraint. Practical payload ceiling is ~3052 bytes. Decide early whether payloads carry full content or a thin "fetch it" signal, because that decision propagates into offline behaviour, service-worker complexity, and privacy posture.
- Infrastructure upgrade timing. Requires PHP 8.2+ on current versions; older pins exist for older runtimes. If you're on an older Laravel/PHP baseline, this package can be the forcing function for a platform upgrade — flag it as a cost, not a footnote.
- Fan-out sizing. Default batch size is 1000, tunable for memory. If a campaign can hit tens of thousands of devices, that's a queue architecture and capacity-planning conversation, not a library detail.
When to Consider This Package
Adopt when:
- The audience is web-first or PWA-based — desktop and mobile browser users you can reach without an installed native app.
- You are already on PHP 8.2+ / Laravel and want push to live in the same codebase, queue workers, and deploy pipeline as everything else — no second runtime, no separate auth model.
- You need protocol-level correctness without owning crypto: VAPID signing, payload encryption, and padding (on by default, better security at a modest CPU cost) are handled.
- Broadcast fan-out is a real use case. The queue-then-flush model with batching, VAPID header reuse (
setReuseVAPIDHeaders(true)), and per-message reports is designed for volume.
- Data residency / privacy matters: sending directly to browser vendor push services with your own keys keeps subscriber data and message content out of a third-party marketing platform.
- You want a liberal licence (MIT) with no seat-based or volume-based pricing to negotiate.
Look elsewhere when:
- The primary need is native iOS/Android push. This library targets the Web Push protocol, not APNs/FCM mobile SDK flows; a native app strategy needs a different (or additional) provider.
- You need a managed product around the pipe: visual campaign builder, journeys, A/B testing, rich media, delivery analytics, and a support contract. That's a commercial push platform, and self-hosting here means building all of it.
- Guaranteed delivery is a stated requirement. Push is best-effort by design — TTL, device offline state, and OS-level suppression all apply. Anything contractual needs an in-app inbox or email fallback.
- The team has no PHP/Laravel appetite or is standardising on Node/Go services; wrapping a PHP library into a polyglot architecture adds a service boundary you don't want.
- You are unwilling to own subscription storage and pruning. Without a disciplined expiry job, list quality decays and your metrics lie.
- Compliance constraints require audited, contracted messaging infrastructure with SLAs and DPA coverage — a community-maintained OSS library won't satisfy that on its own.
Adoption hygiene (set as entry criteria):
- VAPID keys generated once, stored in secrets management, never rotated casually — they're baked into clients and changing them invalidates every subscription.
- A named owner for the subscription table and its decay metrics.
- A test plan across Chrome, Firefox, and Safari, since vendor behaviour (notably around
urgency and content encoding) diverges.
How to Pitch It (Stakeholders)
For executives — one paragraph:
We can add a web push channel with a mature, MIT-licensed PHP library that speaks the standard Web Push protocol directly, rather than signing a per-subscriber messaging SaaS contract. It removes a recurring vendor cost, keeps subscriber data and message content in our own systems, and gives us a re-engagement and alerting loop that doesn't depend on app-store releases. The engineering cost is a focused integration — subscription storage, a notification channel, and expiry handling — not a platform build. Risks are bounded and well understood: it's a free dependency we can replace, browser push is best-effort so we pair it with existing channels rather than replacing them, and it requires our PHP runtime to be on 8.2+.
For engineering — the ask:
- Treat the library as the delivery primitive and scope the surrounding layer explicitly:
push_subscriptions schema, service-worker registration, a queued notification channel, retry/backoff, and a scheduled prune job driven by the library's expiry signal.
- Set policy defaults in config, not code: TTL, urgency, topic, batch size, content type. Safari has been observed to reject messages lacking
urgency, so don't leave it implicit.
- Design for the ~3052-byte practical payload cap from day one; prefer thin payloads plus a fetch, and keep message content out of logs.
- Iterate
flush() exactly once — it's a generator — and persist per-endpoint reports; those rows are our deliverability dataset.
For product — what to promise and what not to:
- Promise: a second, essentially free channel for time-sensitive and lifecycle messaging; user-controlled preferences and quiet hours; deduplication via
topic so we don't spam.
- Don't promise: guaranteed delivery, rich media, or precise open/click attribution without additional instrumentation.
- Define success up front: opt-in rate, subscription decay rate, delivery success rate per vendor, and click-through versus the channel it displaces (usually email or SMS). If push isn't displacing something measurable, the roadmap case is weaker than it looks.
For finance/legal — the short version:
No licence fee, no per-message fee, MIT terms, actively released. Cost is internal engineering time plus ongoing ownership of subscription hygiene; benefit is avoided vendor spend and avoided app-store dependency.