internal RaftEventResult TranslateToState(RaftNodeState newState, RaftMessageBase message = null) { RaftStateBase <T> newStateObject = null; if (newState == RaftNodeState.Candidate) { newStateObject = new Candicate <T>(this); } else if (newState == RaftNodeState.Follower) { newStateObject = new Follower <T>(this); } else if (newState == RaftNodeState.Leader) { newStateObject = new Leader <T>(this); } else { throw new ArgumentException(); } StateObject = newStateObject; RaftEventResult enterStateResult = StateObject.EnterState(); if (message != null) { if (enterStateResult.MessageToSend != null) { throw new Exception("WTF"); } return(OnMessageReceived(message)); } return(enterStateResult); }
public RaftEventResult OnMessageReceived(RaftMessageBase raftMessage) { RaftEventResult raftResult = null; /* Append entries */ var appEntries = raftMessage as AppendEntriesRPC <T>; if (appEntries != null) { raftResult = StateObject.ReceiveAppendEntries(appEntries); } /* Append entries response */ var appEntriesResponse = raftMessage as AppendEntriesResponse; if (appEntriesResponse != null) { raftResult = StateObject.ReceiveAppendEntriesResponse(appEntriesResponse); } /* Request vote */ var requestVote = raftMessage as RequestVote; if (requestVote != null) { raftResult = StateObject.ReceiveRequestVote(requestVote); } /* Request vote response */ var requestVoteResponse = raftMessage as RequestVoteResponse; if (requestVoteResponse != null) { raftResult = StateObject.ReceiveRequestVoteResponse(requestVoteResponse); } /* client rpc */ var clientRequest = raftMessage as ClientRequestRPC <T>; if (clientRequest != null) { PersistedState.AddEntry(clientRequest.Message); raftResult = RaftEventResult.Empty; } if (raftResult == null) { throw new InvalidOperationException("Raft message processing returned null"); } return(raftResult); }
protected override void OnMessageReceived(INetworkSocket channel, object message) { RaftMessageBase raftMessage = message as RaftMessageBase; if (raftMessage is AppendEntriesRPC <string> ) { leaderChannel = channel; } Message messageFromClient = message as Message; if (messageFromClient != null) { if (Raft.State == RaftNodeState.Leader) { raftMessage = new ClientRequestRPC <string>() { Message = messageFromClient.Operation, SequenceNumber = 0 }; } else { if (leaderChannel != null) { SendMessage(leaderChannel, messageFromClient); } // forward message to leader } } if (raftMessage != null) { var raftOperationResult = Raft.OnMessageReceived(raftMessage); ProcessRaftResult(raftOperationResult, channel); } }
/// <summary> /// Create event that will result in broadcasting message /// </summary> /// <param name="raftMessage"></param> /// <returns></returns> public static RaftEventResult BroadcastMessage(RaftMessageBase raftMessage) { return(new RaftEventResult(raftMessage, true)); }
/// <summary> /// Create event that will result in replying to port that request came from /// </summary> /// <param name="raftMessage"></param> /// <returns></returns> public static RaftEventResult ReplyMessage(RaftMessageBase raftMessage) { return(new RaftEventResult(raftMessage, false)); }
/// <summary> /// Create RaftEventResult object /// </summary> /// <param name="raftMessage">Message to broadcast or reply</param> /// <param name="doBroadcast">True of message need broadcasting instead of replying</param> public RaftEventResult(RaftMessageBase raftMessage, bool doBroadcast) { this.DoBroadcast = doBroadcast; this.MessageToSend = raftMessage; }