- Fix pull consumer fetch: send original stream subject in HMSG (not inbox) so NATS client distinguishes data messages from control messages - Fix MaxAge expiry: add background timer in StreamManager for periodic pruning - Fix JetStream wire format: Go-compatible anonymous objects with string enums, proper offset-based pagination for stream/consumer list APIs - Add 42 E2E black-box tests (core messaging, auth, TLS, accounts, JetStream) - Add ~1000 parity tests across all subsystems (gaps closure) - Update gap inventory docs to reflect implementation status
3.6 KiB
3.6 KiB
RAFT Full Parity Design
Date: 2026-02-25
Category: raft
Gap Inventory: gaps/raft.md
Target Outcome: Full Go-to-.NET behavioral parity for this category.
Assumptions
- Full parity is the required outcome.
- No additional requirements gathering is needed for this pass.
- Existing public .NET APIs are preserved unless parity requires targeted, documented adjustments.
Current State Snapshot
MISSING: 99PARTIAL: 38PORTED: 46NOT_APPLICABLE: 13DEFERRED: 0- Open parity work items: 137
Approaches Considered
- Symbol-first closure (Recommended): execute directly against each
MISSINGandPARTIALrow ingaps/raft.md, closing items in deterministic order. Trade-off: strongest traceability and auditability, but can require broad context switching. - Test-first closure: derive all work from Go test scenarios first, then backfill missing symbols. Trade-off: maximizes behavioral confidence, but can miss non-test-covered API and helper parity.
- Vertical runtime slices: port connect/auth/pubsub/cluster flows end-to-end before moving to next slice. Trade-off: smoother integration validation, but weaker one-to-one mapping against inventory rows.
Recommended Design
Architecture
Use the gap inventory as the authoritative backlog. For each row, implement or complete the .NET equivalent, then attach test evidence and update the inventory status. Keep implementation inside existing category boundaries and only refactor when needed to match Go behavior.
Components
- Backlog driver:
gaps/raft.md(row-level tracking for all parity items). - Implementation surface: category-specific .NET source files.
- Verification surface: category-specific .NET tests plus cross-module regression tests.
- Parity bookkeeping: updates to
gaps/raft.mdandgaps/stillmissing.mdafter each closure batch.
Data Flow
- Read one
MISSINGorPARTIALrow fromgaps/raft.md. - Inspect referenced Go implementation and tests.
- Add/adjust .NET implementation in listed category files.
- Add failing .NET tests that reproduce the missing/partial behavior, then make them pass.
- Re-run targeted and regression tests.
- Update the row to
PORTED(or keepPARTIALwith explicit residual notes).
Error Handling and Risk Controls
- Avoid broad rewrites; prefer narrow patches tied to specific inventory rows.
- Preserve protocol and timing semantics when replacing Go concurrency constructs with .NET async patterns.
- Treat edge cases in Go tests as mandatory parity requirements unless explicitly marked
NOT_APPLICABLE. - Require evidence (tests + inventory status updates) before declaring row completion.
Testing Strategy
- Add or expand tests for each row moved from
MISSING/PARTIALtowardPORTED. - Prioritize wire/protocol compatibility, lifecycle transitions, auth boundaries, and backpressure/timeout behavior.
- Keep category-targeted tests fast; run full
NATS.Server.Testsregression before closure.
Definition of Done
- All category rows are either
PORTEDor explicitly justifiedNOT_APPLICABLE/DEFERRED. - No unresolved
MISSINGor unqualifiedPARTIALrows remain for this category. - Relevant .NET tests pass locally and parity evidence is written into inventory notes.
Implementation Scope Inputs
Go Source Files
golang/nats-server/server/raft.go
Go Test Files
golang/nats-server/server/raft_test.gogolang/nats-server/server/raft_helpers_test.gogolang/nats-server/server/raft_chain_of_blocks_helpers_test.go
.NET Source Files
src/NATS.Server/Raft/ (all 20 files)
.NET Test Files
tests/NATS.Server.Tests/Raft/