Skip to main content

nexus-persistence-doctrine

Doctrine ORM adapter for Nexus persistence -- entity-based stores that use EntityManager for all database operations. Shares the same table schema as nexus-persistence-dbal.

Composer: nexus-actors/persistence-doctrine

Namespace: Monadial\Nexus\Persistence\Doctrine\

View class diagram

Dependencies: doctrine/orm ^3.0

Store classes

ClassDescription
DoctrineEventStoreEventStore implementation using EntityManagerInterface. Constructor: EntityManagerInterface, MessageSerializer (default: PhpNativeSerializer). Throws ConcurrentModificationException on duplicate sequence numbers.
DoctrineSnapshotStoreSnapshotStore implementation using EntityManagerInterface. Constructor: EntityManagerInterface, MessageSerializer (default: PhpNativeSerializer).
DoctrineDurableStateStoreDurableStateStore implementation using EntityManagerInterface. Constructor: EntityManagerInterface, MessageSerializer (default: PhpNativeSerializer). Uses Doctrine's #[ORM\Version] for optimistic locking.
DoctrinePessimisticLockProviderPessimisticLockProvider convenience wrapper for Doctrine ORM. Constructor: EntityManagerInterface. Delegates to DbalPessimisticLockProvider via the EntityManager's connection.

ORM entities

Monadial\Nexus\Persistence\Doctrine\Entity\

ClassDescription
EventEntryORM entity mapped to nexus_event_journal. Properties: persistenceId, sequenceNr, eventType, eventData, metadata, timestamp.
SnapshotEntryORM entity mapped to nexus_snapshot_store. Properties: persistenceId, sequenceNr, stateType, stateData, timestamp.
DurableStateEntryORM entity mapped to nexus_durable_state. Properties: persistenceId, version (with #[ORM\Version]), stateType, stateData, timestamp.

Usage

use Doctrine\DBAL\DriverManager;
use Doctrine\ORM\EntityManager;
use Doctrine\ORM\ORMSetup;
use Monadial\Nexus\Persistence\Doctrine\DoctrineEventStore;
use Monadial\Nexus\Persistence\Doctrine\DoctrineSnapshotStore;
use Monadial\Nexus\Persistence\Doctrine\DoctrineDurableStateStore;

$config = ORMSetup::createAttributeMetadataConfiguration(
paths: [__DIR__ . '/vendor/nexus-actors/persistence-doctrine/src/Entity'],
isDevMode: true,
);

$connection = DriverManager::getConnection(['driver' => 'pdo_sqlite', 'path' => 'nexus.db']);
$em = new EntityManager($connection, $config);

$eventStore = new DoctrineEventStore($em);
$snapshotStore = new DoctrineSnapshotStore($em);
$durableStateStore = new DoctrineDurableStateStore($em);

// With a custom serializer
use Monadial\Nexus\Serialization\MessageSerializer;

$eventStore = new DoctrineEventStore($em, $customSerializer);
$durableStateStore = new DoctrineDurableStateStore($em, $customSerializer);

// Pessimistic locking
use Monadial\Nexus\Persistence\Doctrine\DoctrinePessimisticLockProvider;
use Monadial\Nexus\Persistence\Locking\LockingStrategy;

$lockProvider = new DoctrinePessimisticLockProvider($em);

$behavior = EventSourcedBehavior::create($persistenceId, $emptyState, $commandHandler, $eventHandler)
->withEventStore($eventStore)
->withLockingStrategy(LockingStrategy::pessimistic($lockProvider))
->toBehavior();