Skip to content

feat: the manifest names the event holder, so a host reads the events without constructing the manager - #43

Merged
rodrigoteamx merged 1 commit into
mainfrom
feat/declare-events-in-the-manifest
Sep 8, 2026
Merged

rodrigoteamx merged 1 commit into
mainfrom
feat/declare-events-in-the-manifest

Conversation

@rodrigoteamx

Copy link
Copy Markdown
Contributor

Greenhouse decisions/0228, second slicea package declares its events in its manifest.

What the first slice measured

With every emitter declaring at CONSTRUCTION, events:catalogue on fresh cattle listed 7 of the
family's 24
framework events (greenhouse evidence/0567). That is not a bug in the catalogue: a
CLI process never builds a ToolRegistry, a JsonRpcService, a ProcessRunner, and never renders a
live component. The catalogue answered for the process, not for the app.

What this changes here

  • milpa/core floor raised to >=0.12 <1.0 (the release that carries Milpa\Interfaces\Event\DeclaresEvents).
    Only milpa/core moved: v0.11.0 => v0.12.0.
  • Milpa\Plugin\Event\PluginEvents — the package's existing declarations holder — now implements DeclaresEvents.
    Its declarations() was already static and already there; this only makes the contract visible.
  • composer.json gains extra.milpa.events naming that holder, mirroring how a capability already names
    its operation provider in its manifest (greenhouse evidence/0565, read by Capabilities::declaredBy()
    from vendor/composer/installed.json). A host can now declare capability.resolved, plugin.booting,
    plugin.booted and kernel.booted on behalf of a PluginsManager this process never constructs.

No event name, payload key, or declaration content changed.

The falsifier

tests/Event/TheManifestNamesTheEventHolderSoAHostNeedNotConstructTheEmitterTest.php measures the
manifest ON DISK, not the prose about it: it reads the package's own composer.json from the package
root, asserts extra.milpa.events lists exactly this package's holder, that each named class exists and
is_a(..., DeclaresEvents::class, true), and that calling ::declarations() on the class named in the
manifest
reaches the same set of names the holder declares.

Proven it can fail: dropping the trailing s from the FQCN in composer.json turned it red —
2 failures + 1 error (The manifest names holders other than this package's / «…\PluginEvent», which no autoloader can resolve). Restoring the letter turned it green (3 tests, 23 assertions).

Gates

composer validate --strict valid · phpunit 414 tests / 1218 assertions OK · phpstan [OK] No errors ·
docblocks OK (152 public methods) · php-cs-fixer 0 of 95 fixable · attribution OK ·
coverage 94.18% against a floor of 94.

… without constructing the manager

Measured on cattle (greenhouse evidence/0567): with every emitter declaring at construction,
events:catalogue in a CLI process listed 7 of the family's 24 framework events. An emitter
declares when it is BUILT, and a CLI run never builds most of them — the catalogue answered
for the process, not for the app.

PluginEvents now implements Milpa\Interfaces\Event\DeclaresEvents (milpa/core 0.12) and
composer.json names it under extra.milpa.events, the same way a capability already names its
operation provider (greenhouse evidence/0565). A host reading vendor/composer/installed.json
can resolve the holder and declare these four lifecycle events on behalf of a PluginsManager
the running process will never construct. No event name, key or declaration content changed.

The falsifier measures the manifest on disk, not the prose about it: it reads the package's own
composer.json, asserts the listed holders exist and implement the contract, and compares the
declarations reached THROUGH the manifest against the holder's own. Dropping a letter from the
FQCN turns it red (two failures and an error); restoring it turns it green.
@rodrigoteamx
rodrigoteamx merged commit 3a3323f into main Sep 8, 2026
2 checks passed
@rodrigoteamx
rodrigoteamx deleted the feat/declare-events-in-the-manifest branch September 8, 2026 14:59
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant