use of org.apache.ignite.raft.jraft.Node in project ignite-3 by apache.
the class ItNodeTest method testInstallSnapshot.
@Test
public void testInstallSnapshot() throws Exception {
List<PeerId> peers = TestUtils.generatePeers(3);
cluster = new TestCluster("unitest", dataPath, peers, testInfo);
for (PeerId peer : peers) assertTrue(cluster.start(peer.getEndpoint()));
cluster.waitLeader();
// get leader
Node leader = cluster.getLeader();
assertNotNull(leader);
cluster.ensureLeader(leader);
// apply tasks to leader
sendTestTaskAndWait(leader);
cluster.ensureSame();
// stop follower1
List<Node> followers = cluster.getFollowers();
assertEquals(2, followers.size());
Endpoint followerAddr = followers.get(0).getNodeId().getPeerId().getEndpoint();
assertTrue(cluster.stop(followerAddr));
// apply something more
sendTestTaskAndWait(leader, 10, RaftError.SUCCESS);
// trigger leader snapshot
triggerLeaderSnapshot(cluster, leader);
// apply something more
sendTestTaskAndWait(leader, 20, RaftError.SUCCESS);
triggerLeaderSnapshot(cluster, leader, 2);
// wait leader to compact logs
Thread.sleep(50);
// restart follower.
cluster.clean(followerAddr);
assertTrue(cluster.start(followerAddr, false, 300));
cluster.ensureSame();
assertEquals(3, cluster.getFsms().size());
for (MockStateMachine fsm : cluster.getFsms()) assertEquals(30, fsm.getLogs().size(), fsm.getAddress().toString());
}
use of org.apache.ignite.raft.jraft.Node in project ignite-3 by apache.
the class ItNodeTest method testTripleNodesWithLearners.
@Test
public void testTripleNodesWithLearners() throws Exception {
List<PeerId> peers = TestUtils.generatePeers(3);
cluster = new TestCluster("unittest", dataPath, peers, testInfo);
for (PeerId peer : peers) assertTrue(cluster.start(peer.getEndpoint()));
// elect leader
cluster.waitLeader();
// get leader
Node leader = cluster.getLeader();
assertNotNull(leader);
cluster.ensureLeader(leader);
assertEquals(3, leader.listPeers().size());
assertTrue(leader.listLearners().isEmpty());
assertTrue(leader.listAliveLearners().isEmpty());
{
// Adds a learner
SynchronizedClosure done = new SynchronizedClosure();
PeerId learnerPeer = new PeerId(TestUtils.getLocalAddress(), TestUtils.INIT_PORT + 3);
// Start learner
assertTrue(cluster.startLearner(learnerPeer));
leader.addLearners(Arrays.asList(learnerPeer), done);
assertTrue(done.await().isOk());
assertEquals(1, leader.listAliveLearners().size());
assertEquals(1, leader.listLearners().size());
}
// apply tasks to leader
sendTestTaskAndWait(leader);
{
ByteBuffer data = ByteBuffer.wrap("no closure".getBytes(UTF_8));
Task task = new Task(data, null);
leader.apply(task);
}
{
// task with TaskClosure
ByteBuffer data = ByteBuffer.wrap("task closure".getBytes(UTF_8));
List<String> cbs = synchronizedList(new ArrayList<>());
CountDownLatch latch = new CountDownLatch(1);
Task task = new Task(data, new TaskClosure() {
@Override
public void run(Status status) {
cbs.add("apply");
latch.countDown();
}
@Override
public void onCommitted() {
cbs.add("commit");
}
});
leader.apply(task);
latch.await();
assertEquals(2, cbs.size());
assertEquals("commit", cbs.get(0));
assertEquals("apply", cbs.get(1));
}
assertEquals(4, cluster.getFsms().size());
assertEquals(2, cluster.getFollowers().size());
assertEquals(1, cluster.getLearners().size());
cluster.ensureSame();
{
// Adds another learner
SynchronizedClosure done = new SynchronizedClosure();
PeerId learnerPeer = new PeerId(TestUtils.getLocalAddress(), TestUtils.INIT_PORT + 4);
// Start learner
assertTrue(cluster.startLearner(learnerPeer));
leader.addLearners(Arrays.asList(learnerPeer), done);
assertTrue(done.await().isOk());
assertEquals(2, leader.listAliveLearners().size());
assertEquals(2, leader.listLearners().size());
cluster.ensureSame();
}
{
// stop two followers
for (Node follower : cluster.getFollowers()) assertTrue(cluster.stop(follower.getNodeId().getPeerId().getEndpoint()));
// send a new task
ByteBuffer data = ByteBuffer.wrap("task closure".getBytes(UTF_8));
SynchronizedClosure done = new SynchronizedClosure();
leader.apply(new Task(data, done));
// should fail
assertFalse(done.await().isOk());
assertEquals(RaftError.EPERM, done.getStatus().getRaftError());
// One peer with two learners.
assertEquals(3, cluster.getFsms().size());
}
}
use of org.apache.ignite.raft.jraft.Node in project ignite-3 by apache.
the class ItNodeTest method testSingleNode.
@Test
public void testSingleNode() throws Exception {
Endpoint addr = new Endpoint(TestUtils.getLocalAddress(), TestUtils.INIT_PORT);
PeerId peer = new PeerId(addr, 0);
NodeOptions nodeOptions = createNodeOptions();
MockStateMachine fsm = new MockStateMachine(addr);
nodeOptions.setFsm(fsm);
nodeOptions.setLogUri(dataPath + File.separator + "log");
nodeOptions.setRaftMetaUri(dataPath + File.separator + "meta");
nodeOptions.setSnapshotUri(dataPath + File.separator + "snapshot");
nodeOptions.setInitialConf(new Configuration(Collections.singletonList(peer)));
RaftGroupService service = createService("unittest", peer, nodeOptions);
Node node = service.start();
assertEquals(1, node.listPeers().size());
assertTrue(node.listPeers().contains(peer));
while (!node.isLeader()) ;
sendTestTaskAndWait(node);
assertEquals(10, fsm.getLogs().size());
int i = 0;
for (ByteBuffer data : fsm.getLogs()) {
assertEquals("hello" + i++, stringFromBytes(data.array()));
}
}
use of org.apache.ignite.raft.jraft.Node in project ignite-3 by apache.
the class ItNodeTest method testLeaderFail.
@Test
public void testLeaderFail() throws Exception {
List<PeerId> peers = TestUtils.generatePeers(3);
cluster = new TestCluster("unittest", dataPath, peers, testInfo);
for (PeerId peer : peers) assertTrue(cluster.start(peer.getEndpoint()));
// elect leader
cluster.waitLeader();
// get leader
Node leader = cluster.getLeader();
assertNotNull(leader);
LOG.info("Current leader is {}", leader.getLeaderId());
// apply tasks to leader
sendTestTaskAndWait(leader);
List<Node> followers = cluster.getFollowers();
blockMessagesOnFollowers(followers, (msg, nodeId) -> {
if (msg instanceof RpcRequests.RequestVoteRequest) {
RpcRequests.RequestVoteRequest msg0 = (RpcRequests.RequestVoteRequest) msg;
return !msg0.preVote();
}
return false;
});
// stop leader
LOG.warn("Stop leader {}", leader.getNodeId().getPeerId());
PeerId oldLeader = leader.getNodeId().getPeerId();
assertTrue(cluster.stop(leader.getNodeId().getPeerId().getEndpoint()));
assertFalse(followers.isEmpty());
// Should fail, because no leader.
sendTestTaskAndWait("follower apply ", followers.get(0), -1);
stopBlockingMessagesOnFollowers(followers);
// elect new leader
cluster.waitLeader();
leader = cluster.getLeader();
LOG.info("Elect new leader is {}", leader.getLeaderId());
// apply tasks to new leader
CountDownLatch latch = new CountDownLatch(10);
for (int i = 10; i < 20; i++) {
ByteBuffer data = ByteBuffer.wrap(("hello" + i).getBytes(UTF_8));
Task task = new Task(data, new ExpectClosure(latch));
leader.apply(task);
}
waitLatch(latch);
// restart old leader
LOG.info("restart old leader {}", oldLeader);
assertTrue(cluster.start(oldLeader.getEndpoint()));
// apply something
latch = new CountDownLatch(10);
for (int i = 20; i < 30; i++) {
ByteBuffer data = ByteBuffer.wrap(("hello" + i).getBytes(UTF_8));
Task task = new Task(data, new ExpectClosure(latch));
leader.apply(task);
}
waitLatch(latch);
// stop and clean old leader
cluster.stop(oldLeader.getEndpoint());
cluster.clean(oldLeader.getEndpoint());
// restart old leader
LOG.info("Restart old leader with cleanup {}", oldLeader);
assertTrue(cluster.start(oldLeader.getEndpoint()));
cluster.ensureSame();
for (MockStateMachine fsm : cluster.getFsms()) assertEquals(30, fsm.getLogs().size());
}
use of org.apache.ignite.raft.jraft.Node in project ignite-3 by apache.
the class ItNodeTest method testJoinNodes.
@Test
public void testJoinNodes() throws Exception {
PeerId peer0 = new PeerId(TestUtils.getLocalAddress(), TestUtils.INIT_PORT);
PeerId peer1 = new PeerId(TestUtils.getLocalAddress(), TestUtils.INIT_PORT + 1);
PeerId peer2 = new PeerId(TestUtils.getLocalAddress(), TestUtils.INIT_PORT + 2);
PeerId peer3 = new PeerId(TestUtils.getLocalAddress(), TestUtils.INIT_PORT + 3);
ArrayList<PeerId> peers = new ArrayList<>();
peers.add(peer0);
// start single cluster
cluster = new TestCluster("unittest", dataPath, peers, testInfo);
assertTrue(cluster.start(peer0.getEndpoint()));
cluster.waitLeader();
Node leader = cluster.getLeader();
assertNotNull(leader);
assertEquals(leader.getNodeId().getPeerId(), peer0);
sendTestTaskAndWait(leader);
// start peer1
assertTrue(cluster.start(peer1.getEndpoint(), false, 300));
// add peer1
CountDownLatch latch = new CountDownLatch(1);
peers.add(peer1);
leader.addPeer(peer1, new ExpectClosure(latch));
waitLatch(latch);
cluster.ensureSame();
assertEquals(2, cluster.getFsms().size());
for (MockStateMachine fsm : cluster.getFsms()) assertEquals(10, fsm.getLogs().size());
// add peer2 but not start
peers.add(peer2);
latch = new CountDownLatch(1);
leader.addPeer(peer2, new ExpectClosure(RaftError.ECATCHUP, latch));
waitLatch(latch);
// start peer2 after 2 seconds
Thread.sleep(2000);
assertTrue(cluster.start(peer2.getEndpoint(), false, 300));
// re-add peer2
latch = new CountDownLatch(2);
leader.addPeer(peer2, new ExpectClosure(latch));
// concurrent configuration change
leader.addPeer(peer3, new ExpectClosure(RaftError.EBUSY, latch));
waitLatch(latch);
try {
leader.addPeer(peer2, new ExpectClosure(latch));
fail();
} catch (IllegalArgumentException e) {
assertEquals("Peer already exists in current configuration", e.getMessage());
}
cluster.ensureSame();
assertEquals(3, cluster.getFsms().size());
assertEquals(2, cluster.getFollowers().size());
for (MockStateMachine fsm : cluster.getFsms()) assertEquals(10, fsm.getLogs().size());
}
Aggregations