PHPackages                             phpdot/event - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Queues &amp; Workers](/categories/queues)
4. /
5. phpdot/event

ActiveLibrary[Queues &amp; Workers](/categories/queues)

phpdot/event
============

PSR-14 event dispatcher with attribute-based listener discovery, async dispatch, ordering, and persistence abstraction.

v0.1.0(1mo ago)00MITPHPPHP &gt;=8.5

Since Jul 18Pushed 1mo agoCompare

[ Source](https://github.com/phpdot/event)[ Packagist](https://packagist.org/packages/phpdot/event)[ RSS](/packages/phpdot-event/feed)WikiDiscussions main Synced 1w ago

READMEChangelogDependencies (21)Versions (4)Used By (0)

phpdot/event
============

[](#phpdotevent)

A PSR-14 event dispatcher where the `#[Listener]` attribute *is* the registration — no central config, no service providers. Listeners are ordered, can run synchronously or be queued for async dispatch, and the listener set is resolved through a repository so it can be persisted and toggled at runtime.

Table of Contents
-----------------

[](#table-of-contents)

- [Requirements](#requirements)
- [Installation](#installation)
- [Usage](#usage)
- [Architecture](#architecture)
- [Testing](#testing)
- [License](#license)

Requirements
------------

[](#requirements)

RequirementConstraintPHP`>= 8.5``psr/container``^2.0``psr/event-dispatcher``^1.0``psr/log``^3.0`Installation
------------

[](#installation)

```
composer require phpdot/event
```

Usage
-----

[](#usage)

### Events and listeners

[](#events-and-listeners)

An event is any class. A handler declares what it handles with `#[Listener]` — the attribute is the registration:

```
use PHPdot\Event\Attribute\Listener;

final readonly class UserRegistered
{
    public function __construct(public int $userId, public string $email) {}
}

#[Listener(UserRegistered::class, order: 1)]
final class SendWelcomeEmail
{
    public function __construct(private MailerInterface $mailer) {}

    public function __invoke(UserRegistered $event): void
    {
        $this->mailer->send($event->email, 'Welcome!');
    }
}
```

### Dispatching

[](#dispatching)

```
use PHPdot\Event\EventDispatcher;
use PHPdot\Event\ListenerProvider;

$provider = new ListenerProvider();
$provider->addListener(UserRegistered::class, SendWelcomeEmail::class, order: 1);

$dispatcher = new EventDispatcher($provider, $container, $asyncDispatcher, $logger);
$dispatcher->dispatch(new UserRegistered(userId: 1, email: 'omar@example.com'));
```

Listeners run in `order` (lowest first). An event implementing `StoppableEventInterface` halts the chain once propagation is stopped, per PSR-14.

### Async listeners

[](#async-listeners)

A listener marked `#[Listener(..., async: true)]` is handed to the injected `AsyncDispatcherInterface`instead of running inline. `SyncOnlyDispatcher` is the built-in fallback that resolves and runs the handler synchronously; a Swoole or queue-backed implementation can dispatch it off the request path.

Architecture
------------

[](#architecture)

`EventDispatcher` asks the `ListenerProvider` for the ordered listeners of an event, resolves each handler class through the container, and either invokes it synchronously or hands it to the async dispatcher. The listener set itself comes from a repository, so it can be discovered from attributes, persisted, and toggled without touching code.

 ```
graph TD
    EVENT["Event objectany class; StoppableEventInterface halts the chain"]
    DISPATCHER["EventDispatcherPSR-14: orders, resolves, invokes"]
    PROVIDER["ListenerProviderordered listeners for an event"]
    REPO["ListenerRepositoryInterfaceattribute discovery + persistence"]
    SYNC["Synchronous invokecontainer-resolved handler"]
    ASYNC["AsyncDispatcherInterfacequeue / SyncOnlyDispatcher fallback"]

    EVENT --> DISPATCHER
    DISPATCHER --> PROVIDER
    PROVIDER --> REPO
    DISPATCHER --> SYNC
    DISPATCHER --> ASYNC
```

      Loading Testing
-------

[](#testing)

```
composer install
composer test        # PHPUnit
composer analyse     # PHPStan, level max + strict rules
composer cs-check    # PHP-CS-Fixer
composer check       # All three
```

License
-------

[](#license)

MIT.

**This repository is a read-only mirror**, generated by CI from [phpdot/monorepo](https://github.com/phpdot/monorepo). [Pull requests](https://github.com/phpdot/monorepo/pulls)and [issues](https://github.com/phpdot/monorepo/issues) belong in the monorepo.

###  Health Score

38

—

LowBetter than 83% of packages

Maintenance94

Actively maintained with recent releases

Popularity0

Limited adoption so far

Community8

Small or concentrated contributor base

Maturity43

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 80% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~52 days

Total

3

Last Release

32d ago

PHP version history (3 changes)v1.0.0PHP &gt;=8.3

v1.0.1PHP &gt;=8.4

v0.1.0PHP &gt;=8.5

### Community

Maintainers

![](https://www.gravatar.com/avatar/62e82421bda4b5d6ba9a47ba6d88caca060dcd0d1a2862f351f3a97657385db0?d=identicon)[phpdot](/maintainers/phpdot)

---

Top Contributors

[![phpdot](https://avatars.githubusercontent.com/u/252500?v=4)](https://github.com/phpdot "phpdot (4 commits)")[![o3AM](https://avatars.githubusercontent.com/u/252500?v=4)](https://github.com/o3AM "o3AM (1 commits)")

---

Tags

eventasyncpsr-14listenerdispatcherattribute

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP CS Fixer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/phpdot-event/health.svg)

```
[![Health](https://phpackages.com/badges/phpdot-event/health.svg)](https://phpackages.com/packages/phpdot-event)
```

###  Alternatives

[symfony/symfony

The Symfony PHP framework

31.4k87.4M2.2k](/packages/symfony-symfony)[drupal/core-recommended

Locked core dependencies; require this project INSTEAD OF drupal/core.

6943.5M449](/packages/drupal-core-recommended)[typo3/cms

TYPO3 CMS is a free open source Content Management Framework initially created by Kasper Skaarhoj and licensed under GNU/GPL.

1.2k1.9M122](/packages/typo3-cms)[symfony/mailer

Helps sending emails

1.6k424.2M1.7k](/packages/symfony-mailer)[tempest/framework

The PHP framework that gets out of your way.

2.3k37.6k21](/packages/tempest-framework)[ecotone/ecotone

Enterprise architecture layer for Laravel and Symfony — CQRS, Event Sourcing, Durable Workflows (Sagas, Orchestrators), Projections, and Outbox messaging via PHP attributes.

568591.1k63](/packages/ecotone-ecotone)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
