Search in sources :

Example 41 with TestActorRef

use of akka.testkit.TestActorRef in project controller by opendaylight.

the class RaftActorTest method testRaftActorRecoveryWithPersistenceEnabled.

@Test
public void testRaftActorRecoveryWithPersistenceEnabled() throws Exception {
    TEST_LOG.info("testRaftActorRecoveryWithPersistenceEnabled starting");
    TestKit kit = new TestKit(getSystem());
    String persistenceId = factory.generateActorId("follower-");
    DefaultConfigParamsImpl config = new DefaultConfigParamsImpl();
    // Set the heartbeat interval high to essentially disable election otherwise the test
    // may fail if the actor is switched to Leader and the commitIndex is set to the last
    // log entry.
    config.setHeartBeatInterval(new FiniteDuration(1, TimeUnit.DAYS));
    ImmutableMap<String, String> peerAddresses = ImmutableMap.<String, String>builder().put("member1", "address").build();
    ActorRef followerActor = factory.createActor(MockRaftActor.props(persistenceId, peerAddresses, config), persistenceId);
    kit.watch(followerActor);
    List<ReplicatedLogEntry> snapshotUnappliedEntries = new ArrayList<>();
    ReplicatedLogEntry entry1 = new SimpleReplicatedLogEntry(4, 1, new MockRaftActorContext.MockPayload("E"));
    snapshotUnappliedEntries.add(entry1);
    int lastAppliedDuringSnapshotCapture = 3;
    int lastIndexDuringSnapshotCapture = 4;
    // 4 messages as part of snapshot, which are applied to state
    MockSnapshotState snapshotState = new MockSnapshotState(Arrays.asList(new MockRaftActorContext.MockPayload("A"), new MockRaftActorContext.MockPayload("B"), new MockRaftActorContext.MockPayload("C"), new MockRaftActorContext.MockPayload("D")));
    Snapshot snapshot = Snapshot.create(snapshotState, snapshotUnappliedEntries, lastIndexDuringSnapshotCapture, 1, lastAppliedDuringSnapshotCapture, 1, -1, null, null);
    InMemorySnapshotStore.addSnapshot(persistenceId, snapshot);
    // add more entries after snapshot is taken
    List<ReplicatedLogEntry> entries = new ArrayList<>();
    ReplicatedLogEntry entry2 = new SimpleReplicatedLogEntry(5, 1, new MockRaftActorContext.MockPayload("F", 2));
    ReplicatedLogEntry entry3 = new SimpleReplicatedLogEntry(6, 1, new MockRaftActorContext.MockPayload("G", 3));
    ReplicatedLogEntry entry4 = new SimpleReplicatedLogEntry(7, 1, new MockRaftActorContext.MockPayload("H", 4));
    entries.add(entry2);
    entries.add(entry3);
    entries.add(entry4);
    final int lastAppliedToState = 5;
    final int lastIndex = 7;
    InMemoryJournal.addEntry(persistenceId, 5, entry2);
    // 2 entries are applied to state besides the 4 entries in snapshot
    InMemoryJournal.addEntry(persistenceId, 6, new ApplyJournalEntries(lastAppliedToState));
    InMemoryJournal.addEntry(persistenceId, 7, entry3);
    InMemoryJournal.addEntry(persistenceId, 8, entry4);
    // kill the actor
    followerActor.tell(PoisonPill.getInstance(), null);
    kit.expectMsgClass(kit.duration("5 seconds"), Terminated.class);
    kit.unwatch(followerActor);
    // reinstate the actor
    TestActorRef<MockRaftActor> ref = factory.createTestActor(MockRaftActor.props(persistenceId, peerAddresses, config));
    MockRaftActor mockRaftActor = ref.underlyingActor();
    mockRaftActor.waitForRecoveryComplete();
    RaftActorContext context = mockRaftActor.getRaftActorContext();
    assertEquals("Journal log size", snapshotUnappliedEntries.size() + entries.size(), context.getReplicatedLog().size());
    assertEquals("Journal data size", 10, context.getReplicatedLog().dataSize());
    assertEquals("Last index", lastIndex, context.getReplicatedLog().lastIndex());
    assertEquals("Last applied", lastAppliedToState, context.getLastApplied());
    assertEquals("Commit index", lastAppliedToState, context.getCommitIndex());
    assertEquals("Recovered state size", 6, mockRaftActor.getState().size());
    mockRaftActor.waitForInitializeBehaviorComplete();
    assertEquals("getRaftState", RaftState.Follower, mockRaftActor.getRaftState());
    TEST_LOG.info("testRaftActorRecoveryWithPersistenceEnabled ending");
}
Also used : MockSnapshotState(org.opendaylight.controller.cluster.raft.MockRaftActor.MockSnapshotState) ActorRef(akka.actor.ActorRef) TestActorRef(akka.testkit.TestActorRef) ArrayList(java.util.ArrayList) FiniteDuration(scala.concurrent.duration.FiniteDuration) MockPayload(org.opendaylight.controller.cluster.raft.MockRaftActorContext.MockPayload) TestKit(akka.testkit.javadsl.TestKit) ByteString(com.google.protobuf.ByteString) MockPayload(org.opendaylight.controller.cluster.raft.MockRaftActorContext.MockPayload) ApplySnapshot(org.opendaylight.controller.cluster.raft.base.messages.ApplySnapshot) Snapshot(org.opendaylight.controller.cluster.raft.persisted.Snapshot) GetSnapshot(org.opendaylight.controller.cluster.raft.client.messages.GetSnapshot) SimpleReplicatedLogEntry(org.opendaylight.controller.cluster.raft.persisted.SimpleReplicatedLogEntry) SimpleReplicatedLogEntry(org.opendaylight.controller.cluster.raft.persisted.SimpleReplicatedLogEntry) ApplyJournalEntries(org.opendaylight.controller.cluster.raft.persisted.ApplyJournalEntries) Test(org.junit.Test)

Example 42 with TestActorRef

use of akka.testkit.TestActorRef in project controller by opendaylight.

the class RaftActorTest method testLeaderTransitioning.

@Test
public void testLeaderTransitioning() throws Exception {
    TEST_LOG.info("testLeaderTransitioning starting");
    ActorRef notifierActor = factory.createActor(MessageCollectorActor.props());
    DefaultConfigParamsImpl config = new DefaultConfigParamsImpl();
    config.setCustomRaftPolicyImplementationClass(DisableElectionsRaftPolicy.class.getName());
    String persistenceId = factory.generateActorId("test-actor-");
    TestActorRef<MockRaftActor> raftActorRef = factory.createTestActor(MockRaftActor.builder().id(persistenceId).config(config).roleChangeNotifier(notifierActor).props().withDispatcher(Dispatchers.DefaultDispatcherId()), persistenceId);
    MockRaftActor mockRaftActor = raftActorRef.underlyingActor();
    mockRaftActor.waitForInitializeBehaviorComplete();
    raftActorRef.tell(new AppendEntries(1L, "leader", 0L, 1L, Collections.<ReplicatedLogEntry>emptyList(), 0L, -1L, (short) 1), ActorRef.noSender());
    LeaderStateChanged leaderStateChange = MessageCollectorActor.expectFirstMatching(notifierActor, LeaderStateChanged.class);
    assertEquals("getLeaderId", "leader", leaderStateChange.getLeaderId());
    MessageCollectorActor.clearMessages(notifierActor);
    raftActorRef.tell(new LeaderTransitioning("leader"), ActorRef.noSender());
    leaderStateChange = MessageCollectorActor.expectFirstMatching(notifierActor, LeaderStateChanged.class);
    assertEquals("getMemberId", persistenceId, leaderStateChange.getMemberId());
    assertEquals("getLeaderId", null, leaderStateChange.getLeaderId());
    TEST_LOG.info("testLeaderTransitioning ending");
}
Also used : SimpleReplicatedLogEntry(org.opendaylight.controller.cluster.raft.persisted.SimpleReplicatedLogEntry) ActorRef(akka.actor.ActorRef) TestActorRef(akka.testkit.TestActorRef) DisableElectionsRaftPolicy(org.opendaylight.controller.cluster.raft.policy.DisableElectionsRaftPolicy) ByteString(com.google.protobuf.ByteString) AppendEntries(org.opendaylight.controller.cluster.raft.messages.AppendEntries) LeaderTransitioning(org.opendaylight.controller.cluster.raft.base.messages.LeaderTransitioning) LeaderStateChanged(org.opendaylight.controller.cluster.notifications.LeaderStateChanged) Test(org.junit.Test)

Example 43 with TestActorRef

use of akka.testkit.TestActorRef in project controller by opendaylight.

the class RaftActorTest method testReplicateWithBatchHint.

@Test
public void testReplicateWithBatchHint() throws Exception {
    final String leaderId = factory.generateActorId("leader-");
    final String followerId = factory.generateActorId("follower-");
    final ActorRef followerActor = factory.createActor(MessageCollectorActor.props());
    DefaultConfigParamsImpl config = new DefaultConfigParamsImpl();
    config.setHeartBeatInterval(new FiniteDuration(1, TimeUnit.DAYS));
    config.setIsolatedLeaderCheckInterval(new FiniteDuration(1, TimeUnit.DAYS));
    TestActorRef<MockRaftActor> leaderActorRef = factory.createTestActor(MockRaftActor.props(leaderId, ImmutableMap.of(followerId, followerActor.path().toString()), config), leaderId);
    MockRaftActor leaderActor = leaderActorRef.underlyingActor();
    leaderActor.waitForInitializeBehaviorComplete();
    leaderActor.getRaftActorContext().getTermInformation().update(1, leaderId);
    Leader leader = new Leader(leaderActor.getRaftActorContext());
    leaderActor.setCurrentBehavior(leader);
    MessageCollectorActor.expectFirstMatching(followerActor, AppendEntries.class);
    MessageCollectorActor.clearMessages(followerActor);
    leaderActor.onReceiveCommand(new AppendEntriesReply(followerId, 1, true, -1, -1, (short) 0));
    leaderActor.persistData(leaderActorRef, new MockIdentifier("1"), new MockPayload("1"), true);
    MessageCollectorActor.assertNoneMatching(followerActor, AppendEntries.class, 500);
    leaderActor.persistData(leaderActorRef, new MockIdentifier("2"), new MockPayload("2"), true);
    MessageCollectorActor.assertNoneMatching(followerActor, AppendEntries.class, 500);
    leaderActor.persistData(leaderActorRef, new MockIdentifier("3"), new MockPayload("3"), false);
    AppendEntries appendEntries = MessageCollectorActor.expectFirstMatching(followerActor, AppendEntries.class);
    assertEquals("AppendEntries size", 3, appendEntries.getEntries().size());
}
Also used : Leader(org.opendaylight.controller.cluster.raft.behaviors.Leader) AppendEntriesReply(org.opendaylight.controller.cluster.raft.messages.AppendEntriesReply) ActorRef(akka.actor.ActorRef) TestActorRef(akka.testkit.TestActorRef) FiniteDuration(scala.concurrent.duration.FiniteDuration) ByteString(com.google.protobuf.ByteString) AppendEntries(org.opendaylight.controller.cluster.raft.messages.AppendEntries) MockPayload(org.opendaylight.controller.cluster.raft.MockRaftActorContext.MockPayload) Test(org.junit.Test)

Example 44 with TestActorRef

use of akka.testkit.TestActorRef in project controller by opendaylight.

the class RaftActorTest method testRaftRoleChangeNotifierWhenRaftActorHasNoPeers.

@Test
public void testRaftRoleChangeNotifierWhenRaftActorHasNoPeers() throws Exception {
    ActorRef notifierActor = factory.createActor(MessageCollectorActor.props());
    MessageCollectorActor.waitUntilReady(notifierActor);
    DefaultConfigParamsImpl config = new DefaultConfigParamsImpl();
    long heartBeatInterval = 100;
    config.setHeartBeatInterval(FiniteDuration.create(heartBeatInterval, TimeUnit.MILLISECONDS));
    config.setElectionTimeoutFactor(20);
    String persistenceId = factory.generateActorId("notifier-");
    final TestActorRef<MockRaftActor> raftActorRef = factory.createTestActor(MockRaftActor.builder().id(persistenceId).config(config).roleChangeNotifier(notifierActor).dataPersistenceProvider(createProvider()).props().withDispatcher(Dispatchers.DefaultDispatcherId()), persistenceId);
    List<RoleChanged> matches = MessageCollectorActor.expectMatching(notifierActor, RoleChanged.class, 3);
    // check if the notifier got a role change from null to Follower
    RoleChanged raftRoleChanged = matches.get(0);
    assertEquals(persistenceId, raftRoleChanged.getMemberId());
    assertNull(raftRoleChanged.getOldRole());
    assertEquals(RaftState.Follower.name(), raftRoleChanged.getNewRole());
    // check if the notifier got a role change from Follower to Candidate
    raftRoleChanged = matches.get(1);
    assertEquals(persistenceId, raftRoleChanged.getMemberId());
    assertEquals(RaftState.Follower.name(), raftRoleChanged.getOldRole());
    assertEquals(RaftState.Candidate.name(), raftRoleChanged.getNewRole());
    // check if the notifier got a role change from Candidate to Leader
    raftRoleChanged = matches.get(2);
    assertEquals(persistenceId, raftRoleChanged.getMemberId());
    assertEquals(RaftState.Candidate.name(), raftRoleChanged.getOldRole());
    assertEquals(RaftState.Leader.name(), raftRoleChanged.getNewRole());
    LeaderStateChanged leaderStateChange = MessageCollectorActor.expectFirstMatching(notifierActor, LeaderStateChanged.class);
    assertEquals(raftRoleChanged.getMemberId(), leaderStateChange.getLeaderId());
    assertEquals(MockRaftActor.PAYLOAD_VERSION, leaderStateChange.getLeaderPayloadVersion());
    MessageCollectorActor.clearMessages(notifierActor);
    MockRaftActor raftActor = raftActorRef.underlyingActor();
    final String newLeaderId = "new-leader";
    final short newLeaderVersion = 6;
    Follower follower = new Follower(raftActor.getRaftActorContext()) {

        @Override
        public RaftActorBehavior handleMessage(final ActorRef sender, final Object message) {
            setLeaderId(newLeaderId);
            setLeaderPayloadVersion(newLeaderVersion);
            return this;
        }
    };
    raftActor.newBehavior(follower);
    leaderStateChange = MessageCollectorActor.expectFirstMatching(notifierActor, LeaderStateChanged.class);
    assertEquals(persistenceId, leaderStateChange.getMemberId());
    assertEquals(null, leaderStateChange.getLeaderId());
    raftRoleChanged = MessageCollectorActor.expectFirstMatching(notifierActor, RoleChanged.class);
    assertEquals(RaftState.Leader.name(), raftRoleChanged.getOldRole());
    assertEquals(RaftState.Follower.name(), raftRoleChanged.getNewRole());
    MessageCollectorActor.clearMessages(notifierActor);
    raftActor.handleCommand("any");
    leaderStateChange = MessageCollectorActor.expectFirstMatching(notifierActor, LeaderStateChanged.class);
    assertEquals(persistenceId, leaderStateChange.getMemberId());
    assertEquals(newLeaderId, leaderStateChange.getLeaderId());
    assertEquals(newLeaderVersion, leaderStateChange.getLeaderPayloadVersion());
    MessageCollectorActor.clearMessages(notifierActor);
    raftActor.handleCommand("any");
    Uninterruptibles.sleepUninterruptibly(505, TimeUnit.MILLISECONDS);
    leaderStateChange = MessageCollectorActor.getFirstMatching(notifierActor, LeaderStateChanged.class);
    assertNull(leaderStateChange);
}
Also used : ActorRef(akka.actor.ActorRef) TestActorRef(akka.testkit.TestActorRef) Follower(org.opendaylight.controller.cluster.raft.behaviors.Follower) Matchers.anyObject(org.mockito.Matchers.anyObject) ByteString(com.google.protobuf.ByteString) RoleChanged(org.opendaylight.controller.cluster.notifications.RoleChanged) LeaderStateChanged(org.opendaylight.controller.cluster.notifications.LeaderStateChanged) Test(org.junit.Test)

Example 45 with TestActorRef

use of akka.testkit.TestActorRef in project controller by opendaylight.

the class RaftActorTest method testReplicateWithPersistencePending.

@SuppressWarnings({ "unchecked", "rawtypes" })
@Test
public void testReplicateWithPersistencePending() throws Exception {
    final String leaderId = factory.generateActorId("leader-");
    final String followerId = factory.generateActorId("follower-");
    final ActorRef followerActor = factory.createActor(MessageCollectorActor.props());
    DefaultConfigParamsImpl config = new DefaultConfigParamsImpl();
    config.setHeartBeatInterval(new FiniteDuration(1, TimeUnit.DAYS));
    config.setIsolatedLeaderCheckInterval(new FiniteDuration(1, TimeUnit.DAYS));
    DataPersistenceProvider mockPersistenceProvider = mock(DataPersistenceProvider.class);
    doReturn(true).when(mockPersistenceProvider).isRecoveryApplicable();
    TestActorRef<MockRaftActor> leaderActorRef = factory.createTestActor(MockRaftActor.props(leaderId, ImmutableMap.of(followerId, followerActor.path().toString()), config, mockPersistenceProvider), leaderId);
    MockRaftActor leaderActor = leaderActorRef.underlyingActor();
    leaderActor.waitForInitializeBehaviorComplete();
    leaderActor.getRaftActorContext().getTermInformation().update(1, leaderId);
    Leader leader = new Leader(leaderActor.getRaftActorContext());
    leaderActor.setCurrentBehavior(leader);
    leaderActor.persistData(leaderActorRef, new MockIdentifier("1"), new MockRaftActorContext.MockPayload("1"), false);
    ReplicatedLogEntry logEntry = leaderActor.getReplicatedLog().get(0);
    assertNotNull("ReplicatedLogEntry not found", logEntry);
    assertEquals("isPersistencePending", true, logEntry.isPersistencePending());
    assertEquals("getCommitIndex", -1, leaderActor.getRaftActorContext().getCommitIndex());
    leaderActor.onReceiveCommand(new AppendEntriesReply(followerId, 1, true, 0, 1, (short) 0));
    assertEquals("getCommitIndex", -1, leaderActor.getRaftActorContext().getCommitIndex());
    ArgumentCaptor<Procedure> callbackCaptor = ArgumentCaptor.forClass(Procedure.class);
    verify(mockPersistenceProvider).persistAsync(eq(logEntry), callbackCaptor.capture());
    callbackCaptor.getValue().apply(logEntry);
    assertEquals("getCommitIndex", 0, leaderActor.getRaftActorContext().getCommitIndex());
    assertEquals("getLastApplied", 0, leaderActor.getRaftActorContext().getLastApplied());
}
Also used : Leader(org.opendaylight.controller.cluster.raft.behaviors.Leader) ActorRef(akka.actor.ActorRef) TestActorRef(akka.testkit.TestActorRef) FiniteDuration(scala.concurrent.duration.FiniteDuration) MockPayload(org.opendaylight.controller.cluster.raft.MockRaftActorContext.MockPayload) ByteString(com.google.protobuf.ByteString) SimpleReplicatedLogEntry(org.opendaylight.controller.cluster.raft.persisted.SimpleReplicatedLogEntry) AppendEntriesReply(org.opendaylight.controller.cluster.raft.messages.AppendEntriesReply) DataPersistenceProvider(org.opendaylight.controller.cluster.DataPersistenceProvider) Procedure(akka.japi.Procedure) Test(org.junit.Test)

Aggregations

ActorRef (akka.actor.ActorRef)65 TestActorRef (akka.testkit.TestActorRef)65 Test (org.junit.Test)64 FiniteDuration (scala.concurrent.duration.FiniteDuration)18 TestKit (akka.testkit.javadsl.TestKit)17 AddServer (org.opendaylight.controller.cluster.raft.messages.AddServer)14 AddServerReply (org.opendaylight.controller.cluster.raft.messages.AddServerReply)13 SimpleReplicatedLogEntry (org.opendaylight.controller.cluster.raft.persisted.SimpleReplicatedLogEntry)13 DisableElectionsRaftPolicy (org.opendaylight.controller.cluster.raft.policy.DisableElectionsRaftPolicy)12 UpdateSchemaContext (org.opendaylight.controller.cluster.datastore.messages.UpdateSchemaContext)11 ByteString (com.google.protobuf.ByteString)10 RegisterChangeListener (org.opendaylight.controller.cluster.datastore.messages.RegisterChangeListener)10 MockDataChangeListener (org.opendaylight.controller.cluster.datastore.utils.MockDataChangeListener)10 YangInstanceIdentifier (org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier)10 AddressFromURIString (akka.actor.AddressFromURIString)9 AbstractShardManagerTest (org.opendaylight.controller.cluster.datastore.AbstractShardManagerTest)9 RegisterDataTreeNotificationListenerReply (org.opendaylight.controller.cluster.datastore.messages.RegisterDataTreeNotificationListenerReply)9 RoleChangeNotification (org.opendaylight.controller.cluster.notifications.RoleChangeNotification)9 Follower (org.opendaylight.controller.cluster.raft.behaviors.Follower)9 ShardLeaderStateChanged (org.opendaylight.controller.cluster.datastore.messages.ShardLeaderStateChanged)8