Part of #5118 (compliance wave growth), epic #5110.
JasperFx.Events.IEventStore declares the event store explorer surface as default-interface methods that throw unless a store implements them:
GetRecentStreamsAsync(int count, CancellationToken) → IReadOnlyList<StreamSummary>
GetRecentStreamsAsync(int count, string? tenantId, CancellationToken)
GetStreamMetadataAsync(string streamId, CancellationToken) → StreamMetadata?
TryCreateUsage(CancellationToken) → EventStoreUsage?
Both products implement them, both test them independently, and the fixture already exposes EventStore. Portable with no seam addition.
This surface matters more than a normal test suite: it is what CritterWatch consumes, so a cross-store contract test is the cheapest guard against a tooling regression on one store only.
What each store tests today
| Marten |
Polecat |
EventSourcingTests/Explorer/* |
Diagnostics/event_store_explorer_tests.cs |
generating_event_store_descriptors.cs |
Diagnostics/event_store_explorer_tenant_isolation_tests.cs |
event_statistics.cs |
Diagnostics/tenant_scoped_explorer_reads_tests.cs |
determining_the_event_store_identity.cs |
Events/event_store_statistics_tests.cs |
Scope
New EventStoreExplorerCompliance suite:
GetRecentStreamsAsync returns the N most recent streams, newest first, with correct StreamSummary fields
- Requesting more streams than exist returns everything without throwing
GetStreamMetadataAsync for a known stream, and null for an unknown one
TryCreateUsage reports registered event types and projections
- Per-tenant overloads (gated on the tenancy suite's config support — see the conjoined tenancy issue; keep the single-tenant cases here unconditional)
The default-interface throw is itself worth an assertion path: a store that has not implemented an overload should skip via a capability gate, not fail — but neither current store should need the gate.
Acceptance
- Suite enrolled in both stores; any gate that ends up needed is filed as a product issue
- Originals retired for the absorbed behavior in both repos
Part of #5118 (compliance wave growth), epic #5110.
JasperFx.Events.IEventStoredeclares the event store explorer surface as default-interface methods that throw unless a store implements them:GetRecentStreamsAsync(int count, CancellationToken)→IReadOnlyList<StreamSummary>GetRecentStreamsAsync(int count, string? tenantId, CancellationToken)GetStreamMetadataAsync(string streamId, CancellationToken)→StreamMetadata?TryCreateUsage(CancellationToken)→EventStoreUsage?Both products implement them, both test them independently, and the fixture already exposes
EventStore. Portable with no seam addition.This surface matters more than a normal test suite: it is what CritterWatch consumes, so a cross-store contract test is the cheapest guard against a tooling regression on one store only.
What each store tests today
EventSourcingTests/Explorer/*Diagnostics/event_store_explorer_tests.csgenerating_event_store_descriptors.csDiagnostics/event_store_explorer_tenant_isolation_tests.csevent_statistics.csDiagnostics/tenant_scoped_explorer_reads_tests.csdetermining_the_event_store_identity.csEvents/event_store_statistics_tests.csScope
New
EventStoreExplorerCompliancesuite:GetRecentStreamsAsyncreturns the N most recent streams, newest first, with correctStreamSummaryfieldsGetStreamMetadataAsyncfor a known stream, and null for an unknown oneTryCreateUsagereports registered event types and projectionsThe default-interface throw is itself worth an assertion path: a store that has not implemented an overload should skip via a capability gate, not fail — but neither current store should need the gate.
Acceptance