Merge branch 'cassandra-4.0' into cassandra-4.1

This commit is contained in:
Ariel Weisberg 2024-08-21 16:01:58 -04:00
commit 02f38208b1
3 changed files with 71 additions and 8 deletions

View File

@ -6,6 +6,7 @@
* Reduce info logging from automatic paxos repair (CASSANDRA-19445)
* Support legacy plain_text_auth section in credentials file removed unintentionally (CASSANDRA-19498)
Merged from 4.0:
* Fix latency reported by ideal consistency level monitoring (CASSANDRA-19651)
* Use default commitlog settings in test YAMLs (CASSANDRA-19830)
* Do not spam log with SSLExceptions (CASSANDRA-18839)
* Fix schema.cql created by a snapshot after dropping more than one column (CASSANDRA-19747)

View File

@ -189,7 +189,7 @@ public abstract class AbstractWriteResponseHandler<T> implements RequestCallback
}
}
public final void expired()
protected final void logFailureOrTimeoutToIdealCLDelegate()
{
//Tracking ideal CL was not configured
if (idealCLDelegate == null)
@ -209,6 +209,11 @@ public abstract class AbstractWriteResponseHandler<T> implements RequestCallback
}
}
public final void expired()
{
logFailureOrTimeoutToIdealCLDelegate();
}
/**
* @return the minimum number of endpoints that must respond.
*/
@ -259,9 +264,13 @@ public abstract class AbstractWriteResponseHandler<T> implements RequestCallback
{
//The ideal CL should only count as a strike if the requested CL was achieved.
//If the requested CL is not achieved it's fine for the ideal CL to also not be achieved.
if (idealCLDelegate != null)
if (idealCLDelegate != null && blockFor() + failures <= candidateReplicaCount())
{
idealCLDelegate.requestedCLAchieved = true;
if (idealCLDelegate == this)
{
replicaPlan.keyspace().metric.idealCLWriteLatency.addNano(nanoTime() - requestTime.startedAtNanos());
}
}
condition.signalAll();
@ -280,6 +289,8 @@ public abstract class AbstractWriteResponseHandler<T> implements RequestCallback
failureReasonByEndpoint.put(from, failureReason);
logFailureOrTimeoutToIdealCLDelegate();
if (blockFor() + n > candidateReplicaCount())
signal();
@ -309,10 +320,6 @@ public abstract class AbstractWriteResponseHandler<T> implements RequestCallback
{
replicaPlan.keyspace().metric.writeFailedIdealCL.inc();
}
else
{
replicaPlan.keyspace().metric.idealCLWriteLatency.addNano(nanoTime() - requestTime.startedAtNanos());
}
}
}

View File

@ -26,6 +26,7 @@ import java.util.concurrent.TimeUnit;
import com.google.common.base.Predicates;
import org.apache.cassandra.dht.Murmur3Partitioner;
import org.apache.cassandra.exceptions.RequestFailureReason;
import org.apache.cassandra.locator.EndpointsForToken;
import org.apache.cassandra.locator.ReplicaPlans;
import org.junit.Before;
@ -153,17 +154,23 @@ public class WriteResponseHandlerTest
//dc1
awr.onResponse(createDummyMessage(0));
awr.onResponse(createDummyMessage(1));
// there are not enough responses for ideal EACH_QUORUM yet
assertEquals(startingCount, ks.metric.idealCLWriteLatency.latency.getCount());
//dc2
awr.onResponse(createDummyMessage(4));
awr.onResponse(createDummyMessage(5));
// there are enough responses for ideal EACH_QUORUM, we should not wait for all responses
assertTrue( TimeUnit.DAYS.toMicros(1) < ks.metric.idealCLWriteLatency.totalLatency.getCount());
assertEquals(startingCount + 1, ks.metric.idealCLWriteLatency.latency.getCount());
//Don't need the others
awr.expired();
awr.expired();
assertEquals(0, ks.metric.writeFailedIdealCL.getCount());
assertTrue( TimeUnit.DAYS.toMicros(1) < ks.metric.idealCLWriteLatency.totalLatency.getCount());
assertEquals(startingCount + 1, ks.metric.idealCLWriteLatency.latency.getCount());
}
/**
@ -235,6 +242,30 @@ public class WriteResponseHandlerTest
assertEquals(0, ks.metric.idealCLWriteLatency.totalLatency.getCount());
}
@Test
public void failedIdealCLIncrementsStatForExplicitOnFailure()
{
AbstractWriteResponseHandler awr = createWriteResponseHandler(ConsistencyLevel.LOCAL_QUORUM, ConsistencyLevel.EACH_QUORUM);
long startingCountForWriteFailedIdealCL = ks.metric.writeFailedIdealCL.getCount();
long startingCountForIdealCLWriteLatency = ks.metric.idealCLWriteLatency.totalLatency.getCount();
//Succeed in local DC
awr.onResponse(createDummyMessage(0));
awr.onResponse(createDummyMessage(1));
awr.onResponse(createDummyMessage(2));
//Fail in remote DC
awr.onFailure(targets.get(3).endpoint(), RequestFailureReason.TIMEOUT);
awr.onFailure(targets.get(4).endpoint(), RequestFailureReason.TIMEOUT);
awr.onResponse(createDummyMessage(5));
assertEquals(startingCountForWriteFailedIdealCL + 1, ks.metric.writeFailedIdealCL.getCount());
assertEquals(startingCountForIdealCLWriteLatency, ks.metric.idealCLWriteLatency.totalLatency.getCount());
}
/**
* Validate that failing to achieve ideal CL doesn't increase the failure counter when not meeting CL
* @throws Throwable
@ -260,6 +291,30 @@ public class WriteResponseHandlerTest
assertEquals(startingCount, ks.metric.writeFailedIdealCL.getCount());
}
@Test
public void failedIdealCLDoesNotIncrementsStatOnExplicitQueryFailure()
{
AbstractWriteResponseHandler awr = createWriteResponseHandler(ConsistencyLevel.LOCAL_QUORUM, ConsistencyLevel.EACH_QUORUM);
long startingCountForWriteFailedIdealCL = ks.metric.writeFailedIdealCL.getCount();
long startingCountForIdealCLWriteLatency = ks.metric.idealCLWriteLatency.totalLatency.getCount();
//Fail in local DC
awr.onFailure(targets.get(0).endpoint(), RequestFailureReason.TIMEOUT);
awr.onFailure(targets.get(1).endpoint(), RequestFailureReason.TIMEOUT);
awr.onResponse(createDummyMessage(2));
//Fail in remote DC
awr.onFailure(targets.get(3).endpoint(), RequestFailureReason.TIMEOUT);
awr.onFailure(targets.get(4).endpoint(), RequestFailureReason.TIMEOUT);
awr.onResponse(createDummyMessage(5));
assertEquals(startingCountForWriteFailedIdealCL, ks.metric.writeFailedIdealCL.getCount());
assertEquals(startingCountForIdealCLWriteLatency, ks.metric.idealCLWriteLatency.totalLatency.getCount());
}
private static AbstractWriteResponseHandler createWriteResponseHandler(ConsistencyLevel cl, ConsistencyLevel ideal)
{