use of org.apache.cassandra.locator.InetAddressAndPort in project cassandra by apache.
the class SystemKeyspace method getTransferredRanges.
public static synchronized Map<InetAddressAndPort, Set<Range<Token>>> getTransferredRanges(String description, String keyspace, IPartitioner partitioner) {
Map<InetAddressAndPort, Set<Range<Token>>> result = new HashMap<>();
String query = "SELECT * FROM system.%s WHERE operation = ? AND keyspace_name = ?";
UntypedResultSet rs = executeInternal(String.format(query, TRANSFERRED_RANGES_V2), description, keyspace);
for (UntypedResultSet.Row row : rs) {
InetAddress peerAddress = row.getInetAddress("peer");
int port = row.getInt("peer_port");
InetAddressAndPort peer = InetAddressAndPort.getByAddressOverrideDefaults(peerAddress, port);
Set<ByteBuffer> rawRanges = row.getSet("ranges", BytesType.instance);
Set<Range<Token>> ranges = Sets.newHashSetWithExpectedSize(rawRanges.size());
for (ByteBuffer rawRange : rawRanges) {
ranges.add(byteBufferToRange(rawRange, partitioner));
}
result.put(peer, ranges);
}
return ImmutableMap.copyOf(result);
}
use of org.apache.cassandra.locator.InetAddressAndPort in project cassandra by apache.
the class SystemKeyspace method loadDcRackInfo.
/**
* Return a map of IP addresses containing a map of dc and rack info
*/
public static Map<InetAddressAndPort, Map<String, String>> loadDcRackInfo() {
Map<InetAddressAndPort, Map<String, String>> result = new HashMap<>();
for (UntypedResultSet.Row row : executeInternal("SELECT peer, peer_port, data_center, rack from system." + PEERS_V2)) {
InetAddress address = row.getInetAddress("peer");
Integer port = row.getInt("peer_port");
InetAddressAndPort peer = InetAddressAndPort.getByAddressOverrideDefaults(address, port);
if (row.has("data_center") && row.has("rack")) {
Map<String, String> dcRack = new HashMap<>();
dcRack.put("data_center", row.getString("data_center"));
dcRack.put("rack", row.getString("rack"));
result.put(peer, dcRack);
}
}
return result;
}
use of org.apache.cassandra.locator.InetAddressAndPort in project cassandra by apache.
the class StorageProxy method submitHint.
public static Future<Void> submitHint(Mutation mutation, EndpointsForToken targets, AbstractWriteResponseHandler<IMutation> responseHandler) {
// hints should not be written for transient replicas
Replicas.assertFull(targets);
HintRunnable runnable = new HintRunnable(targets) {
public void runMayThrow() {
Set<InetAddressAndPort> validTargets = new HashSet<>(targets.size());
Set<UUID> hostIds = new HashSet<>(targets.size());
for (InetAddressAndPort target : targets.endpoints()) {
UUID hostId = StorageService.instance.getHostIdForEndpoint(target);
if (hostId != null) {
hostIds.add(hostId);
validTargets.add(target);
} else
logger.debug("Discarding hint for endpoint not part of ring: {}", target);
}
logger.trace("Adding hints for {}", validTargets);
HintsService.instance.write(hostIds, Hint.create(mutation, currentTimeMillis()));
validTargets.forEach(HintsService.instance.metrics::incrCreatedHints);
// Notify the handler only for CL == ANY
if (responseHandler != null && responseHandler.replicaPlan.consistencyLevel() == ConsistencyLevel.ANY)
responseHandler.onResponse(null);
}
};
return submitHint(runnable);
}
use of org.apache.cassandra.locator.InetAddressAndPort in project cassandra by apache.
the class StorageProxy method describeSchemaVersions.
/**
* initiate a request/response session with each live node to check whether or not everybody is using the same
* migration id. This is useful for determining if a schema change has propagated through the cluster. Disagreement
* is assumed if any node fails to respond.
*/
public static Map<String, List<String>> describeSchemaVersions(boolean withPort) {
final String myVersion = Schema.instance.getVersion().toString();
final Map<InetAddressAndPort, UUID> versions = new ConcurrentHashMap<>();
final Set<InetAddressAndPort> liveHosts = Gossiper.instance.getLiveMembers();
final CountDownLatch latch = newCountDownLatch(liveHosts.size());
RequestCallback<UUID> cb = message -> {
// record the response from the remote node.
versions.put(message.from(), message.payload);
latch.decrement();
};
// an empty message acts as a request to the SchemaVersionVerbHandler.
Message message = out(SCHEMA_VERSION_REQ, noPayload);
for (InetAddressAndPort endpoint : liveHosts) MessagingService.instance().sendWithCallback(message, endpoint, cb);
try {
// wait for as long as possible. timeout-1s if possible.
latch.await(DatabaseDescriptor.getRpcTimeout(NANOSECONDS), NANOSECONDS);
} catch (InterruptedException e) {
throw new UncheckedInterruptedException(e);
}
// maps versions to hosts that are on that version.
Map<String, List<String>> results = new HashMap<String, List<String>>();
Iterable<InetAddressAndPort> allHosts = concat(Gossiper.instance.getLiveMembers(), Gossiper.instance.getUnreachableMembers());
for (InetAddressAndPort host : allHosts) {
UUID version = versions.get(host);
String stringVersion = version == null ? UNREACHABLE : version.toString();
List<String> hosts = results.get(stringVersion);
if (hosts == null) {
hosts = new ArrayList<String>();
results.put(stringVersion, hosts);
}
hosts.add(host.getHostAddress(withPort));
}
// we're done: the results map is ready to return to the client. the rest is just debug logging:
if (results.get(UNREACHABLE) != null)
logger.debug("Hosts not in agreement. Didn't get a response from everybody: {}", join(results.get(UNREACHABLE), ","));
for (Map.Entry<String, List<String>> entry : results.entrySet()) {
// check for version disagreement. log the hosts that don't agree.
if (entry.getKey().equals(UNREACHABLE) || entry.getKey().equals(myVersion))
continue;
for (String host : entry.getValue()) logger.debug("{} disagrees ({})", host, entry.getKey());
}
if (results.size() == 1)
logger.debug("Schemas are in agreement.");
return results;
}
use of org.apache.cassandra.locator.InetAddressAndPort in project cassandra by apache.
the class StorageProxy method sendToHintedReplicas.
/**
* Send the mutations to the right targets, write it locally if it corresponds or writes a hint when the node
* is not available.
*
* Note about hints:
* <pre>
* {@code
* | Hinted Handoff | Consist. Level |
* | on | >=1 | --> wait for hints. We DO NOT notify the handler with handler.response() for hints;
* | on | ANY | --> wait for hints. Responses count towards consistency.
* | off | >=1 | --> DO NOT fire hints. And DO NOT wait for them to complete.
* | off | ANY | --> DO NOT fire hints. And DO NOT wait for them to complete.
* }
* </pre>
*
* @throws OverloadedException if the hints cannot be written/enqueued
*/
public static void sendToHintedReplicas(final Mutation mutation, ReplicaPlan.ForTokenWrite plan, AbstractWriteResponseHandler<IMutation> responseHandler, String localDataCenter, Stage stage) throws OverloadedException {
// this dc replicas:
Collection<Replica> localDc = null;
// extra-datacenter replicas, grouped by dc
Map<String, Collection<Replica>> dcGroups = null;
// only need to create a Message for non-local writes
Message<Mutation> message = null;
boolean insertLocal = false;
Replica localReplica = null;
Collection<Replica> endpointsToHint = null;
List<InetAddressAndPort> backPressureHosts = null;
for (Replica destination : plan.contacts()) {
checkHintOverload(destination);
if (plan.isAlive(destination)) {
if (destination.isSelf()) {
insertLocal = true;
localReplica = destination;
} else {
// belongs on a different server
if (message == null)
message = Message.outWithFlag(MUTATION_REQ, mutation, MessageFlag.CALL_BACK_ON_FAILURE);
String dc = DatabaseDescriptor.getEndpointSnitch().getDatacenter(destination);
// (1.1 knows how to forward old-style String message IDs; updated to int in 2.0)
if (localDataCenter.equals(dc)) {
if (localDc == null)
localDc = new ArrayList<>(plan.contacts().size());
localDc.add(destination);
} else {
if (dcGroups == null)
dcGroups = new HashMap<>();
Collection<Replica> messages = dcGroups.get(dc);
if (messages == null)
// most DCs will have <= 3 replicas
messages = dcGroups.computeIfAbsent(dc, (v) -> new ArrayList<>(3));
messages.add(destination);
}
if (backPressureHosts == null)
backPressureHosts = new ArrayList<>(plan.contacts().size());
backPressureHosts.add(destination.endpoint());
}
} else {
// Immediately mark the response as expired since the request will not be sent
responseHandler.expired();
if (shouldHint(destination)) {
if (endpointsToHint == null)
endpointsToHint = new ArrayList<>();
endpointsToHint.add(destination);
}
}
}
if (endpointsToHint != null)
submitHint(mutation, EndpointsForToken.copyOf(mutation.key().getToken(), endpointsToHint), responseHandler);
if (insertLocal) {
Preconditions.checkNotNull(localReplica);
performLocally(stage, localReplica, mutation::apply, responseHandler);
}
if (localDc != null) {
for (Replica destination : localDc) MessagingService.instance().sendWriteWithCallback(message, destination, responseHandler, true);
}
if (dcGroups != null) {
// for each datacenter, send the message to one node to relay the write to other replicas
for (Collection<Replica> dcTargets : dcGroups.values()) sendMessagesToNonlocalDC(message, EndpointsForToken.copyOf(mutation.key().getToken(), dcTargets), responseHandler);
}
}
Aggregations