use of com.ibm.etcd.client.FutureListener in project etcd-java by IBM.
the class PersistentLeaseKey method putKey.
// called only from our serialized executor context
protected void putKey(long leaseId) {
if (leaseId == 0L || closeFuture != null)
return;
if (updateFuture != null && !updateFuture.isDone()) {
// if the cancellation wins then putKey will be immediately retried
updateFuture.cancel(false);
return;
}
// execute a transaction which either sets the lease on an existing key
// or creates the key with the lease if it doesn't exist
PutRequest.Builder putBld = PutRequest.newBuilder().setKey(key).setLease(leaseId);
KvClient.FluentTxnRequest req = client.getKvClient().txnIf().exists(key).backoffRetry(() -> closeFuture == null && isActive());
ListenableFuture<? extends Object> fut;
ListenableFuture<TxnResponse> txnFut;
if (rangeCache == null) {
fut = txnFut = req.then().put(putBld.setIgnoreValue(true)).elseDo().put(putBld.setIgnoreValue(false).setValue(defaultValue)).async();
} else {
RangeRequest getOp = RangeRequest.newBuilder().setKey(key).build();
txnFut = req.then().put(putBld.setIgnoreValue(true)).get(getOp).elseDo().put(putBld.setIgnoreValue(false).setValue(defaultValue)).get(getOp).async();
fut = Futures.transform(txnFut, (Function<TxnResponse, Object>) tr -> rangeCache.offerUpdate(tr.getResponses(1).getResponseRange().getKvs(0), false));
}
if (!isDone())
fut = Futures.transform(fut, (Function<Object, Object>) r -> set(key));
// this callback is to trigger an immediate retry in case the attempt was cancelled by a more
// recent lease state change to active
Futures.addCallback(fut, (FutureListener<Object>) (v, t) -> {
if (t instanceof CancellationException && isActive())
putKey(leaseId);
}, executor);
updateFuture = fut;
}
Aggregations