-
-
Notifications
You must be signed in to change notification settings - Fork 1
feat: implement run_projection free function (ADR-029) #263
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
ADR-029 (accepted): Projection Runner API Simplification - Replace ProjectionRunner struct with run_projection free function - Require backend to implement EventReader + CheckpointStore + ProjectorCoordinator - Matches execute(command, &store) ergonomics ARCHITECTURE.md v2.7: - Add Projection Runner API section documenting run_projection - Update architectural principles to mention run_projection - Add unified backend traits to summary Relates to #258
Add run_projection(projector, &backend) as the primary projection API with automatic leadership coordination. Backend must implement EventReader + CheckpointStore + ProjectorCoordinator. Changes: - Add run_projection() free function to eventcore/src/projection.rs - Add ProjectionError::LeadershipError for coordination failures - InMemoryEventStore now implements CheckpointStore and ProjectorCoordinator - PostgresEventStore now implements CheckpointStore and ProjectorCoordinator - Add blanket impl for &T: CheckpointStore in eventcore-types - Document ProjectionRunner as low-level API (prefer run_projection) Tests: - run_projection_acquires_leadership_and_processes_events - run_projection_returns_leadership_error_when_lock_already_held - run_projection_holds_leadership_during_event_processing - postgres_event_store_saves_and_loads_checkpoint - postgres_event_store_implements_projector_coordinator - in_memory_event_store_implements_checkpoint_store - in_memory_event_store_implements_projector_coordinator Closes #258
|
This change is part of the following stack: Change managed by git-spice. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
One critical issue: CoordinationGuard::drop() uses catch_unwind incorrectly, which will not catch the block_in_place panic on single-threaded runtimes.
Address review feedback: catch_unwind does not catch panics from block_in_place setup on single-threaded runtimes. Instead, check runtime_flavor() to determine the appropriate unlock strategy. - Multi-threaded runtime: use block_in_place for synchronous unlock - Single-threaded runtime: spawn task for async unlock
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Critical issue with single-threaded runtime unlock in CoordinationGuard::drop(). Previous catch_unwind issue fixed correctly, but spawned task may not execute before shutdown.
Address review feedback: Document that on single-threaded runtimes, the spawned unlock task may not execute before process shutdown. The advisory lock is released when the PostgreSQL session ends. Added comprehensive documentation to CoordinationGuard explaining: - Multi-threaded vs single-threaded runtime behavior - PostgreSQL session-scoped lock safety net - Connection pool timeout recommendations
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Previous coordination guard drop() issue resolved. Runtime flavor check correctly avoids block_in_place panic, and documentation clearly explains lock release behavior.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Previous issues addressed. Comprehensive documentation explains single-threaded runtime behavior and PostgreSQL session-scoped lock safety net.
## 🤖 New release
* `eventcore-macros`: 0.4.0 -> 0.5.0
* `eventcore-types`: 0.4.0 -> 0.5.0 (✓ API compatible changes)
* `eventcore-postgres`: 0.4.0 -> 0.5.0 (✓ API compatible changes)
* `eventcore`: 0.4.0 -> 0.5.0 (⚠ API breaking changes)
* `eventcore-memory`: 0.4.0 -> 0.5.0 (✓ API compatible changes)
* `eventcore-testing`: 0.4.0 -> 0.5.0 (✓ API compatible changes)
### ⚠ `eventcore` breaking changes
```text
--- failure enum_variant_added: enum variant added on exhaustive enum ---
Description:
A publicly-visible enum without #[non_exhaustive] has a new variant.
ref: https://doc.rust-lang.org/cargo/reference/semver.html#enum-variant-new
impl: https://github.com/obi1kenobi/cargo-semver-checks/tree/v0.45.0/src/lints/enum_variant_added.ron
Failed in:
variant ProjectionError:LeadershipError in /tmp/.tmpKfk26o/eventcore/eventcore/src/projection.rs:532
```
<details><summary><i><b>Changelog</b></i></summary><p>
## `eventcore-macros`
<blockquote>
##
[0.3.0](eventcore-macros-v0.2.0...eventcore-macros-v0.3.0)
- 2025-12-27
### Refactoring
- *(release)* switch to workspace version inheritance for full lockstep
versioning ([#221](#221))
</blockquote>
## `eventcore-types`
<blockquote>
##
[0.5.0](eventcore-types-v0.4.0...eventcore-types-v0.5.0)
- 2025-12-31
### Features
- add ProjectorCoordinator trait and PostgreSQL advisory lock
implementation ([#259](#259))
- implement run_projection free function (ADR-029)
([#263](#263))
</blockquote>
## `eventcore-postgres`
<blockquote>
##
[0.5.0](eventcore-postgres-v0.4.0...eventcore-postgres-v0.5.0)
- 2025-12-31
### Features
- add ProjectorCoordinator trait and PostgreSQL advisory lock
implementation ([#259](#259))
- implement run_projection free function (ADR-029)
([#263](#263))
</blockquote>
## `eventcore`
<blockquote>
##
[0.5.0](eventcore-v0.4.0...eventcore-v0.5.0)
- 2025-12-31
### Documentation
- align issues and ADRs with ARCHITECTURE.md guidance
([#256](#256))
### Features
- implement run_projection free function (ADR-029)
([#263](#263))
</blockquote>
## `eventcore-memory`
<blockquote>
##
[0.5.0](eventcore-memory-v0.4.0...eventcore-memory-v0.5.0)
- 2025-12-31
### Features
- add ProjectorCoordinator trait and PostgreSQL advisory lock
implementation ([#259](#259))
- implement run_projection free function (ADR-029)
([#263](#263))
</blockquote>
## `eventcore-testing`
<blockquote>
##
[0.5.0](eventcore-testing-v0.4.0...eventcore-testing-v0.5.0)
- 2025-12-31
### Features
- add ProjectorCoordinator trait and PostgreSQL advisory lock
implementation ([#259](#259))
</blockquote>
</p></details>
---
This PR was generated with
[release-plz](https://github.com/release-plz/release-plz/).
Closes #258
Summary
Implements the
run_projection(projector, &backend)free function per ADR-029 and ARCHITECTURE.md v2.7, providing a simplified API for running projections with automatic leadership coordination.Changes
run_projectionfunction - Free function that acquires leadership viaProjectorCoordinator::try_acquire()before processing eventsProjectionError::LeadershipError- New error variant for coordination failures (non-blocking per ADR-028)InMemoryEventStore- Now implementsCheckpointStoreandProjectorCoordinatordirectlyPostgresEventStore- Now implementsCheckpointStoreandProjectorCoordinatordirectly&T: CheckpointStore- Enables ergonomic reference usageProjectionRunnerdocs updated - Documented as low-level API, recommendingrun_projectionfor most casesAPI Change
Before:
After:
Testing
Acceptance Criteria
run_projection(projector, &backend)free function createdEventReader + CheckpointStore + ProjectorCoordinatorrun_projectionacquires leadership before processing eventsProjectionErrorif leadership unavailable (non-blocking per ADR-028)InMemoryEventStoreimplements all three traitsPostgresEventStoreimplements all three traitsProjectionRunnerdocumented as low-level APIReferences