use of com.aerospike.client.cluster.Partition in project aerospike-client-java by aerospike.
the class SyncCommand method execute.
// private static final AtomicLong TranCounter = new AtomicLong();
public final void execute(Cluster cluster, Policy policy, Key key, Node node, boolean isRead) {
// final long tranId = TranCounter.getAndIncrement();
final Partition partition = (key != null) ? new Partition(key) : null;
AerospikeException exception = null;
long deadline = 0;
int socketTimeout = policy.socketTimeout;
int totalTimeout = policy.totalTimeout;
int iteration = 0;
int commandSentCounter = 0;
boolean isClientTimeout;
if (totalTimeout > 0) {
deadline = System.nanoTime() + TimeUnit.MILLISECONDS.toNanos(totalTimeout);
if (socketTimeout > totalTimeout) {
socketTimeout = totalTimeout;
}
}
// Execute command until successful, timed out or maximum iterations have been reached.
while (true) {
try {
if (partition != null) {
// Single record command node retrieval.
node = getNode(cluster, partition, policy.replica, isRead);
// if (iteration > 0 && !isRead) {
// Log.info("Retry: " + tranId + ',' + node + ',' + sequence + ',' + iteration);
// }
}
Connection conn = node.getConnection(socketTimeout);
try {
// Set command buffer.
writeBuffer();
// Check if total timeout needs to be changed in send buffer.
if (totalTimeout != policy.totalTimeout) {
// Reset timeout in send buffer (destined for server) and socket.
Buffer.intToBytes(totalTimeout, dataBuffer, 22);
}
// Send command.
conn.write(dataBuffer, dataOffset);
commandSentCounter++;
// Parse results.
parseResult(conn);
// Put connection back in pool.
node.putConnection(conn);
// Command has completed successfully. Exit method.
return;
} catch (AerospikeException ae) {
if (ae.keepConnection()) {
// Put connection back in pool.
node.putConnection(conn);
} else {
// Close socket to flush out possible garbage. Do not put back in pool.
node.closeConnection(conn);
}
if (ae.getResultCode() == ResultCode.TIMEOUT) {
// Go through retry logic on server timeout.
// Log.info("Server timeout: " + tranId + ',' + node + ',' + sequence + ',' + iteration);
exception = new AerospikeException.Timeout(node, policy, iteration + 1, false);
isClientTimeout = false;
if (isRead) {
super.sequence++;
}
} else {
// Log.info("Throw AerospikeException: " + tranId + ',' + node + ',' + sequence + ',' + iteration + ',' + ae.getResultCode());
ae.setInDoubt(isRead, commandSentCounter);
throw ae;
}
} catch (RuntimeException re) {
// All runtime exceptions are considered fatal. Do not retry.
// Close socket to flush out possible garbage. Do not put back in pool.
// Log.info("Throw RuntimeException: " + tranId + ',' + node + ',' + sequence + ',' + iteration);
node.closeConnection(conn);
throw re;
} catch (SocketTimeoutException ste) {
// Full timeout has been reached.
// Log.info("Socket timeout: " + tranId + ',' + node + ',' + sequence + ',' + iteration);
node.closeConnection(conn);
isClientTimeout = true;
if (isRead) {
super.sequence++;
}
} catch (IOException ioe) {
// IO errors are considered temporary anomalies. Retry.
// Log.info("IOException: " + tranId + ',' + node + ',' + sequence + ',' + iteration);
node.closeConnection(conn);
exception = new AerospikeException(ioe);
isClientTimeout = false;
super.sequence++;
}
} catch (AerospikeException.Connection ce) {
// Socket connection error has occurred. Retry.
// Log.info("Connection error: " + tranId + ',' + node + ',' + sequence + ',' + iteration);
exception = ce;
isClientTimeout = false;
super.sequence++;
}
// Check maxRetries.
if (++iteration > policy.maxRetries) {
break;
}
if (policy.totalTimeout > 0) {
// Check for total timeout.
long remaining = deadline - System.nanoTime() - TimeUnit.MILLISECONDS.toNanos(policy.sleepBetweenRetries);
if (remaining <= 0) {
break;
}
// Convert back to milliseconds for remaining check.
remaining = TimeUnit.NANOSECONDS.toMillis(remaining);
if (remaining < totalTimeout) {
totalTimeout = (int) remaining;
if (socketTimeout > totalTimeout) {
socketTimeout = totalTimeout;
}
}
}
if (!isClientTimeout && policy.sleepBetweenRetries > 0) {
// Sleep before trying again.
Util.sleep(policy.sleepBetweenRetries);
}
}
// Retries have been exhausted. Throw last exception.
if (isClientTimeout) {
// Log.info("SocketTimeoutException: " + tranId + ',' + sequence + ',' + iteration);
exception = new AerospikeException.Timeout(node, policy, iteration, true);
}
// Log.info("Runtime exception: " + tranId + ',' + sequence + ',' + iteration + ',' + exception.getMessage());
exception.setInDoubt(isRead, commandSentCounter);
throw exception;
}
use of com.aerospike.client.cluster.Partition in project aerospike-client-java by aerospike.
the class BatchNode method generateList.
public static List<BatchNode> generateList(Cluster cluster, BatchPolicy policy, List<BatchRead> records) throws AerospikeException {
Node[] nodes = cluster.getNodes();
if (nodes.length == 0) {
throw new AerospikeException(ResultCode.SERVER_NOT_AVAILABLE, "Command failed because cluster is empty.");
}
// Create initial key capacity for each node as average + 25%.
int max = records.size();
int keysPerNode = max / nodes.length;
keysPerNode += keysPerNode >>> 2;
// The minimum key capacity is 10.
if (keysPerNode < 10) {
keysPerNode = 10;
}
// Split keys by server node.
List<BatchNode> batchNodes = new ArrayList<BatchNode>(nodes.length);
for (int i = 0; i < max; i++) {
Partition partition = new Partition(records.get(i).key);
Node node = cluster.getMasterNode(partition);
BatchNode batchNode = findBatchNode(batchNodes, node);
if (batchNode == null) {
batchNodes.add(new BatchNode(node, keysPerNode, i));
} else {
batchNode.addKey(i);
}
}
return batchNodes;
}
use of com.aerospike.client.cluster.Partition in project aerospike-client-java by aerospike.
the class BatchNode method generateList.
public static List<BatchNode> generateList(Cluster cluster, BatchPolicy policy, Key[] keys) throws AerospikeException {
Node[] nodes = cluster.getNodes();
if (nodes.length == 0) {
throw new AerospikeException(ResultCode.SERVER_NOT_AVAILABLE, "Command failed because cluster is empty.");
}
// Create initial key capacity for each node as average + 25%.
int keysPerNode = keys.length / nodes.length;
keysPerNode += keysPerNode >>> 2;
// The minimum key capacity is 10.
if (keysPerNode < 10) {
keysPerNode = 10;
}
// Split keys by server node.
List<BatchNode> batchNodes = new ArrayList<BatchNode>(nodes.length);
for (int i = 0; i < keys.length; i++) {
Partition partition = new Partition(keys[i]);
Node node = cluster.getMasterNode(partition);
BatchNode batchNode = findBatchNode(batchNodes, node);
if (batchNode == null) {
batchNodes.add(new BatchNode(node, keysPerNode, i));
} else {
batchNode.addKey(i);
}
}
return batchNodes;
}
Aggregations