Files
natsdotnet/src/NATS.Server/Raft/RaftPeerState.cs
Joseph Doherty 5b706c969d feat(raft): add commit queue, election timers, and peer health tracking (B1+B2+B3)
- CommitQueue<T>: channel-based queue for committed entries awaiting state machine application
- RaftPeerState: tracks replication and health state (nextIndex, matchIndex, lastContact)
- RaftNode: CommitIndex/ProcessedIndex tracking, election timer with randomized 150-300ms interval,
  peer state integration with heartbeat and replication updates
- 52 new tests across RaftApplyQueueTests, RaftElectionTimerTests, RaftHealthTests
2026-02-24 17:01:00 -05:00

47 lines
1.5 KiB
C#

namespace NATS.Server.Raft;
/// <summary>
/// Tracks replication and health state for a single RAFT peer.
/// Go reference: raft.go peer tracking fields (nextIndex, matchIndex, last contact).
/// </summary>
public sealed class RaftPeerState
{
/// <summary>
/// The peer's unique node identifier.
/// </summary>
public required string PeerId { get; init; }
/// <summary>
/// The next log index to send to this peer (leader use only).
/// </summary>
public long NextIndex { get; set; } = 1;
/// <summary>
/// The highest log index known to be replicated on this peer.
/// </summary>
public long MatchIndex { get; set; }
/// <summary>
/// Timestamp of the last successful communication with this peer.
/// </summary>
public DateTime LastContact { get; set; } = DateTime.UtcNow;
/// <summary>
/// Whether this peer is considered active in the cluster.
/// </summary>
public bool Active { get; set; } = true;
/// <summary>
/// Returns true if this peer has been contacted within the election timeout window.
/// Go reference: raft.go isCurrent check.
/// </summary>
public bool IsCurrent(TimeSpan electionTimeout)
=> DateTime.UtcNow - LastContact < electionTimeout;
/// <summary>
/// Returns true if this peer is both active and has been contacted within the health threshold.
/// </summary>
public bool IsHealthy(TimeSpan healthThreshold)
=> Active && DateTime.UtcNow - LastContact < healthThreshold;
}