Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Phpamqplib Messenger Laravel Package

checkthiscloud/phpamqplib-messenger

Symfony Messenger transport for RabbitMQ built on the pure-PHP php-amqplib library instead of the php-amqp C extension. Point a phpamqplib DSN at your broker to create exchanges, queues, and bindings, and gain async consumers, efficient message streaming, and easier PHP upgrades.

View on GitHub
Deep Wiki
Context7

Technical Evaluation

Architecture Fit checkthiscloud/phpamqplib-messenger is a Symfony bundle, not a Laravel package. It registers as Jwage\PhpAmqpLibMessengerBundle\PhpAmqpLibMessengerBundle in config/bundles.php and plugs a new transport into framework.messenger.transports via a phpamqplib:// DSN. That means it only fits stacks running Symfony FrameworkBundle (Symfony 6.4/7.x/8.x); a Laravel application would need to adopt Symfony's Messenger component and its bundle/DI bootstrapping first, which is a heavy architectural change and should be treated as out of scope unless Messenger is already in place.

Where the fit is genuinely strong:

  • Eliminates the ext-amqp C extension. The transport speaks AMQP through php-amqplib/php-amqplib in pure PHP. This matters when our base images are Alpine/distroless, when we cannot compile PECL extensions in CI or on managed runtimes, and when PHP minor upgrades historically break the extension before the library.
  • True asynchronous consumers. php-amqplib streams from the broker with a blocking read and a fetchSize/prefetch hint instead of polling get(). That translates into lower idle CPU and lower message latency on low-volume queues.
  • Safe worker shutdown. Blocking consume plus pcntl signal handling means a SIGTERM from Kubernetes or Supervisor lets the in-flight handler finish rather than aborting mid-message — a real operational win versus the known consume() behaviour of ext-amqp.
  • Reliability-first defaults. Publisher confirms are on and publishes are retried when the client cannot tell whether the broker received the frame. The vendor explicitly documents that this can produce at-least-once duplicates, so handlers must be idempotent. That is an architectural precondition, not an implementation detail.
  • Convention over configuration. DSN parsing creates the exchange, binds the queue, and targets the vhost; advanced knobs (exchange type, queue durability, DLX, delays, QoS) live in the bundled docs/.

Integration Feasibility

  • High for an existing Symfony app already on Messenger with symfony/amqp-messenger: it is largely a DSN-scheme swap plus extension removal.
  • Medium where topology is centrally managed. If a platform team pre-declares exchanges/queues with strict policies, the bundle's declaration behaviour must be disabled or aligned, or the broker returns PRECONDITION_FAILED.
  • Low for Laravel-only stacks, and for teams unwilling to own a pre-1.0 dependency.

Technical Risk

  • Supply-chain / maturity risk (primary). 0 stars, 0 dependents, a 0.x version line, and a single visible maintainer (@kralmichal). The Jwage\ root namespace signals a re-hosted or forked codebase under a new org. Under SemVer, 0.x permits breaking changes on minor bumps, and the 0.10 → 0.11 series already churned composer requirements (adding ext-sockets, bumping symfony/uid, adding symfony/dependency-injection). This is a pin-exact-version, review-every-upgrade dependency, not a floating one.
  • Absorption-by-core risk. The stated roadmap is to reach 1.0 as a third-party bundle and then land in Symfony core as symfony/phpamqplib-messenger around the 7.4 LTS line. That is good long-term news but creates a namespace and package migration somewhere in our future. Config should be isolated so the swap is a one-file change.
  • Duplicate delivery. Confirms + retry-on-uncertainty means at-least-once by design. Without idempotency keys or dedupe storage we will get double-charged orders and double-sent emails.
  • Dependency surface. Pulls symfony/messenger, symfony/dependency-injection, symfony/uid, and requires ext-sockets (added in 0.11.0). Version ranges must be reconciled with the rest of the app; a mixed Symfony minor set is the most likely first-day failure.
  • Documentation gaps. The README is thin and points to docs/index.md; there is no published production runbook, no load/soak evidence, and no benchmark of confirms-on throughput. Real-world behaviour under our prefetch and message-size profile is unproven.
  • Metadata anomaly. The release list shows dates into late 2026 and a very compressed 0.10.x → 0.11.2 cadence (hotfix, ext removal, ext addition, composer bumps). Rapid patch churn on a 0.x package is a signal to gate adoption behind our own compatibility test, not to trust the version number.
  • Coverage is now measurable. Codecov plus PHPUnit reporting landed in 0.11.2, which is the first objective quality signal available. Treat the coverage report as an input, not a guarantee — coverage on the publish/retry/fetch paths is what matters to us.

Key Questions

  1. Do we run Symfony Messenger today, and on which Symfony minor? Is a 7.x or 7.4 LTS upgrade already on the roadmap?
  2. Is ext-amqp actually blocked in our build or runtime (Alpine, distroless, managed platform, locked PECL)? If the extension installs cleanly, the business case weakens considerably.
  3. Can we add ext-sockets and accept the symfony/dependency-injection / symfony/uid constraints without conflicting with pinned versions?
  4. Who owns RabbitMQ topology — us or a platform team — and can this bundle declare exchanges and queues, or must declaration be suppressed?
  5. Are our message handlers provably idempotent today, and if not, what is the cost to make them so before cutover?
  6. Does the team accept a single-maintainer, 0-star dependency for a production message path, and who is the named internal owner if upstream stalls?
  7. What is our contingency for the eventual Jwage\… → symfony/phpamqplib-messenger namespace move — fork, adopt core, or fall back to symfony/amqp-messenger?
  8. What latency/throughput budget do we need, and have we measured confirms-enabled publish rates against it?

Integration Approach

Stack Fit

  • Target profile: a Symfony 6.4/7.x service using Messenger for async work, containerised, RabbitMQ 3.12+ reachable over AMQP 0-9-1.
  • Coexistence: the transport is additive. Existing amqp:// transports and phpamqplib:// transports can run side by side in the same messenger.yaml, which is what makes a per-transport cutover possible.
  • Prerequisites to confirm before any code change: ext-sockets present in the image, composer resolution clean against our Symfony pins, network policy open to the broker, and vhost permissions that allow exchange/queue declaration (or a decision to declare out-of-band).
  • Not a fit: Laravel queue workers, or any service whose messaging goes through a cloud provider SDK rather than AMQP.

Migration Path

  1. Inventory and baseline. List every framework.messenger.transports entry, note exchange/queue/DLX/retry settings, and capture current throughput and consumer lag as the comparison baseline.
  2. Dependency gate. composer require --dry-run checkthiscloud/phpamqplib-messenger:0.11.2 against the app's lockfile; resolve symfony/messenger, symfony/dependency-injection, and symfony/uid conflicts deliberately, not by letting Composer drift. Pin the exact patch and commit the lockfile.
  3. Register the bundle in config/bundles.php behind the all environment, and keep ext-amqp installed in the image for the duration of the pilot so rollback is a config revert, not a rebuild.
  4. Add one pilot transport with a parallel DSN pointing at a non-critical queue, e.g. phpamqplib://user:pass@rabbit:5672/vhost/orders_pilot, with explicit exchange type, durability, and DLX settings rather than relying on defaults.
  5. Parity test. Publish the same message shape through both transports; verify consumer receives identical envelopes, headers, and retry/DLX behaviour; confirm a forced connection drop during publish results in a retry and a single visible consumer-side effect.
  6. Idempotency hardening. Add dedupe keys (message id + business key) and a uniqueness guard in the handler before any real traffic moves. This is a prerequisite, not a follow-up.
  7. Cutover per transport. Flip DSNs one queue at a time, oldest/lowest-risk first; keep the old transport definition commented in place for a defined rollback window.
  8. Deprovision the extension. Only after all transports are migrated and a soak period has passed, remove ext-amqp from the image and from CI, and simplify the Dockerfile accordingly.

Compatibility and Sequencing Notes

  • Sequence composer constraint resolution → bundle registration → single-transport pilot → idempotency → full migration → extension removal. Doing extension removal early destroys the rollback path.
  • If a Symfony 8.x upgrade is on the roadmap, adopt 0.11.2 or later specifically for the fetchSize receiver hint; older 0.10.x will need an adapter shim when the framework advances.
  • Budget for a second migration when the package lands in Symfony core — keep transport config in one file and avoid referencing Jwage\ classes directly in application code.

Operational Impact

Maintenance

  • Upgrade cadence is on us. A 0.x dependency with a single maintainer and no dependents means we are effectively the QA function. Nominate an owner, subscribe to releases, and review every minor bump against a pinned-version CI job. Do not allow ^0.11 floating ranges in production manifests.
  • Two migrations are likely, not one: the 0.x → 1.0 stabilisation and the third-party → Symfony core absorption. Both are cheap if application code touches only DSNs and message classes, and expensive if it references bundle internals.
  • Low ongoing code surface. The bundle is thin — transport, connection, receiver, sender — so the maintenance burden is mostly dependency hygiene rather than patching logic. The fetchSize release shows the maintainer tracking Symfony's transport contract, which is the right thing to watch.

Support

  • Upstream support is community/best-effort. There is no vendor SLA, no LTS commitment, and no commercial backer. Escalation path for a production incident is: our own Symfony/RabbitMQ engineers, then the upstream issue tracker. Plan accordingly for tier-1 services.
  • Internal knowledge must be seeded, not borrowed. At minimum one engineer should be able to read the transport source and explain connection setup, confirms, and prefetch. The docs directory is adequate for configuration but not for incident response.
  • Broker-side expertise is the real dependency. Most failures will look like AMQP problems (blocked connections, resource alarms, policy conflicts), not bundle bugs. Support for those sits with whoever owns RabbitMQ.

Scaling

  • Favourable: async consume with a blocking read scales down better than polling (no idle get() churn) and scales up predictably via prefetch/fetchSize and consumer replica count, since workers stay stateless.
  • Throughput caveat: publisher confirms are enabled by default and the package explicitly prioritises reliability over raw performance. Publish-heavy paths (fan-out, high-rate event emission) must be benchmarked before we assume parity with ext-amqp. Tune fetchSize/prefetch and confirms settings against measured latency budgets, not defaults.
  • Horizontal scaling is broker-bound, not library-bound — connection count, channel count, and memory per worker are the levers. Long-lived pure-PHP consumers need a max-messages/max-time recycle policy to bound memory growth.
  • Topology scaling: one transport per queue keeps blast radius contained; declaring topology from DSNs is convenient at small scale and awkward once several services share an exchange, which is the point at which declaration should move to infrastructure-as-code.

Failure Modes

  • Duplicate delivery after a connection drop during publish — the documented, expected behaviour. Mitigation: idempotent handlers, dedupe store, and monitoring for duplicate business keys.
  • Topology mismatch (PRECONDITION_FAILED on a mismatched exchange type or queue argument) — mitigation: align with broker-declared policies, or disable declaration and manage topology externally.
  • Consumer stalls / connection loss with no reconnect, leaving workers idle-but-alive — mitigation: heartbeat tuning, worker health checks, --time-limit/--memory-limit recycling, and lag alerting rather than process-liveness alerting alone.
  • Blocked connection from a broker memory or disk alarm, which presents as publish latency rather than errors — mitigation: alert on publish duration percentiles, not just error rates.
  • Unacked message pile-up after a crashed worker mid-handler — mitigation: bounded prefetch, sensible ack timeout, and DLQ with a redrive runbook.
  • Composer drift breaking a deploy after an unrelated composer update — mitigation: exact pins, lockfile commits, and a canary deploy for message-path services.
  • Upstream abandonment or namespace move — mitigation: named internal owner, a documented fallback to symfony/amqp-messenger, and rollback tested during the pilot.

Ramp-Up

  • Engineer effort: roughly 1–2 days for a Symfony-fluent developer to wire the bundle, run the pilot transport, and validate dispatch/consume/retry locally. Most of that time is dependency resolution and broker access, not the package.
  • Hidden effort: idempotency work in handlers is the real cost and is entirely ours. Estimate per message type, not per transport.
  • Team effort: half a day of shared context on the reliability model (confirms, at-least-once, idempotency), one hour on the core-absorption roadmap, and a short runbook covering DLQ redrive, worker restart, and rollback to amqp://.
  • Documentation debt to close internally: transport inventory, prefetch and retry settings per queue, alert thresholds for lag and publish latency, and the explicit statement that this dependency is pre-1.0 and pinned. Treat the Codecov report as a merge gate for any version bump and re-run the pilot parity test on each minor upgrade.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
uni-method/symfony-lib
tacticmedia/scim-server-bundle
neika-ai/symfony-bundle
mattleads/agent-publishing-bundle
glavweb/framework-bundle
glavweb/extra-bundle
glavweb/api-bundle
glavweb/admin-bundle
adachsoft/api-version-bundle
elsayed85/laravel-api-exceptions
ouhssini/laravel-demo-mode
daworks/ncloud-outbound-mailer-driver
gp247/cms
ignibyte/aic-gates
nexa-merchant/blog
novasa/laravel-language-center
opencage/geocode
adolfoholzer/parameters
livenetworks/ln-starter
cgv/localized-resource