# openraft port — membership/t12_concurrent_write_and_add_learner: adding a learner CONCURRENTLY with
# a client write must not lose the write to the new learner. (openraft's bug: when a fresh replica
# was lagging, its replication buffers were purged and only committed logs re-sent, so an uncommitted
# write proposed in the same window never reached the learner.) Here the add-learner conf-change and a
# normal write `b` are both proposed before any delivery; the new lagging learner n4 must catch up to
# EVERY log, including the concurrently-written `b`.
add-nodes 3 voters=(1,2,3)
----
n1: created voters={1,2,3} term=0 commit=0 last=0
n2: created voters={1,2,3} term=0 commit=0 last=0
n3: created voters={1,2,3} term=0 commit=0 last=0

campaign 1
----
n1 candidate term=1
RequestVote term=1 last=0/0 prevote=false
RequestVote term=1 last=0/0 prevote=false

stabilize
----
> n2 recv RequestVote term=1 last=0/0 prevote=false
> n3 recv RequestVote term=1 last=0/0 prevote=false
> n2 ready
  VoteResponse term=1 prevote=false reject=false
> n3 ready
  VoteResponse term=1 prevote=false reject=false
> n1 recv VoteResponse term=1 prevote=false reject=false
> n1 recv VoteResponse term=1 prevote=false reject=false
> n1 ready
  Heartbeat term=1 commit=0
  Heartbeat term=1 commit=0
  AppendEntries term=1 prev=0/0 commit=0 entries=[1/1 empty]
  AppendEntries term=1 prev=0/0 commit=0 entries=[1/1 empty]
  n1 leader-changed term=1 lead=1
> n2 recv Heartbeat term=1 commit=0
> n3 recv Heartbeat term=1 commit=0
> n2 recv AppendEntries term=1 prev=0/0 commit=0 entries=[1/1 empty]
> n3 recv AppendEntries term=1 prev=0/0 commit=0 entries=[1/1 empty]
> n2 ready
  HeartbeatResponse term=1
  AppendResponse term=1 match=1
  n2 leader-changed term=1 lead=1
> n3 ready
  HeartbeatResponse term=1
  AppendResponse term=1 match=1
  n3 leader-changed term=1 lead=1
> n1 recv HeartbeatResponse term=1
> n1 recv AppendResponse term=1 match=1
> n1 recv HeartbeatResponse term=1
> n1 recv AppendResponse term=1 match=1
> n1 ready
  AppendEntries term=1 prev=0/0 commit=0 entries=[1/1 empty]
  AppendEntries term=1 prev=1/1 commit=1 entries=[]
  AppendEntries term=1 prev=0/0 commit=1 entries=[1/1 empty]
  AppendEntries term=1 prev=1/1 commit=1 entries=[]
> n2 recv AppendEntries term=1 prev=0/0 commit=0 entries=[1/1 empty]
> n2 recv AppendEntries term=1 prev=1/1 commit=1 entries=[]
> n3 recv AppendEntries term=1 prev=0/0 commit=1 entries=[1/1 empty]
> n3 recv AppendEntries term=1 prev=1/1 commit=1 entries=[]
> n2 ready
  AppendResponse term=1 match=1
  AppendResponse term=1 match=1
> n3 ready
  AppendResponse term=1 match=1
  AppendResponse term=1 match=1
> n1 recv AppendResponse term=1 match=1
> n1 recv AppendResponse term=1 match=1
> n1 recv AppendResponse term=1 match=1
> n1 recv AppendResponse term=1 match=1

propose 1 a
----
AppendEntries term=1 prev=1/1 commit=1 entries=[1/2 normal 0x010000000000000061]
AppendEntries term=1 prev=1/1 commit=1 entries=[1/2 normal 0x010000000000000061]

stabilize
----
> n2 recv AppendEntries term=1 prev=1/1 commit=1 entries=[1/2 normal 0x010000000000000061]
> n3 recv AppendEntries term=1 prev=1/1 commit=1 entries=[1/2 normal 0x010000000000000061]
> n2 ready
  AppendResponse term=1 match=2
> n3 ready
  AppendResponse term=1 match=2
> n1 recv AppendResponse term=1 match=2
> n1 recv AppendResponse term=1 match=2
> n1 ready
  AppendEntries term=1 prev=1/2 commit=2 entries=[]
  AppendEntries term=1 prev=1/2 commit=2 entries=[]
  n1 applied index=2
> n2 recv AppendEntries term=1 prev=1/2 commit=2 entries=[]
> n3 recv AppendEntries term=1 prev=1/2 commit=2 entries=[]
> n2 ready
  AppendResponse term=1 match=2
  n2 applied index=2
> n3 ready
  AppendResponse term=1 match=2
  n3 applied index=2
> n1 recv AppendResponse term=1 match=2
> n1 recv AppendResponse term=1 match=2

propose-conf-change 1 addlearner 4
----
n1 proposed conf-change addlearner n4 at index 3
AppendEntries term=1 prev=1/2 commit=2 entries=[1/3 conf-change 0x120c080212080400000000000000]
AppendEntries term=1 prev=1/2 commit=2 entries=[1/3 conf-change 0x120c080212080400000000000000]

propose 1 b
----
AppendEntries term=1 prev=1/3 commit=2 entries=[1/4 normal 0x010000000000000062]
AppendEntries term=1 prev=1/3 commit=2 entries=[1/4 normal 0x010000000000000062]

stabilize
----
> n2 recv AppendEntries term=1 prev=1/2 commit=2 entries=[1/3 conf-change 0x120c080212080400000000000000]
> n3 recv AppendEntries term=1 prev=1/2 commit=2 entries=[1/3 conf-change 0x120c080212080400000000000000]
> n2 recv AppendEntries term=1 prev=1/3 commit=2 entries=[1/4 normal 0x010000000000000062]
> n3 recv AppendEntries term=1 prev=1/3 commit=2 entries=[1/4 normal 0x010000000000000062]
> n2 ready
  AppendResponse term=1 match=3
  AppendResponse term=1 match=4
> n3 ready
  AppendResponse term=1 match=3
  AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=3
> n1 recv AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=3
> n1 recv AppendResponse term=1 match=4
> n1 ready
  AppendEntries term=1 prev=1/4 commit=3 entries=[]
  AppendEntries term=1 prev=1/4 commit=4 entries=[]
  AppendEntries term=1 prev=1/4 commit=4 entries=[]
  AppendEntries term=1 prev=1/4 commit=4 entries=[]
  n1 conf-changed index=3 voters={1,2,3} learners={4}
  n1 applied index=4
> n2 recv AppendEntries term=1 prev=1/4 commit=3 entries=[]
> n2 recv AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n3 recv AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n3 recv AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n2 ready
  AppendResponse term=1 match=4
  AppendResponse term=1 match=4
  n2 conf-changed index=3 voters={1,2,3} learners={4}
  n2 applied index=4
> n3 ready
  AppendResponse term=1 match=4
  AppendResponse term=1 match=4
  n3 conf-changed index=3 voters={1,2,3} learners={4}
  n3 applied index=4
> n1 recv AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=4

tick-heartbeat 1
----
Heartbeat term=1 commit=4
Heartbeat term=1 commit=4
Heartbeat term=1 commit=0

stabilize
----
> n2 recv Heartbeat term=1 commit=4
> n3 recv Heartbeat term=1 commit=4
> n4 recv Heartbeat term=1 commit=0
> n2 ready
  HeartbeatResponse term=1
> n3 ready
  HeartbeatResponse term=1
> n4 ready
  HeartbeatResponse term=1
  n4 leader-changed term=1 lead=1
> n1 recv HeartbeatResponse term=1
> n1 recv HeartbeatResponse term=1
> n1 recv HeartbeatResponse term=1
> n1 ready
  AppendEntries term=1 prev=1/4 commit=4 entries=[]
  AppendEntries term=1 prev=1/4 commit=4 entries=[]
  AppendEntries term=1 prev=1/3 commit=4 entries=[1/4 normal 0x010000000000000062]
> n2 recv AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n3 recv AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n4 recv AppendEntries term=1 prev=1/3 commit=4 entries=[1/4 normal 0x010000000000000062]
> n2 ready
  AppendResponse term=1 match=4
> n3 ready
  AppendResponse term=1 match=4
> n4 ready
  AppendResponse term=1 reject hint=0/0
> n1 recv AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 reject hint=0/0
> n1 ready
  AppendEntries term=1 prev=0/0 commit=4 entries=[1/1 empty, 1/2 normal 0x010000000000000061, 1/3 conf-change 0x120c080212080400000000000000, 1/4 normal 0x010000000000000062]
> n4 recv AppendEntries term=1 prev=0/0 commit=4 entries=[1/1 empty, 1/2 normal 0x010000000000000061, 1/3 conf-change 0x120c080212080400000000000000, 1/4 normal 0x010000000000000062]
> n4 ready
  AppendResponse term=1 match=4
  n4 applied index=2
  n4 conf-changed index=3 voters={1,2,3} learners={4}
  n4 applied index=4
> n1 recv AppendResponse term=1 match=4
> n1 ready
  AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n4 recv AppendEntries term=1 prev=1/4 commit=4 entries=[]
> n4 ready
  AppendResponse term=1 match=4
> n1 recv AppendResponse term=1 match=4

raft-log 4
----
n4: commit=4 applied=4 last=4
  1/1 empty
  1/2 normal 0x010000000000000061
  1/3 conf-change 0x120c080212080400000000000000
  1/4 normal 0x010000000000000062

conf-state 4
----
n4: voters={1,2,3} learners={4}

