Design Patterns
This page references the 23 Gang of Four (GoF) design patterns, documenting their theoretical foundations and their application within Phexium's Clean Architecture and CQRS context.
Of the 23 patterns, 16 are implemented in Phexium and 7 are not represented as they are not required by the framework's architectural approach.
Creational Patterns
Creational patterns abstract the instantiation process, making the system independent of how objects are created, composed, and represented.
Abstract Factory
Theory: Provides an interface for creating families of related objects without specifying their concrete classes.
Application Clean Architecture: Each Plugin defines a Port (interface) with multiple interchangeable Adapters depending on the environment. This allows switching implementations (test, development, production) without modifying client code.
Implementation in Phexium:
| Component | File |
|---|---|
| Port | src/Plugin/Cache/Port/CacheInterface.php |
| Adapters | src/Plugin/Cache/Adapter/InMemoryCache.php, RedisCache.php, FileCache.php |
| Port | src/Plugin/Clock/Port/ClockInterface.php |
| Adapters | src/Plugin/Clock/Adapter/SystemClock.php, FrozenClock.php |
| Port | src/Plugin/SqlDriver/Port/SqlDriverInterface.php |
| Adapters | src/Plugin/SqlDriver/Adapter/SqliteDriver.php, MysqlDriver.php, PostgresqlDriver.php |
Learn more on refactoring.guru
Builder
Theory: Separates the construction of a complex object from its representation, allowing the same construction process to create different representations.
Application Clean Architecture: Fluent construction of HTTP responses with optional steps enables readable and flexible response building in controllers.
Implementation in Phexium:
| Component | File |
|---|---|
| Builder | src/Presentation/ResponseBuilder.php |
| Methods | withHeader(), withStatus(), withHtml(), build() |
Learn more on refactoring.guru
Factory Method
Theory: Defines an interface for creating objects, but lets subclasses decide which class to instantiate.
Application Clean Architecture: Value Objects use factory methods (fromString()) to encapsulate validation and guarantee valid instances. ID generators use generate() to produce identifiers.
Implementation in Phexium:
| Component | File |
|---|---|
| ID Factory | src/Domain/Id/Uuid.php (from()) |
| ID Generators | src/Plugin/IdGenerator/Adapter/*Generator.php (generate()) |
| Value Objects | app/demo/Library/Domain/Title.php, ISBN.php |
| Value Objects | app/demo/User/Domain/Email.php |
Learn more on refactoring.guru
Prototype
Theory: Creates new objects by copying an existing instance (prototype) rather than instantiating a class.
Not implemented
Immutable Value Objects and Entities with identity do not require cloning. Object creation goes through factory methods or constructors, which provide validation guarantees that cloning would bypass.
Learn more on refactoring.guru
Singleton
Theory: Ensures a class has only one instance and provides a global access point to it.
Not implemented
Dependency injection (PHP-DI) manages instance lifecycle. The Singleton pattern is considered an anti-pattern in modern PHP development because it creates global state and complicates testing. The container handles singleton-like behavior when needed.
Learn more on refactoring.guru
Structural Patterns
Structural patterns deal with class and object composition, using inheritance and composition to create larger structures.
Adapter
Theory: Converts the interface of a class into another interface that clients expect.
Application Clean Architecture: Foundation of hexagonal architecture. The Domain layer defines Ports (interfaces), and the Infrastructure layer provides Adapters (implementations). This inverts dependencies and allows the domain to remain independent of infrastructure concerns.
Implementation in Phexium:
| Component | File |
|---|---|
| All Ports | src/Plugin/*/Port/*Interface.php |
| All Adapters | src/Plugin/*/Adapter/*.php |
| Domain Port | app/demo/Library/Domain/BookRepositoryInterface.php |
| Adapters | app/demo/Library/Infrastructure/SqliteBookRepository.php, InMemoryBookRepository.php |
Learn more on refactoring.guru
Bridge
Theory: Decouples an abstraction from its implementation so that the two can vary independently.
Application Clean Architecture: Separates generic SQL operations from DBMS-specific details. The abstract driver defines common behavior while concrete drivers implement database-specific syntax.
Implementation in Phexium:
| Component | File |
|---|---|
| Abstraction | src/Plugin/SqlDriver/Internal/AbstractSqlDriver.php |
| Implementations | src/Plugin/SqlDriver/Adapter/SqliteDriver.php |
| Implementations | src/Plugin/SqlDriver/Adapter/MysqlDriver.php |
| Implementations | src/Plugin/SqlDriver/Adapter/PostgresqlDriver.php |
Learn more on refactoring.guru
Composite
Theory: Composes objects into tree structures to represent part-whole hierarchies. Clients can treat individual objects and compositions uniformly.
Application Clean Architecture: Specifications can be combined (AND, OR, NOT) to build complex queries while maintaining a uniform interface. Each specification, whether simple or composite, implements the same interface.
Implementation in Phexium:
| Component | File |
|---|---|
| Interface | src/Domain/Specification/SpecificationInterface.php |
| Composite Base | src/Domain/Specification/BinaryAbstract.php (composes left + right) |
| Leaf Composites | src/Domain/Specification/BinaryAndSpecification.php, BinaryOrSpecification.php |
Learn more on refactoring.guru
Decorator
Theory: Attaches additional responsibilities to an object dynamically, providing a flexible alternative to subclassing.
Application Clean Architecture: Adds cross-cutting behaviors (transactions, monotonicity) without modifying base implementations. Decorators wrap existing services and enhance them transparently.
Implementation in Phexium:
| Component | File |
|---|---|
| Transaction Decorator | src/Plugin/CommandBus/Adapter/TransactionalCommandBus.php (wraps CommandBusInterface) |
| Clock Decorator | src/Plugin/Clock/Adapter/MonotonicClock.php (wraps ClockInterface) |
| Clock Decorator | src/Plugin/Clock/Adapter/OffsetClock.php |
Learn more on refactoring.guru
Facade
Theory: Provides a unified interface to a set of interfaces in a subsystem, making the subsystem easier to use.
Application Clean Architecture: The Bus components expose a simple dispatch() method that hides handler resolution, routing, and middleware execution. Clients interact with a simple interface while complex orchestration happens behind the scenes.
Implementation in Phexium:
| Component | File |
|---|---|
| Command Bus Facade | src/Plugin/CommandBus/Adapter/SyncCommandBus.php |
| Query Bus Facade | src/Plugin/QueryBus/Adapter/SyncQueryBus.php |
| Event Bus Facade | src/Plugin/EventBus/Adapter/SyncEventBus.php |
Learn more on refactoring.guru
Flyweight
Theory: Reduces memory consumption by sharing common data between multiple objects.
Not implemented
Phexium HTTP requests are stateless and short-lived. Memory optimization through state sharing is not necessary in this context where each request creates fresh object graphs that are garbage collected after the response.
Learn more on refactoring.guru
Proxy
Theory: Provides a surrogate or placeholder for another object to control access to it.
Application Clean Architecture: Interchangeable implementations that are transparent to clients. Null implementations for testing, real implementations for production. The proxy and real subject share the same interface.
Implementation in Phexium:
| Component | File |
|---|---|
| Null Logger | src/Plugin/Logger/Adapter/NullLogger.php |
| File Logger | src/Plugin/Logger/Adapter/FileLogger.php |
| Null Cache | src/Plugin/Cache/Adapter/NullCache.php |
Learn more on refactoring.guru
Behavioral Patterns
Behavioral patterns deal with algorithms and the assignment of responsibilities between objects.
Chain of Responsibility
Theory: Passes a request along a chain of handlers. Each handler decides either to process the request or to pass it to the next handler in the chain.
Application Clean Architecture: PSR-15 middlewares process HTTP requests in a chain (authentication, RBAC, session). Each middleware can process, modify, or reject the request before passing it along.
Implementation in Phexium:
| Component | File |
|---|---|
| Session Middleware | src/Presentation/Middleware/SessionMiddleware.php |
| RBAC Middleware | app/demo/Shared/Application/Middleware/RbacPermissionMiddleware.php |
Learn more on refactoring.guru
Command
Theory: Encapsulates a request as an object, allowing parameterization of clients with different requests, queuing of requests, and logging of operations.
Application Clean Architecture: Core of CQRS. Commands encapsulate write operations, decoupling intent from execution. This enables middleware processing, transaction management, and event dispatching around command handling.
Implementation in Phexium:
| Component | File |
|---|---|
| Command Interface | src/Application/Command/CommandInterface.php |
| Handler Interface | src/Application/Command/CommandHandlerInterface.php |
| Bus Interface | src/Plugin/CommandBus/Port/CommandBusInterface.php |
| Example Command | app/demo/Library/Application/Command/CreateBookCommand.php |
Learn more on refactoring.guru
Interpreter
Theory: Defines a grammar for a language and provides an interpreter to evaluate sentences in that language, typically using an abstract syntax tree.
Not implemented
Phexium does not include a DSL or expression language requiring parsing and interpretation. The Specification pattern (used for query composition) serves a different purpose: it encapsulates business rules rather than parsing grammar. True Interpreter implementations would be needed for template engines, query languages, or expression evaluators.
Iterator
Theory: Provides a way to access elements of a collection sequentially without exposing its underlying representation.
Application Clean Architecture: Domain Collections implement IteratorAggregate for standard traversal. This allows foreach loops and other iteration constructs to work with domain collections.
Implementation in Phexium:
| Component | File |
|---|---|
| Collection Interface | src/Domain/Collection/CollectionInterface.php (extends IteratorAggregate) |
| Abstract Collection | src/Domain/Collection/AbstractCollection.php |
| Iterator Trait | src/Domain/Collection/Trait/TraitCollectionCore.php (getIterator()) |
Learn more on refactoring.guru
Mediator
Theory: Defines an object that encapsulates how a set of objects interact, preventing direct references between them.
Not implemented
Inter-module decoupling is achieved through Domain Events (Observer pattern). The Mediator would add complexity without additional benefit in the Phexium context where modules communicate through events rather than direct method calls.
Learn more on refactoring.guru
Memento
Theory: Captures and externalizes an object's internal state so that the object can be restored to this state later.
Not implemented
Phexium uses a classic CRUD approach without state history. Event Sourcing (not implemented) would make this pattern relevant. Current entities are mutable but do not track previous states.
Learn more on refactoring.guru
Observer
Theory: Defines a one-to-many dependency between objects so that when one object changes state, all its dependents are notified and updated automatically.
Application Clean Architecture: Domain Events notify listeners of state changes, decoupling modules. A handler can dispatch events without knowing which listeners will react, enabling loose coupling between bounded contexts.
Implementation in Phexium:
| Component | File |
|---|---|
| Event Bus Interface | src/Plugin/EventBus/Port/EventBusInterface.php |
| Dispatcher | src/Plugin/Dispatcher/Adapter/LeagueDispatcher.php |
| Example Event | app/demo/Library/Domain/Event/BookCreatedEvent.php |
| Example Listener | app/demo/Loan/Application/EventListener/LoanCreatedEventHandler.php |
Learn more on refactoring.guru
State
Theory: Allows an object to alter its behavior when its internal state changes. The object will appear to change its class.
Application Clean Architecture: Enums with methods encapsulate state transition rules for entities. The enum itself contains the logic for what operations are valid in each state.
Implementation in Phexium:
| Component | File |
|---|---|
| Book Status | app/demo/Library/Domain/BookStatus.php (canBeBorrowed(), isAvailable()) |
| Loan Status | app/demo/Loan/Domain/LoanStatus.php |
Learn more on refactoring.guru
Strategy
Theory: Defines a family of algorithms, encapsulates each one, and makes them interchangeable.
Application Clean Architecture: Plugins allow choosing the algorithm based on context (hashing, caching, persistence). The same interface supports different implementations that can be swapped via dependency injection.
Implementation in Phexium:
| Component | File |
|---|---|
| Password Hashers | src/Plugin/PasswordHasher/Adapter/ (Argon2id, Bcrypt, Plaintext) |
| Cache Strategies | src/Plugin/Cache/Adapter/ (InMemory, Redis, File) |
| Presenters | app/demo/Library/Presentation/ListBooksHtmlPresenter.php vs ListBooksJsonPresenter.php |
Learn more on refactoring.guru
Template Method
Theory: Defines the skeleton of an algorithm in a method, deferring some steps to subclasses.
Application Clean Architecture: Abstract classes define the algorithm structure while concrete classes implement specific details. This ensures consistent behavior while allowing customization.
Implementation in Phexium:
| Component | File |
|---|---|
| Abstract Template | src/Domain/Specification/BinaryAbstract.php (abstract getSqlTemplate(), evaluateBinary()) |
| Concrete Implementations | src/Domain/Specification/BinaryAndSpecification.php, BinaryOrSpecification.php |
Learn more on refactoring.guru
Visitor
Theory: Separates an algorithm from the object structure on which it operates, allowing new operations to be added without modifying the classes.
Not implemented
Phexium data structures (Entities, Collections) do not have complex hierarchies requiring this pattern. Operations are defined directly in the relevant classes rather than externalized into visitors.
Learn more on refactoring.guru
Summary
| Category | Implemented | Not Implemented |
|---|---|---|
| Creational | Abstract Factory, Builder, Factory Method | Prototype, Singleton |
| Structural | Adapter, Bridge, Composite, Decorator, Facade, Proxy | Flyweight |
| Behavioral | Chain of Responsibility, Command, Iterator, Observer, State, Strategy, Template Method | Interpreter, Mediator, Memento, Visitor |
| Total | 16 | 7 |