use of com.palantir.paxos.PaxosRoundFailureException in project atlasdb by palantir.
the class LeadershipEventRecorderTest method recordsProposalFailure.
@Test
public void recordsProposalFailure() {
PaxosRoundFailureException ex = new PaxosRoundFailureException("foo");
recorder.recordProposalFailure(ex);
verify(events).proposalFailure(ex);
}
use of com.palantir.paxos.PaxosRoundFailureException in project atlasdb by palantir.
the class PaxosTimestampBoundStore method storeUpperLimit.
/**
* Proposes a new timestamp limit, with sequence number 1 greater than the current agreed bound, or
* PaxosAcceptor.NO_LOG_ENTRY + 1 if nothing has been proposed or accepted yet.
*
* @param limit the new upper limit to be stored
* @throws IllegalArgumentException if trying to persist a limit smaller than the agreed limit
* @throws NotCurrentLeaderException if the timestamp limit has changed out from under us
*/
@Override
public synchronized void storeUpperLimit(long limit) throws MultipleRunningTimestampServiceError {
long newSeq = PaxosAcceptor.NO_LOG_ENTRY + 1;
if (agreedState != null) {
Preconditions.checkArgument(limit >= agreedState.getBound(), "Tried to store an upper limit %s less than the current limit %s", limit, agreedState.getBound());
newSeq = agreedState.getSeqId() + 1;
}
while (true) {
try {
proposer.propose(newSeq, PtBytes.toBytes(limit));
PaxosValue value = knowledge.getLearnedValue(newSeq);
checkAgreedBoundIsOurs(limit, newSeq, value);
long newLimit = PtBytes.toLong(value.getData());
agreedState = ImmutableSequenceAndBound.of(newSeq, newLimit);
if (newLimit < limit) {
// The bound is ours, but is not high enough.
// This is dangerous; proposing at the next sequence number is unsafe, as timestamp services
// generally assume they have the ALLOCATION_BUFFER_SIZE timestamps up to this.
// TODO (jkong): Devise a method that better preserves availability of the cluster.
log.warn("It appears we updated the timestamp limit to {}, which was less than our target {}." + " This suggests we have another timestamp service running; possibly because we" + " lost and regained leadership. For safety, we are now stopping this service.", SafeArg.of("newLimit", newLimit), SafeArg.of("target", limit));
throw new NotCurrentLeaderException(String.format("We updated the timestamp limit to %s, which was less than our target %s.", newLimit, limit));
}
return;
} catch (PaxosRoundFailureException e) {
waitForRandomBackoff(e, this::wait);
}
}
}
use of com.palantir.paxos.PaxosRoundFailureException in project atlasdb by palantir.
the class PaxosTransactionService method putUnlessExists.
@Override
public void putUnlessExists(long startTimestamp, long commitTimestamp) throws KeyAlreadyExistsException {
try {
byte[] finalValue = proposer.propose(startTimestamp, PtBytes.toBytes(commitTimestamp));
long finalCommitTs = PtBytes.toLong(finalValue);
try {
// Make sure we do this put before we return because we want #get to succeed.
kvStore.putAll(ImmutableMap.of(startTimestamp, finalCommitTs));
} catch (KeyAlreadyExistsException e) {
// this case isn't worrisome
}
if (commitTimestamp != finalCommitTs) {
throw new KeyAlreadyExistsException("Key " + startTimestamp + " already exists and is mapped to " + finalCommitTs);
}
} catch (PaxosRoundFailureException e) {
throw new ServiceNotAvailableException("Could not store trascaction");
}
}
Aggregations