Skip to content
CAI
Software that uses CAICheck a score

gpslab/cqrs

58.2

Adequate · 21 September 2026

1.3k

lines of production code

PHP

primary language

4

measurements over time

CAI band scale
CAI trend line
CAI lens gauges

What this system is

This system is a PHP-based CQRS (Command Query Responsibility Segregation) infrastructure library designed to structure applications around distinct command and query operations. It provides a command bus for routing and executing commands, supported by pluggable handler locators and a queue system for both pull and subscribe-based message processing. The library also includes a query bus for read operations, with dedicated serialization services and comprehensive test coverage for all components.

Features

Introduce CommandQueue interface for command processing

A new CommandQueue interface is introduced in the src/Command/Queue directory, defining a contract for publishing commands to a queue. This establishes a common interface for command queue implementations, supporting the refactoring of PubSub and PullPush operations into a unified structure.

src/Command/Queue · high confidence

Introduce SubscribeCommandQueue interface and Redis-backed implementation

A new \SubscribeCommandQueue\ interface and its \PredisSubscribeCommandQueue\ implementation are added to the \src/Command/Queue/Subscribe\ directory. This introduces the ability to subscribe to and unsubscribe from command queues, with the Redis-backed version handling serialization, lazy subscription, and deserialization validation. A basic in-memory \ExecutingSubscribeCommandQueue\ is also provided.

src/Command/Queue/Subscribe · high confidence

Introduce a dedicated queue serialization interface and implementation

A new \Serializer\ interface and a \SymfonySerializer\ implementation have been added to the queue component. The interface defines \serialize\ and \deserialize\ methods, while the implementation wraps the Symfony Serializer to handle command serialization using the 'predis' format by default. This change provides a dedicated, typed contract for serializing queue commands, replacing any previous ad-hoc or implicit serialization logic.

src/Command/Queue/Serializer · high confidence

Introduce command bus for handling commands via a locator

A new command bus implementation has been added to the application, providing a way to route and execute commands. The \CommandBus\ interface and the \HandlerLocatedCommandBus\ class work together to locate and invoke the appropriate handler for each command, ensuring that only callable handlers are executed and throwing a \HandlerNotFoundException\ if no suitable handler is found.

src/Command/Bus · high confidence

Introduce command handler locator interfaces and implementations

The command handling system now uses a pluggable locator strategy. A new \CommandSubscriber\ interface allows services to declare which commands they handle. Two locator implementations are provided: \DirectBindingCommandHandlerLocator\ for direct callable registration, and \ContainerCommandHandlerLocator\ (plus a Symfony-specific variant) for lazy-loading handlers from a service container. This enables more flexible and efficient command dispatching.

src/Command/Handler · high confidence

Introduce pull-based command queue implementations

Added new pull-based command queue implementations for both in-memory and Redis (Predis) backends, including unique and standard variants. These classes implement the new PullCommandQueue interface, which extends the existing CommandQueue interface with a pull() method for retrieving commands from the queue. The Redis implementations integrate with a separate serializer service to handle command serialization and deserialization, while the memory-based queues provide simple array-backed storage.

src/Command/Queue/Pull · high confidence

Introduce query handler locator implementations

Added new query handler locator classes—ContainerQueryHandlerLocator, DirectBindingQueryHandlerLocator, and SymfonyContainerQueryHandlerLocator—along with the QuerySubscriber interface and QueryHandlerLocator interface. These changes enable the system to locate and invoke query handlers via service containers or direct bindings, supporting both Symfony-specific and generic container-based resolution strategies.

src/Query/Handler · high confidence

Introduced empty Command and Query interfaces

Added new empty interfaces for the Command and Query components within the GpsLab library. These serve as base markers for command and query objects, enabling strict typing and type-hinting for these distinct operation types.

src/Command, src/Query · high confidence

Behavioural changes

Add PHPStan configuration for Predis 1.0 compatibility

A new PHPStan configuration file (.travis/predis\_10\_phpstan.neon) has been added to the project. This file extends the base PHPStan configuration and explicitly ignores the error related to 'Predis\\Client\<Predis\\Client\>', addressing the issue where the Predis client in version 1.0 is not iterable.

.travis · medium confidence

Add exception classes for missing command and query handlers

Introduced new exception classes, GpsLab\\Component\\Command\\Exception\\HandlerNotFoundException and GpsLab\\Component\\Query\\Exception\\HandlerNotFoundException, to signal when a handler is not found for a given command or query. Each class provides a static notFound() method that accepts the relevant command or query object and returns a descriptive exception message.

src/Command/Exception, src/Query/Exception · medium confidence

Introduce strict-typed QueryBus interface and HandlerLocatedQueryBus implementation

The Query Bus component now exposes a formalized interface (QueryBus) and a concrete implementation (HandlerLocatedQueryBus) that locates and invokes query handlers. The bus enforces strict typing and validates that the resolved handler is callable before invocation, ensuring predictable behavior for query dispatching.

src/Query/Bus · medium confidence

Reworked command queue interfaces and added configurable serialization

The command queue API has been refactored: the \Push\ and \Pull\ queues now use a common \CommandQueue\ interface with a \publish\ method instead of \push\. The \PubSub\ and \PullPush\ namespaces have been renamed to \Subscribe\ and \Pull\ respectively, with all related classes and tests updated. Additionally, command serialization is now handled by a separate \Serializer\ service, allowing users to provide custom serialization implementations for queue payloads.

(repo-wide) · high confidence

Test coverage

Add test bootstrap file for the test suite; Added test fixtures for contact commands; Added test fixtures for query handlers; Added tests for command queue pull implementations; Added tests for the HandlerLocatedQueryBus; Added tests for the new Subscribe command queue implementation; Added unit tests for HandlerLocatedCommandBus; Added unit tests for query handler locators; Added unit tests for the new SymfonySerializer service.

Dependencies

Initial release of the CQRS infrastructure library

The project is introduced as a new library named 'gpslab/cqrs' for creating CQRS applications. The package defines its PHP version requirement as \>=7.1.0 and specifies development dependencies including PSR-11 and PSR-3 implementations, Symfony components, PHPUnit, PHPStan, and Predis for Redis-based pub/sub functionality.

(dependencies) · medium confidence

Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.

How this codebase got here

Score

  • CAI 61 → 58 (-2.4)
  • Rubric changed (rubric-2026.08.19 → rubric-2026.09.15) — scores are not directly comparable.

Lenses

  • Code Health 100 → 98 (-1.3)
  • Architecture 69 → 69 (+0.0)
  • Maturity 46 → 46 (+0.0)
  • Readiness 64 → 55 (-9.0)
  • Security 100 → 100 (+0.0)

Resolved (8)

  • Change coupling: ContainerCommandHandlerLocator.php ↔ SymfonyContainerCommandHandlerLocator.php (src/Command/Handler/Locator/ContainerCommandHandlerLocator.php)
  • Coverage not included — suite not readable by the collector
  • Dependency hygiene not measured — dependency manifest found but not parsed for hygiene
  • Duplicated block (15 lines × 2) (src/Command/Queue/Pull/PredisPullCommandQueue.php)
  • LLM evaluation failed
  • No exposed public API
  • Test reliability not included
  • dormant codebase — no living knowledge left to concentrate

New (11)

  • Duplicate Logic in Locator Implementations: ContainerCommandHandlerLocator and SymfonyContainerCommandHandlerLocator (and their Query counterparts) expose identical registerService and registerSubscriberService methods. Given that SymfonyContainerCommandHandlerLocator likely extends or wraps ContainerCommandHandlerLocator (or shares the same logic), exposing these registration methods on both types creates confusion about which locator to use for manual registration.
  • Duplicated block (11 lines × 4) (src/Command/Handler/Locator/ContainerCommandHandlerLocator.php)
  • Duplicated block (24 lines × 2) (src/Command/Queue/Pull/PredisPullCommandQueue.php)
  • Duplicated block (6 lines × 2) (src/Command/Handler/Locator/ContainerCommandHandlerLocator.php)
  • Duplicated block (6 lines × 2) (src/Command/Handler/Locator/DirectBindingCommandHandlerLocator.php)
  • Duplicated block (6 lines × 2) (src/Query/Handler/Locator/ContainerQueryHandlerLocator.php)
  • Duplicated block (7 lines × 2) (src/Command/Handler/Locator/ContainerCommandHandlerLocator.php)
  • Duplicated block (7 lines × 2) (src/Command/Handler/Locator/SymfonyContainerCommandHandlerLocator.php)
  • Duplicated block (9 lines × 2) (src/Command/Queue/Subscribe/ExecutingSubscribeCommandQueue.php)
  • No dependency advisory monitoring
  • Redundant Base Types: CommandBus and QueryBus are defined as distinct types with identical handle signatures, but they are never used as base classes or interfaces for the concrete implementations (HandlerLocatedCommandBus and HandlerLocatedQueryBus). The concrete classes duplicate the interface of the base types without extending them, creating unnecessary type hierarchy noise.

Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.

Survey your own repository

gpslab/cqrs was measured the same way every project in this corpus was: the same rubric, at a pinned commit, with the result published in full. Point a surveyor at a repository you know and see whether you agree with it.

About this page

  • The score is its most recent published measurement, taken on 21 September 2026 at a pinned commit. It is not a live figure and does not change until the project is measured again.
  • Measured at commit d088be22f1e30f1b3d693c8a87fa2dd28829a56c — the exact code this score is about.
  • Scored under rubric-2026.09.15 — the same rubric and the same method as every other entry in this index.
  • Measured by watchdog.canine.dev using codehealth-analyzer preprod-fa71c66cabd8.