Search by

extendssoftware / exa-php-2

vincentvandijk

The successor to the PHP library ExaPHP.

Package info

github.com/extendssoftware/exa-php-2

pkg:composer/extendssoftware/exa-php-2

Statistics

Installs: 1

Dependents: 0

Suggesters: 0

Stars: 0

Open Issues: 0

dev-main 2026-10-20 12:58 UTC

This package is auto-updated.

Last update: 2026-10-20 12:58:48 UTC


README

The successor to the PHP library ExaPHP. The project is in initial development.

Requirements

  • PHP ^8.5 with the uri extension
  • Composer

Persistent messaging and outbox workers require ext-pcntl for graceful signal handling; --once does not.

Development setup

Development dependencies require ext-pcntl for signal-handling tests. The development container includes it. Install dependencies from the repository root:

composer install

Source code belongs in src/ under the ExtendsSoftware\ExaPHP namespace. Tests belong in tests/ under the ExtendsSoftware\ExaPHP\Tests namespace.

Components

  • Application: modules, lifecycle hooks, configuration, and service locator creation. See the guides for modules and configuration.
  • Authentication: credential verification contracts, authenticated actors, and failure types.
  • Authorization: actor-based access requests, application authorization rules, denial guards, and optional HTTP 403 mapping.
  • CLI: command definitions, parsing and dispatch, help, immutable input, stream output, and named exit codes.
  • Clock: a clock contract with UTC system time and immutable frozen time implementations.
  • CQRS: command and typed query contracts, synchronous buses, middleware, and dispatch metadata.
  • Domain: aggregate event recording, domain events, and composable specifications.
  • Event: event messages, generic listeners, and synchronous event dispatch.
  • HTTP: immutable messages, middleware, named routing and URL generation, JSON request decoding, response negotiation, Problem Details, route groups and middleware, and PHP server adapters.
  • Identity: immutable actors identifying the principal performing an operation.
  • Integration: application wiring for CQRS, events, logging, HTTP pipelines, and CLI command execution, plus JSON-RPC server and method registration services.
  • JSON-RPC: a transport-independent JSON-RPC 2.0 server with typed messages, method handlers, notifications, batches, standard and application error responses, and opt-in application wiring.
  • Logging: stream logging, log records, NDJSON formatting, severity levels, and exceptions.
  • Messaging: immutable JSON messages, durable publishing, subscription lookup, subscriber processing and retries, consumer delivery contracts, a CLI consumer worker, and an Outbox bridge.
  • Outbox: transactional JSON messages, processing ownership, delivery coordination, bounded retries, and a persistent CLI worker.
  • Processing: validators, string transformers, immutable results, sequential pipelines, and nested object/array processing.
  • Service locator: shared object services and constructor injection, with extensible resolvers.
  • Transaction: transactional execution contracts, lifecycle exceptions, and CQRS command middleware.

Basic usage

Bootstrap an application using an existing configuration directory. An empty directory is sufficient to get started:

mkdir -p config
<?php

declare(strict_types=1);

use ExtendsSoftware\ExaPHP\Application\Application;
use ExtendsSoftware\ExaPHP\Application\Configuration\Configuration;

require 'vendor/autoload.php';

$application = new Application(__DIR__ . '/config');
$services = $application->bootstrap();

try {
    assert($application->config() === $services->get(Configuration::class));
} finally {
    $application->shutdown();
}

Place this script in the project root. Register module classes before calling bootstrap() as shown in the application guide. The service locator can also be used independently.

Testing

Run the test suite with PHPUnit:

vendor/bin/phpunit

PHPUnit loads phpunit.xml.dist automatically.

Run PHPStan against src/ using phpstan.neon.dist:

vendor/bin/phpstan analyse

GitHub Actions runs just install, just test, just analyse --no-progress, and just check-style on pushes and pull requests using the same recipes and PHP container as local development. Tests, static analysis, and code style checks run in one job.

Container workflow

With Docker Compose and just installed, run Composer, PHPUnit, PHPStan, and PHP-CS-Fixer in the PHP 8.5 CLI container:

just install
just test
just analyse
just check-style

just test forwards all arguments to PHPUnit, including quoted filters; just analyse forwards arguments to PHPStan. just check-style previews required formatting changes and exits unsuccessfully when any are found. Use just fix to apply formatting with .php-cs-fixer.dist.php; additional arguments are forwarded to PHP-CS-Fixer. Run just to list recipes or just build to build the image explicitly. Install, test, analysis, and formatting recipes build the image as needed and remove their containers afterward. The repository, including vendor/, is mounted into the container. Recipes use your host user and group IDs so generated files retain your ownership. The bind mount uses the shared SELinux label (:z) so containers can access the checkout on SELinux hosts, including when multiple development commands run concurrently. The native PHP workflow remains available.

Without just, use docker compose run --build --rm php composer install and docker compose run --build --rm php vendor/bin/phpunit. Compose defaults to UID/GID 1000; set LOCAL_UID and LOCAL_GID to your user and group IDs if needed. On Windows, use these commands through WSL for the same ownership behavior.

Changelog

See CHANGELOG.md for notable changes.

License

ExaPHP is licensed under the MIT license.