coconutcraig/laravel-postmark
Laravel mail transport for Postmark, sending transactional email through Postmark's API instead of SMTP. Drop-in driver configuration, supports Laravel notifications and mailables, and handles Postmark-specific features like message streams and tags with minimal setup.
Architecture fit. This is a thin mail transport adapter: it registers a postmark transport so Laravel's Mail facade and queue workers hand messages to the Postmark API instead of SMTP. For a TPM the important property is that it sits entirely behind a stable framework contract. Everything above the Mail facade — Mailables, notifications, queued jobs, templates, localization — is unaffected by swapping it out. That clean seam is what makes this a cheap, low-drama program item rather than an architecture risk. Treat it as replaceable infrastructure, never as a platform dependency, and never let it leak into product code (no direct calls to package classes, no Postmark-specific logic scattered through services).
Integration feasibility. High in isolation, conditional in practice. If the application is already on Postmark and on a Laravel version the package supports, adoption is a Composer install plus three config edits (server token in config/services.php, a named mailer in config/mail.php, MAIL_MAILER in the environment). The genuine feasibility question is the version matrix, not the code. The package's last release was 2020-10-30; community guidance places support around Laravel 6–8, and Laravel 9+ replaced the Swift Mailer layer this package hooks into and shipped a first-party Postmark transport via symfony/postmark-mailer. The README's claims should not be treated as authoritative eight years after the freeze — confirm empirically before it enters a plan or a schedule.
Technical risk. Lifecycle risk dominates; technical complexity is negligible. Ranked:
| Risk | Severity | Why it matters to the program |
|---|---|---|
| Framework cliff (Swift Mailer removal in Laravel 9) | High | Retirement is not optional; it is forced by any framework upgrade. The package is a blocking dependency on the modernization roadmap. |
| Abandoned upstream (single maintainer, 0 dependents, ~218 stars) | High | No ecosystem backstop, no security patching, no PHP 8.x guarantees. Fails procurement/audit conversations about supported vendors in a delivery path. |
| Config drift across versions | Medium | The env key changed between releases (POSTMARK_TOKEN vs. POSTMARK_API_KEY/POSTMARK_SECRET). A silent misread produces "mail sent" with nothing delivered. |
| Postmark API drift | Medium | Adapter frozen in 2020; API behavior and error semantics may have moved. |
| Shadow integration | Medium | Advanced features (tags, message streams, templates, batch, suppressions, webhooks) are not exposed. Teams that need them will call wildbit/postmark-php directly, creating a second, unmonitored sending path. |
| MIT fork temptation | Medium | Licensing permits vendoring, but owning a fork costs more over twelve months than migrating — and it isn't on anyone's roadmap until it is. |
Key questions (each needs an owner and a date before funding a plan):
Stack fit. Only for Laravel applications already committed to Postmark as the ESP. It is not a Postmark SDK and has no place in non-Laravel services or background workers written in other runtimes. Note the sequencing dependency: choosing Postmark is a separate, larger decision (deliverability, pricing tier, message streams); this package is downstream of it and is never a reason to make it.
Migration path — frame as a decision, not a task. Four options, each with a cost the program can defend:
Transport class. Roughly 1–2 engineer-days including tests. Only rational if the framework upgrade is blocked for reasons unrelated to mail.Recommend B as the destination and A as the interim posture. Explicitly reject preemptive forking: MIT means we can vendor it, but the twelve-month carrying cost of an owned fork exceeds migration, and a fork needs a named owner, a patching cadence, and an exit criterion before anyone starts.
Compatibility. Produce one version-matrix artifact before scheduling anything: Laravel version, PHP version, Composer constraints, presence/absence of Swift Mailer, and the exact env key the installed release expects. Gate the plan on it. If the matrix shows the target Laravel version is unsupported, the answer is native transport or a maintained alternative — not a production patch on the delivery path.
Sequencing (with gates).
Mail::fake() and assertQueued() behave identically to SMTP, so the test suite barely notices the transport; add one real end-to-end smoke send to a Postmark inbound address, verified in the activity log.MAIL_MAILER), everything queued with tries/backoff, and a failover mailer (['postmark', 'smtp']) so a Postmark outage degrades instead of dropping mail.Cross-team dependency map to manage explicitly: platform/Laravel engineering (implementation), infrastructure/DevOps (queue workers, secrets management, DNS), security (dependency review, exception sign-off), email/deliverability ops (domain auth, bounce policy), procurement (any vendor-support requirement). The single most likely schedule failure is DNS/domain verification owned by someone outside the delivery team.
Maintenance. Low code surface, elevated lifecycle exposure. Assign a named owner, pin the version (no floating constraints), and make every Laravel major upgrade a compatibility gate with this package on the checklist. Adopt a standing policy — no unmaintained dependency in a critical path without a documented exception and a dated retirement plan — because that artifact is what survives an audit. Review fork-or-replace on a fixed cadence, not when something breaks.
Support. Community-only, no SLA. Postmark supports delivery and API behavior; package defects and Laravel integration problems fall to the internal team. Publish an escalation path and make sure on-call knows that "mail is down" is an application-level page, not a vendor ticket.
Scaling. Postmark absorbs delivery scale; application-side scale is queue workers, concurrency, rate limiting, and retry/backoff behavior. Capacity-plan the queue, not the transport. Track send latency, API throttling, queue backlog/age, bounce and complaint rates, and suppressed-recipient counts. Postmark pricing tiers are volume-based and message-stream-scoped — model cost at projected volume when the ESP decision is revisited.
Failure modes — each needs detection, mitigation, and an owner:
Ramp-up. Laravel developers are productive in hours because the integration follows framework conventions; the TPM's ramp is governance, not code. Before production: runbook (rotate token, verify domain, replay dead letters, fail over to SMTP), rollback procedure, dashboards for the metrics above, a quarterly dependency-review cadence, and a written decision record stating why this package is retained, until when, and who owns its retirement.
How can I help you explore Laravel packages today?