203a61233d3df2d8c95da39701f746e31e5df1a4
[controller.git] / opendaylight / md-sal / sal-akka-raft / src / main / java / org / opendaylight / controller / cluster / raft / GetSnapshotReplyActor.java
1 /*
2  * Copyright (c) 2015 Brocade Communications Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.controller.cluster.raft;
9
10 import akka.actor.ActorRef;
11 import akka.actor.PoisonPill;
12 import akka.actor.Props;
13 import akka.actor.ReceiveTimeout;
14 import akka.actor.UntypedActor;
15 import com.google.common.base.Preconditions;
16 import java.util.concurrent.TimeoutException;
17 import org.opendaylight.controller.cluster.raft.base.messages.CaptureSnapshot;
18 import org.opendaylight.controller.cluster.raft.base.messages.CaptureSnapshotReply;
19 import org.opendaylight.controller.cluster.raft.client.messages.GetSnapshotReply;
20 import org.opendaylight.controller.cluster.raft.persisted.ServerConfigurationPayload;
21 import org.opendaylight.controller.cluster.raft.persisted.Snapshot;
22 import org.slf4j.Logger;
23 import org.slf4j.LoggerFactory;
24 import scala.concurrent.duration.Duration;
25
26 /**
27  * Temporary actor used to receive a CaptureSnapshotReply message and return a GetSnapshotReply instance.
28  *
29  * @author Thomas Pantelis
30  */
31 class GetSnapshotReplyActor extends UntypedActor {
32     private static final Logger LOG = LoggerFactory.getLogger(GetSnapshotReplyActor.class);
33
34     private final Params params;
35
36     private GetSnapshotReplyActor(Params params) {
37         this.params = params;
38
39         getContext().setReceiveTimeout(params.receiveTimeout);
40     }
41
42     @Override
43     public void onReceive(Object message) {
44         if (message instanceof CaptureSnapshotReply) {
45             Snapshot snapshot = Snapshot.create(
46                     ((CaptureSnapshotReply)message).getSnapshotState(),
47                     params.captureSnapshot.getUnAppliedEntries(),
48                     params.captureSnapshot.getLastIndex(), params.captureSnapshot.getLastTerm(),
49                     params.captureSnapshot.getLastAppliedIndex(), params.captureSnapshot.getLastAppliedTerm(),
50                     params.electionTerm.getCurrentTerm(), params.electionTerm.getVotedFor(),
51                     params.peerInformation);
52
53             LOG.debug("{}: Received CaptureSnapshotReply, sending {}", params.id, snapshot);
54
55             params.replyToActor.tell(new GetSnapshotReply(params.id, snapshot), getSelf());
56             getSelf().tell(PoisonPill.getInstance(), getSelf());
57         } else if (message instanceof ReceiveTimeout) {
58             LOG.warn("{}: Got ReceiveTimeout for inactivity - did not receive CaptureSnapshotReply within {} ms",
59                     params.id, params.receiveTimeout.toMillis());
60
61             params.replyToActor.tell(new akka.actor.Status.Failure(new TimeoutException(String.format(
62                     "Timed out after %d ms while waiting for CaptureSnapshotReply",
63                         params.receiveTimeout.toMillis()))), getSelf());
64             getSelf().tell(PoisonPill.getInstance(), getSelf());
65         }
66     }
67
68     public static Props props(CaptureSnapshot captureSnapshot, ElectionTerm electionTerm, ActorRef replyToActor,
69             Duration receiveTimeout, String id, ServerConfigurationPayload updatedPeerInfo) {
70         return Props.create(GetSnapshotReplyActor.class, new Params(captureSnapshot, electionTerm, replyToActor,
71                 receiveTimeout, id, updatedPeerInfo));
72     }
73
74     private static final class Params {
75         final CaptureSnapshot captureSnapshot;
76         final ActorRef replyToActor;
77         final ElectionTerm electionTerm;
78         final Duration receiveTimeout;
79         final String id;
80         final ServerConfigurationPayload peerInformation;
81
82         Params(CaptureSnapshot captureSnapshot, ElectionTerm electionTerm, ActorRef replyToActor,
83                 Duration receiveTimeout, String id, ServerConfigurationPayload peerInfo) {
84             this.captureSnapshot = Preconditions.checkNotNull(captureSnapshot);
85             this.electionTerm = Preconditions.checkNotNull(electionTerm);
86             this.replyToActor = Preconditions.checkNotNull(replyToActor);
87             this.receiveTimeout = Preconditions.checkNotNull(receiveTimeout);
88             this.id = Preconditions.checkNotNull(id);
89             this.peerInformation = peerInfo;
90         }
91     }
92 }