Search in sources :

Example 1 with SnapshotInfo

use of org.apache.ratis.statemachine.SnapshotInfo in project incubator-ratis by apache.

the class LeaderElection method askForVotes.

/**
 * After a peer changes its role to candidate, it invokes this method to
 * send out requestVote rpc to all other peers.
 */
private void askForVotes() throws InterruptedException, IOException {
    final ServerState state = server.getState();
    while (running && server.isCandidate()) {
        // one round of requestVotes
        final long electionTerm;
        synchronized (server) {
            electionTerm = state.initElection();
            server.getState().persistMetadata();
        }
        LOG.info(state.getSelfId() + ": begin an election in Term " + electionTerm);
        TermIndex lastEntry = state.getLog().getLastEntryTermIndex();
        if (lastEntry == null) {
            // lastEntry may need to be derived from snapshot
            SnapshotInfo snapshot = state.getLatestSnapshot();
            if (snapshot != null) {
                lastEntry = snapshot.getTermIndex();
            }
        }
        final ResultAndTerm r;
        if (others.isEmpty()) {
            r = new ResultAndTerm(Result.PASSED, electionTerm);
        } else {
            try {
                initExecutor();
                int submitted = submitRequests(electionTerm, lastEntry);
                r = waitForResults(electionTerm, submitted);
            } finally {
                if (executor != null) {
                    executor.shutdown();
                }
            }
        }
        synchronized (server) {
            if (electionTerm != state.getCurrentTerm() || !running || !server.isCandidate()) {
                // term already passed or no longer a candidate.
                return;
            }
            switch(r.result) {
                case PASSED:
                    server.changeToLeader();
                    return;
                case SHUTDOWN:
                    LOG.info("{} received shutdown response when requesting votes.", server.getId());
                    server.getProxy().close();
                    return;
                case REJECTED:
                case DISCOVERED_A_NEW_TERM:
                    final long term = r.term > server.getState().getCurrentTerm() ? r.term : server.getState().getCurrentTerm();
                    server.changeToFollower(term, true);
                    return;
                case TIMEOUT:
            }
        }
    }
}
Also used : SnapshotInfo(org.apache.ratis.statemachine.SnapshotInfo) TermIndex(org.apache.ratis.server.protocol.TermIndex)

Example 2 with SnapshotInfo

use of org.apache.ratis.statemachine.SnapshotInfo in project incubator-ratis by apache.

the class ServerState method isLogUpToDate.

boolean isLogUpToDate(TermIndex candidateLastEntry) {
    TermIndex local = log.getLastEntryTermIndex();
    // need to take into account snapshot
    SnapshotInfo snapshot = server.getStateMachine().getLatestSnapshot();
    if (local == null && snapshot == null) {
        return true;
    } else if (candidateLastEntry == null) {
        return false;
    }
    if (local == null || (snapshot != null && snapshot.getIndex() > local.getIndex())) {
        local = snapshot.getTermIndex();
    }
    return local.compareTo(candidateLastEntry) <= 0;
}
Also used : SnapshotInfo(org.apache.ratis.statemachine.SnapshotInfo) TermIndex(org.apache.ratis.server.protocol.TermIndex)

Example 3 with SnapshotInfo

use of org.apache.ratis.statemachine.SnapshotInfo in project incubator-ratis by apache.

the class ServerState method initStatemachine.

private long initStatemachine(StateMachine sm, RaftProperties properties) throws IOException {
    sm.initialize(selfId, properties, storage);
    storage.setStateMachineStorage(sm.getStateMachineStorage());
    SnapshotInfo snapshot = sm.getLatestSnapshot();
    if (snapshot == null || snapshot.getTermIndex().getIndex() < 0) {
        return RaftServerConstants.INVALID_LOG_INDEX;
    }
    // get the raft configuration from the snapshot
    RaftConfiguration raftConf = sm.getRaftConfiguration();
    if (raftConf != null) {
        configurationManager.addConfiguration(raftConf.getLogEntryIndex(), raftConf);
    }
    return snapshot.getIndex();
}
Also used : SnapshotInfo(org.apache.ratis.statemachine.SnapshotInfo)

Example 4 with SnapshotInfo

use of org.apache.ratis.statemachine.SnapshotInfo in project incubator-ratis by apache.

the class StateMachineUpdater method run.

@Override
public void run() {
    final RaftStorage storage = server.getState().getStorage();
    while (isRunning()) {
        try {
            synchronized (this) {
                // Thus initially lastAppliedIndex can be greater than lastCommitted.
                while (lastAppliedIndex >= raftLog.getLastCommittedIndex()) {
                    wait();
                }
            }
            final long committedIndex = raftLog.getLastCommittedIndex();
            Preconditions.assertTrue(lastAppliedIndex < committedIndex);
            if (state == State.RELOAD) {
                Preconditions.assertTrue(stateMachine.getLifeCycleState() == LifeCycle.State.PAUSED);
                stateMachine.reinitialize(server.getId(), properties, storage);
                SnapshotInfo snapshot = stateMachine.getLatestSnapshot();
                Preconditions.assertTrue(snapshot != null && snapshot.getIndex() > lastAppliedIndex, "Snapshot: %s, lastAppliedIndex: %s", snapshot, lastAppliedIndex);
                lastAppliedIndex = snapshot.getIndex();
                lastSnapshotIndex = snapshot.getIndex();
                state = State.RUNNING;
            }
            final MemoizedSupplier<List<CompletableFuture<Message>>> futures = MemoizedSupplier.valueOf(() -> new ArrayList<>());
            while (lastAppliedIndex < committedIndex) {
                final long nextIndex = lastAppliedIndex + 1;
                final LogEntryProto next = raftLog.get(nextIndex);
                if (next != null) {
                    if (LOG.isDebugEnabled()) {
                        LOG.debug("{}: applying nextIndex={}, nextLog={}", this, nextIndex, ServerProtoUtils.toString(next));
                    }
                    final CompletableFuture<Message> f = server.applyLogToStateMachine(next);
                    if (f != null) {
                        futures.get().add(f);
                    }
                    lastAppliedIndex = nextIndex;
                } else {
                    LOG.debug("{}: logEntry {} is null. There may be snapshot to load. state:{}", this, nextIndex, state);
                    break;
                }
            }
            // check if need to trigger a snapshot
            if (shouldTakeSnapshot(lastAppliedIndex)) {
                if (futures.isInitialized()) {
                    JavaUtils.allOf(futures.get()).get();
                }
                stateMachine.takeSnapshot();
                // TODO purge logs, including log cache. but should keep log for leader's RPCSenders
                lastSnapshotIndex = lastAppliedIndex;
            }
        } catch (InterruptedException e) {
            if (!isRunning()) {
                LOG.info("{}: the StateMachineUpdater is interrupted and will exit.", this);
            } else {
                final String s = this + ": the StateMachineUpdater is wrongly interrupted";
                ExitUtils.terminate(1, s, e, LOG);
            }
        } catch (Throwable t) {
            final String s = this + ": the StateMachineUpdater hits Throwable";
            ExitUtils.terminate(2, s, t, LOG);
        }
    }
}
Also used : SnapshotInfo(org.apache.ratis.statemachine.SnapshotInfo) LogEntryProto(org.apache.ratis.shaded.proto.RaftProtos.LogEntryProto) RaftStorage(org.apache.ratis.server.storage.RaftStorage) Message(org.apache.ratis.protocol.Message) ArrayList(java.util.ArrayList) List(java.util.List)

Example 5 with SnapshotInfo

use of org.apache.ratis.statemachine.SnapshotInfo in project incubator-ratis by apache.

the class GRpcLogAppender method run.

@Override
public void run() {
    while (isAppenderRunning()) {
        if (shouldSendRequest()) {
            SnapshotInfo snapshot = shouldInstallSnapshot();
            if (snapshot != null) {
                installSnapshot(snapshot, snapshotResponseHandler);
            } else {
                // keep appending log entries or sending heartbeats
                try {
                    appendLog();
                } catch (RaftLogIOException e) {
                    LOG.error(this + " hit IOException while loading raft log", e);
                    stopSender();
                }
            }
        }
        if (isAppenderRunning() && !shouldSendRequest()) {
            // use lastSend time instead of lastResponse time
            final long waitTime = getHeartbeatRemainingTime(follower.getLastRpcTime());
            if (waitTime > 0) {
                synchronized (this) {
                    try {
                        LOG.debug("{} decides to wait {}ms before appending to {}", server.getId(), waitTime, follower.getPeer());
                        wait(waitTime);
                    } catch (InterruptedException ignored) {
                    }
                }
            }
        }
    }
    appendLogRequestObserver.onCompleted();
}
Also used : SnapshotInfo(org.apache.ratis.statemachine.SnapshotInfo) RaftLogIOException(org.apache.ratis.server.storage.RaftLogIOException)

Aggregations

SnapshotInfo (org.apache.ratis.statemachine.SnapshotInfo)12 TermIndex (org.apache.ratis.server.protocol.TermIndex)4 SingleFileSnapshotInfo (org.apache.ratis.statemachine.impl.SingleFileSnapshotInfo)4 NotFoundException (alluxio.exception.status.NotFoundException)2 File (java.io.File)2 FileNotFoundException (java.io.FileNotFoundException)2 IOException (java.io.IOException)2 AbortedException (alluxio.exception.status.AbortedException)1 AlluxioStatusException (alluxio.exception.status.AlluxioStatusException)1 DownloadSnapshotPRequest (alluxio.grpc.DownloadSnapshotPRequest)1 DownloadSnapshotPResponse (alluxio.grpc.DownloadSnapshotPResponse)1 JournalQueryResponse (alluxio.grpc.JournalQueryResponse)1 UploadSnapshotPRequest (alluxio.grpc.UploadSnapshotPRequest)1 UploadSnapshotPResponse (alluxio.grpc.UploadSnapshotPResponse)1 Timer (com.codahale.metrics.Timer)1 FileOutputStream (java.io.FileOutputStream)1 FileChannel (java.nio.channels.FileChannel)1 ArrayList (java.util.ArrayList)1 List (java.util.List)1 CompletionException (java.util.concurrent.CompletionException)1