This is an automated email from the ASF dual-hosted git repository. aweisberg pushed a commit to branch cep-15-accord in repository https://gitbox.apache.org/repos/asf/cassandra.git
commit a59536f105fea338d474299cd19bfbc6bb348600 Author: Caleb Rackliffe <[email protected]> AuthorDate: Fri Sep 27 14:07:24 2024 -0500 Use SinglePartitionReadCommand for index queries that use strict filtering patch by Caleb Rackliffe; reviewed by Ariel Weisberg for CASSANDRA-19968 --- .../cassandra/cql3/statements/SelectStatement.java | 31 +++++++----- .../cassandra/db/PartitionRangeReadCommand.java | 9 +--- .../cassandra/db/PartitionRangeReadQuery.java | 2 - src/java/org/apache/cassandra/db/ReadCommand.java | 13 ++++- src/java/org/apache/cassandra/db/ReadQuery.java | 9 +++- .../cassandra/db/SinglePartitionReadCommand.java | 19 ++++--- .../cassandra/db/SinglePartitionReadQuery.java | 7 +++ .../index/internal/CassandraIndexSearcher.java | 59 ++++++++++++++++------ .../cassandra/index/sai/plan/QueryController.java | 8 +-- .../cassandra/index/sasi/plan/QueryController.java | 6 +-- .../index/sasi/plan/SASIIndexSearcher.java | 2 +- .../org/apache/cassandra/utils/btree/BTreeSet.java | 8 ++- .../db/AbstractReadQueryToCQLStringTest.java | 19 +++---- .../db/ReadCommandVerbHandlerOutOfRangeTest.java | 3 +- .../cassandra/db/ReadCommandVerbHandlerTest.java | 3 +- .../org/apache/cassandra/db/ReadResponseTest.java | 3 +- .../cassandra/service/reads/ReadExecutorTest.java | 2 +- .../reads/repair/RepairedDataVerifierTest.java | 3 +- 18 files changed, 131 insertions(+), 75 deletions(-) diff --git a/src/java/org/apache/cassandra/cql3/statements/SelectStatement.java b/src/java/org/apache/cassandra/cql3/statements/SelectStatement.java index fea826d0ac..66a4797637 100644 --- a/src/java/org/apache/cassandra/cql3/statements/SelectStatement.java +++ b/src/java/org/apache/cassandra/cql3/statements/SelectStatement.java @@ -453,19 +453,21 @@ public class SelectStatement implements CQLStatement.SingleKeyspaceCqlStatement, long nowInSec, DataLimits limit) { - boolean isPartitionRangeQuery = isPartitionRangeQuery(); + RowFilter rowFilter = getRowFilter(options, state); - if (isPartitionRangeQuery) + if (restrictions.isKeyRange()) { - if (restrictions.isKeyRange() && restrictions.usesSecondaryIndexing() && !SchemaConstants.isLocalSystemKeyspace(table.keyspace)) + if (restrictions.usesSecondaryIndexing() && !SchemaConstants.isLocalSystemKeyspace(table.keyspace)) Guardrails.nonPartitionRestrictedIndexQueryEnabled.ensureEnabled(state); - return getRangeCommand(options, state, columnFilter, limit, nowInSec); + return getRangeCommand(options, state, columnFilter, rowFilter, limit, nowInSec); } - return getSliceCommands(options, state, columnFilter, limit, nowInSec); - } + if (restrictions.usesSecondaryIndexing() && !rowFilter.isStrict()) + return getRangeCommand(options, state, columnFilter, rowFilter, limit, nowInSec); + return getSliceCommands(options, state, columnFilter, rowFilter, limit, nowInSec); + } private ResultMessage.Rows execute(ReadQuery query, QueryOptions options, ClientState state, @@ -768,7 +770,7 @@ public class SelectStatement implements CQLStatement.SingleKeyspaceCqlStatement, } private ReadQuery getSliceCommands(QueryOptions options, ClientState state, ColumnFilter columnFilter, - DataLimits limit, long nowInSec) + RowFilter rowFilter, DataLimits limit, long nowInSec) { Collection<ByteBuffer> keys = restrictions.getPartitionKeys(options, state); if (keys.isEmpty()) @@ -783,8 +785,6 @@ public class SelectStatement implements CQLStatement.SingleKeyspaceCqlStatement, if (filter == null || filter.isEmpty(table.comparator)) return ReadQuery.empty(table); - RowFilter rowFilter = getRowFilter(options, state); - List<DecoratedKey> decoratedKeys = new ArrayList<>(keys.size()); for (ByteBuffer key : keys) { @@ -792,7 +792,13 @@ public class SelectStatement implements CQLStatement.SingleKeyspaceCqlStatement, decoratedKeys.add(table.partitioner.decorateKey(ByteBufferUtil.clone(key))); } - return SinglePartitionReadQuery.createGroup(table, nowInSec, columnFilter, rowFilter, limit, decoratedKeys, filter); + SinglePartitionReadQuery.Group<? extends SinglePartitionReadQuery> group = + SinglePartitionReadQuery.createGroup(table, nowInSec, columnFilter, rowFilter, limit, decoratedKeys, filter); + + // If there's a secondary index that the commands can use, have it validate the request parameters. + group.maybeValidateIndex(); + + return group; } /** @@ -840,14 +846,13 @@ public class SelectStatement implements CQLStatement.SingleKeyspaceCqlStatement, return getRowFilter(QueryOptions.forInternalCalls(Collections.emptyList()), ClientState.forInternalCalls()); } - private ReadQuery getRangeCommand(QueryOptions options, ClientState state, ColumnFilter columnFilter, DataLimits limit, long nowInSec) + private ReadQuery getRangeCommand(QueryOptions options, ClientState state, ColumnFilter columnFilter, + RowFilter rowFilter, DataLimits limit, long nowInSec) { ClusteringIndexFilter clusteringIndexFilter = makeClusteringIndexFilter(options, state, columnFilter); if (clusteringIndexFilter == null) return ReadQuery.empty(table); - RowFilter rowFilter = getRowFilter(options, state); - // The LIMIT provided by the user is the number of CQL row he wants returned. // We want to have getRangeSlice to count the number of columns, not the number of keys. AbstractBounds<PartitionPosition> keyBounds = restrictions.getPartitionKeyBounds(options); diff --git a/src/java/org/apache/cassandra/db/PartitionRangeReadCommand.java b/src/java/org/apache/cassandra/db/PartitionRangeReadCommand.java index fccdc9e447..fb2888e13a 100644 --- a/src/java/org/apache/cassandra/db/PartitionRangeReadCommand.java +++ b/src/java/org/apache/cassandra/db/PartitionRangeReadCommand.java @@ -64,7 +64,6 @@ public class PartitionRangeReadCommand extends ReadCommand implements PartitionR { protected static final SelectionDeserializer selectionDeserializer = new Deserializer(); - protected final DataRange dataRange; protected final Slices requestedSlices; @VisibleForTesting @@ -82,8 +81,7 @@ public class PartitionRangeReadCommand extends ReadCommand implements PartitionR Index.QueryPlan indexQueryPlan, boolean trackWarnings) { - super(serializedAtEpoch, Kind.PARTITION_RANGE, isDigest, digestVersion, acceptsTransient, allowOutOfRangeReads, metadata, nowInSec, columnFilter, rowFilter, limits, indexQueryPlan, trackWarnings); - this.dataRange = dataRange; + super(serializedAtEpoch, Kind.PARTITION_RANGE, isDigest, digestVersion, acceptsTransient, allowOutOfRangeReads, metadata, nowInSec, columnFilter, rowFilter, limits, indexQueryPlan, trackWarnings, dataRange); this.requestedSlices = dataRange.clusteringIndexFilter.getSlices(metadata()); } @@ -177,11 +175,6 @@ public class PartitionRangeReadCommand extends ReadCommand implements PartitionR false); } - public DataRange dataRange() - { - return dataRange; - } - public ClusteringIndexFilter clusteringIndexFilter(DecoratedKey key) { return dataRange.clusteringIndexFilter(key); diff --git a/src/java/org/apache/cassandra/db/PartitionRangeReadQuery.java b/src/java/org/apache/cassandra/db/PartitionRangeReadQuery.java index d48277d41f..d91930125d 100644 --- a/src/java/org/apache/cassandra/db/PartitionRangeReadQuery.java +++ b/src/java/org/apache/cassandra/db/PartitionRangeReadQuery.java @@ -41,8 +41,6 @@ public interface PartitionRangeReadQuery extends ReadQuery return PartitionRangeReadCommand.create(table, nowInSec, columnFilter, rowFilter, limits, dataRange); } - DataRange dataRange(); - /** * Creates a new {@code PartitionRangeReadQuery} with the updated limits. * diff --git a/src/java/org/apache/cassandra/db/ReadCommand.java b/src/java/org/apache/cassandra/db/ReadCommand.java index 34069df1c4..9c0bfe7e8b 100644 --- a/src/java/org/apache/cassandra/db/ReadCommand.java +++ b/src/java/org/apache/cassandra/db/ReadCommand.java @@ -130,6 +130,8 @@ public abstract class ReadCommand extends AbstractReadQuery private boolean trackWarnings; + protected final DataRange dataRange; + @Nullable private final Index.QueryPlan indexQueryPlan; @@ -175,7 +177,8 @@ public abstract class ReadCommand extends AbstractReadQuery RowFilter rowFilter, DataLimits limits, Index.QueryPlan indexQueryPlan, - boolean trackWarnings) + boolean trackWarnings, + DataRange dataRange) { super(metadata, nowInSec, columnFilter, rowFilter, limits); if (acceptsTransient && isDigestQuery) @@ -189,6 +192,7 @@ public abstract class ReadCommand extends AbstractReadQuery this.allowsOutOfRangeReads = allowsOutOfRangeReads; this.trackWarnings = trackWarnings; this.serializedAtEpoch = serializedAtEpoch; + this.dataRange = dataRange; } public static ReadCommand getCommand() @@ -319,6 +323,12 @@ public abstract class ReadCommand extends AbstractReadQuery */ public abstract ClusteringIndexFilter clusteringIndexFilter(DecoratedKey key); + @Override + public DataRange dataRange() + { + return dataRange; + } + /** * Returns a copy of this command. * @@ -423,6 +433,7 @@ public abstract class ReadCommand extends AbstractReadQuery * validation method to check that nothing in this command's parameters * violates the implementation specific validation rules. */ + @Override public void maybeValidateIndex() { if (null != indexQueryPlan) diff --git a/src/java/org/apache/cassandra/db/ReadQuery.java b/src/java/org/apache/cassandra/db/ReadQuery.java index 798e0bc7d4..ee383b9631 100644 --- a/src/java/org/apache/cassandra/db/ReadQuery.java +++ b/src/java/org/apache/cassandra/db/ReadQuery.java @@ -126,10 +126,15 @@ public interface ReadQuery */ public TableMetadata metadata(); + default DataRange dataRange() + { + throw new UnsupportedOperationException("dataRange() must be implemented by implementation class"); + } + /** * Starts a new read operation. * <p> - * This must be called before {@link executeInternal} and passed to it to protect the read. + * This must be called before {@link #executeInternal} and passed to it to protect the read. * The returned object <b>must</b> be closed on all path and it is thus strongly advised to * use it in a try-with-ressource construction. * @@ -142,7 +147,7 @@ public interface ReadQuery * * @param consistency the consistency level to achieve for the query. * @param state client state - * @param state request enqueue / and start times + * @param requestTime request enqueue / and start times * @return the result of the query. */ public PartitionIterator execute(ConsistencyLevel consistency, ClientState state, Dispatcher.RequestTime requestTime) throws RequestExecutionException; diff --git a/src/java/org/apache/cassandra/db/SinglePartitionReadCommand.java b/src/java/org/apache/cassandra/db/SinglePartitionReadCommand.java index 91c85486aa..ea770b812f 100644 --- a/src/java/org/apache/cassandra/db/SinglePartitionReadCommand.java +++ b/src/java/org/apache/cassandra/db/SinglePartitionReadCommand.java @@ -63,6 +63,7 @@ import org.apache.cassandra.db.transform.RTBoundValidator; import org.apache.cassandra.db.transform.Transformation; import org.apache.cassandra.db.virtual.VirtualKeyspaceRegistry; import org.apache.cassandra.db.virtual.VirtualTable; +import org.apache.cassandra.dht.Bounds; import org.apache.cassandra.exceptions.RequestExecutionException; import org.apache.cassandra.index.Index; import org.apache.cassandra.io.sstable.SSTableReadsListener; @@ -106,9 +107,10 @@ public class SinglePartitionReadCommand extends ReadCommand implements SinglePar DecoratedKey partitionKey, ClusteringIndexFilter clusteringIndexFilter, Index.QueryPlan indexQueryPlan, - boolean trackWarnings) + boolean trackWarnings, + DataRange dataRange) { - super(serializedAtEpoch, Kind.SINGLE_PARTITION, isDigest, digestVersion, acceptsTransient, allowsOutOfRangeReads, metadata, nowInSec, columnFilter, rowFilter, limits, indexQueryPlan, trackWarnings); + super(serializedAtEpoch, Kind.SINGLE_PARTITION, isDigest, digestVersion, acceptsTransient, allowsOutOfRangeReads, metadata, nowInSec, columnFilter, rowFilter, limits, indexQueryPlan, trackWarnings, dataRange); assert partitionKey.getPartitioner() == metadata.partitioner; this.partitionKey = partitionKey; this.clusteringIndexFilter = clusteringIndexFilter; @@ -129,6 +131,8 @@ public class SinglePartitionReadCommand extends ReadCommand implements SinglePar Index.QueryPlan indexQueryPlan, boolean trackWarnings) { + DataRange dataRange = new DataRange(new Bounds<>(partitionKey, partitionKey), clusteringIndexFilter); + if (metadata.isVirtual()) { return new VirtualTableSinglePartitionReadCommand(isDigest, @@ -142,7 +146,8 @@ public class SinglePartitionReadCommand extends ReadCommand implements SinglePar partitionKey, clusteringIndexFilter, indexQueryPlan, - trackWarnings); + trackWarnings, + dataRange); } return new SinglePartitionReadCommand(serializedAtEpoch, isDigest, @@ -157,7 +162,8 @@ public class SinglePartitionReadCommand extends ReadCommand implements SinglePar partitionKey, clusteringIndexFilter, indexQueryPlan, - trackWarnings); + trackWarnings, + dataRange); } /** @@ -1400,9 +1406,10 @@ public class SinglePartitionReadCommand extends ReadCommand implements SinglePar DecoratedKey partitionKey, ClusteringIndexFilter clusteringIndexFilter, Index.QueryPlan indexQueryPlan, - boolean trackWarnings) + boolean trackWarnings, + DataRange dataRange) { - super(metadata.epoch, isDigest, digestVersion, true, acceptsTransient, metadata, nowInSec, columnFilter, rowFilter, limits, partitionKey, clusteringIndexFilter, indexQueryPlan, trackWarnings); + super(metadata.epoch, isDigest, digestVersion, true, acceptsTransient, metadata, nowInSec, columnFilter, rowFilter, limits, partitionKey, clusteringIndexFilter, indexQueryPlan, trackWarnings, dataRange); } @Override diff --git a/src/java/org/apache/cassandra/db/SinglePartitionReadQuery.java b/src/java/org/apache/cassandra/db/SinglePartitionReadQuery.java index 5d65c7307a..5409cde8c4 100644 --- a/src/java/org/apache/cassandra/db/SinglePartitionReadQuery.java +++ b/src/java/org/apache/cassandra/db/SinglePartitionReadQuery.java @@ -176,6 +176,13 @@ public interface SinglePartitionReadQuery extends ReadQuery assert queries.get(i).nowInSec() == nowInSec; } + @Override + public void maybeValidateIndex() + { + for (ReadQuery query : queries) + query.maybeValidateIndex(); + } + public long nowInSec() { return nowInSec; diff --git a/src/java/org/apache/cassandra/index/internal/CassandraIndexSearcher.java b/src/java/org/apache/cassandra/index/internal/CassandraIndexSearcher.java index 55bbab65b2..61d446674e 100644 --- a/src/java/org/apache/cassandra/index/internal/CassandraIndexSearcher.java +++ b/src/java/org/apache/cassandra/index/internal/CassandraIndexSearcher.java @@ -21,20 +21,36 @@ package org.apache.cassandra.index.internal; import java.nio.ByteBuffer; -import java.util.NavigableSet; +import java.util.SortedSet; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import org.apache.cassandra.schema.TableMetadata; -import org.apache.cassandra.db.*; -import org.apache.cassandra.db.filter.*; +import org.apache.cassandra.db.BufferClusteringBound; +import org.apache.cassandra.db.Clustering; +import org.apache.cassandra.db.ClusteringBound; +import org.apache.cassandra.db.ColumnFamilyStore; +import org.apache.cassandra.db.DataRange; +import org.apache.cassandra.db.DecoratedKey; +import org.apache.cassandra.db.PartitionPosition; +import org.apache.cassandra.db.ReadCommand; +import org.apache.cassandra.db.ReadExecutionController; +import org.apache.cassandra.db.SinglePartitionReadCommand; +import org.apache.cassandra.db.Slice; +import org.apache.cassandra.db.Slices; +import org.apache.cassandra.db.filter.ClusteringIndexFilter; +import org.apache.cassandra.db.filter.ClusteringIndexNamesFilter; +import org.apache.cassandra.db.filter.ClusteringIndexSliceFilter; +import org.apache.cassandra.db.filter.ColumnFilter; +import org.apache.cassandra.db.filter.RowFilter; import org.apache.cassandra.db.partitions.UnfilteredPartitionIterator; import org.apache.cassandra.db.rows.RowIterator; import org.apache.cassandra.db.rows.UnfilteredRowIterator; import org.apache.cassandra.db.rows.UnfilteredRowIterators; import org.apache.cassandra.dht.AbstractBounds; import org.apache.cassandra.index.Index; +import org.apache.cassandra.index.internal.composites.CollectionValueIndex; +import org.apache.cassandra.schema.TableMetadata; import org.apache.cassandra.utils.btree.BTreeSet; public abstract class CassandraIndexSearcher implements Index.Searcher @@ -90,17 +106,33 @@ public abstract class CassandraIndexSearcher implements Index.Searcher { if (command instanceof SinglePartitionReadCommand) { - // Note: as yet there's no route to get here - a 2i query *always* uses a - // PartitionRangeReadCommand. This is here in preparation for coming changes - // in SelectStatement. SinglePartitionReadCommand sprc = (SinglePartitionReadCommand)command; ByteBuffer pk = sprc.partitionKey().getKey(); ClusteringIndexFilter filter = sprc.clusteringIndexFilter(); if (filter instanceof ClusteringIndexNamesFilter) { - NavigableSet<Clustering<?>> requested = ((ClusteringIndexNamesFilter)filter).requestedRows(); - BTreeSet<Clustering<?>> clusterings = BTreeSet.copy(requested, index.getIndexComparator()); + if (index instanceof CollectionValueIndex) + { + // Collection value indexes have an extra clustering key for the path, but we cannot construct an + // index names filter from the filter on the backing table, because it has no path information. + // Instead, we construct a slice from the clustering keys that are provided. + Slices slices = filter.getSlices(index.baseCfs.metadata()); + ClusteringBound<?> start = BufferClusteringBound.BOTTOM; + ClusteringBound<?> end = BufferClusteringBound.TOP; + + if (slices.size() > 0) + start = slices.get(0).start(); + if (slices.size() > 0) + end = slices.get(slices.size() - 1).end(); + + Slice slice = Slice.make(makeIndexBound(pk, start), makeIndexBound(pk, end)); + return new ClusteringIndexSliceFilter(Slices.with(index.getIndexComparator(), slice), filter.isReversed()); + } + + SortedSet<Clustering<?>> requested = ((ClusteringIndexNamesFilter) filter).requestedRows(); + // The partition key from the base table must be the first element of al clusterings of the index table. + BTreeSet<Clustering<?>> clusterings = BTreeSet.copy(requested, index.getIndexComparator(), clustering -> makeIndexClustering(pk, clustering)); return new ClusteringIndexNamesFilter(clusterings, filter.isReversed()); } else @@ -114,8 +146,7 @@ public abstract class CassandraIndexSearcher implements Index.Searcher } else { - - DataRange dataRange = ((PartitionRangeReadCommand)command).dataRange(); + DataRange dataRange = command.dataRange(); AbstractBounds<PartitionPosition> range = dataRange.keyRange(); Slice slice = Slice.ALL; @@ -145,10 +176,8 @@ public abstract class CassandraIndexSearcher implements Index.Searcher */ if (!dataRange.isNamesQuery() && !index.indexedColumn.isStatic()) { - ClusteringIndexSliceFilter startSliceFilter = ((ClusteringIndexSliceFilter) dataRange.clusteringIndexFilter( - startKey)); - ClusteringIndexSliceFilter endSliceFilter = ((ClusteringIndexSliceFilter) dataRange.clusteringIndexFilter( - endKey)); + ClusteringIndexSliceFilter startSliceFilter = ((ClusteringIndexSliceFilter) dataRange.clusteringIndexFilter(startKey)); + ClusteringIndexSliceFilter endSliceFilter = ((ClusteringIndexSliceFilter) dataRange.clusteringIndexFilter(endKey)); // We can't effectively support reversed queries when we have a range, so we don't support it // (or through post-query reordering) and shouldn't get there. diff --git a/src/java/org/apache/cassandra/index/sai/plan/QueryController.java b/src/java/org/apache/cassandra/index/sai/plan/QueryController.java index 7b9b91c526..4f8efb8248 100644 --- a/src/java/org/apache/cassandra/index/sai/plan/QueryController.java +++ b/src/java/org/apache/cassandra/index/sai/plan/QueryController.java @@ -48,7 +48,6 @@ import org.apache.cassandra.db.guardrails.Guardrails; import org.apache.cassandra.db.rows.Row; import org.apache.cassandra.db.rows.UnfilteredRowIterator; import org.apache.cassandra.dht.AbstractBounds; -import org.apache.cassandra.dht.Range; import org.apache.cassandra.index.sai.QueryContext; import org.apache.cassandra.index.sai.StorageAttachedIndex; import org.apache.cassandra.index.sai.VectorQueryContext; @@ -437,14 +436,11 @@ public class QueryController { if (command instanceof SinglePartitionReadCommand) { - SinglePartitionReadCommand cmd = (SinglePartitionReadCommand) command; - DecoratedKey key = cmd.partitionKey(); - return Lists.newArrayList(new DataRange(new Range<>(key, key), cmd.clusteringIndexFilter())); + return Lists.newArrayList(command.dataRange()); } else if (command instanceof PartitionRangeReadCommand) { - PartitionRangeReadCommand cmd = (PartitionRangeReadCommand) command; - return Lists.newArrayList(cmd.dataRange()); + return Lists.newArrayList(command.dataRange()); } else { diff --git a/src/java/org/apache/cassandra/index/sasi/plan/QueryController.java b/src/java/org/apache/cassandra/index/sasi/plan/QueryController.java index 15865570ce..432dd80677 100644 --- a/src/java/org/apache/cassandra/index/sasi/plan/QueryController.java +++ b/src/java/org/apache/cassandra/index/sasi/plan/QueryController.java @@ -27,7 +27,7 @@ import com.google.common.collect.Sets; import org.apache.cassandra.db.ColumnFamilyStore; import org.apache.cassandra.db.DataRange; import org.apache.cassandra.db.DecoratedKey; -import org.apache.cassandra.db.PartitionRangeReadCommand; +import org.apache.cassandra.db.ReadCommand; import org.apache.cassandra.db.ReadExecutionController; import org.apache.cassandra.db.SinglePartitionReadCommand; import org.apache.cassandra.db.filter.DataLimits; @@ -58,11 +58,11 @@ public class QueryController private final long executionStart; private final ColumnFamilyStore cfs; - private final PartitionRangeReadCommand command; + private final ReadCommand command; private final DataRange range; private final Map<Collection<Expression>, List<RangeIterator<Long, Token>>> resources = new HashMap<>(); - public QueryController(ColumnFamilyStore cfs, PartitionRangeReadCommand command, long timeQuotaMs) + public QueryController(ColumnFamilyStore cfs, ReadCommand command, long timeQuotaMs) { this.cfs = cfs; this.command = command; diff --git a/src/java/org/apache/cassandra/index/sasi/plan/SASIIndexSearcher.java b/src/java/org/apache/cassandra/index/sasi/plan/SASIIndexSearcher.java index 10d2aab5c4..6da4f8a969 100644 --- a/src/java/org/apache/cassandra/index/sasi/plan/SASIIndexSearcher.java +++ b/src/java/org/apache/cassandra/index/sasi/plan/SASIIndexSearcher.java @@ -38,7 +38,7 @@ public class SASIIndexSearcher implements Index.Searcher public SASIIndexSearcher(ColumnFamilyStore cfs, ReadCommand command, long executionQuotaMs) { this.command = command; - this.controller = new QueryController(cfs, (PartitionRangeReadCommand) command, executionQuotaMs); + this.controller = new QueryController(cfs, command, executionQuotaMs); } @Override diff --git a/src/java/org/apache/cassandra/utils/btree/BTreeSet.java b/src/java/org/apache/cassandra/utils/btree/BTreeSet.java index 949c4c0721..20ee7cf044 100644 --- a/src/java/org/apache/cassandra/utils/btree/BTreeSet.java +++ b/src/java/org/apache/cassandra/utils/btree/BTreeSet.java @@ -30,6 +30,7 @@ import java.util.Objects; import java.util.SortedSet; import java.util.Spliterator; import java.util.Spliterators; +import java.util.function.Function; import com.google.common.collect.Ordering; @@ -680,10 +681,15 @@ public class BTreeSet<V> extends AbstractSet<V> implements NavigableSet<V>, List } public static <V> BTreeSet<V> copy(SortedSet<? extends V> copy, Comparator<? super V> comparator) + { + return copy(copy, comparator, v -> v); + } + + public static <V> BTreeSet<V> copy(SortedSet<? extends V> copy, Comparator<? super V> comparator, Function<V, V> modifier) { try (BTree.FastBuilder<V> builder = BTree.fastBuilder()) { - copy.forEach(builder::add); + copy.forEach(value -> builder.add(modifier.apply(value))); return wrap(builder.build(), comparator); } } diff --git a/test/unit/org/apache/cassandra/db/AbstractReadQueryToCQLStringTest.java b/test/unit/org/apache/cassandra/db/AbstractReadQueryToCQLStringTest.java index 7d3162413b..019a70e819 100644 --- a/test/unit/org/apache/cassandra/db/AbstractReadQueryToCQLStringTest.java +++ b/test/unit/org/apache/cassandra/db/AbstractReadQueryToCQLStringTest.java @@ -103,8 +103,7 @@ public class AbstractReadQueryToCQLStringTest extends CQLTester test("SELECT * FROM %s WHERE v2 = 2 ALLOW FILTERING"); test("SELECT * FROM %s WHERE v1 = 1 AND v2 = 2 ALLOW FILTERING"); test("SELECT * FROM %s WHERE token(k) > 0 AND v1 = 1"); - test("SELECT * FROM %s WHERE k = 0 AND v1 = 1", - "SELECT * FROM %s WHERE token(k) >= token(0) AND token(k) <= token(0) AND v1 = 1"); + test("SELECT * FROM %s WHERE k = 0 AND v1 = 1"); // grouped partition-directed queries, maybe producing multiple queries test("SELECT * FROM %s WHERE k IN (0)", @@ -188,8 +187,7 @@ public class AbstractReadQueryToCQLStringTest extends CQLTester test("SELECT * FROM %s WHERE token(k1, k2) > 0 AND k2 = 2"); test("SELECT * FROM %s WHERE token(k1, k2) > 0 AND v1 = 1"); test("SELECT * FROM %s WHERE token(k1, k2) > 0 AND v2 = 2"); - test("SELECT * FROM %s WHERE k1 = 1 AND k2 = 2 AND v1 = 1", - "SELECT * FROM %s WHERE token(k1, k2) >= token(1, 2) AND token(k1, k2) <= token(1, 2) AND v1 = 1"); + test("SELECT * FROM %s WHERE k1 = 1 AND k2 = 2 AND v1 = 1"); // grouped partition-directed queries, maybe producing multiple queries test("SELECT * FROM %s WHERE k1 IN (1) AND k2 = 2", @@ -279,10 +277,9 @@ public class AbstractReadQueryToCQLStringTest extends CQLTester test("SELECT * FROM %s WHERE v2 = 2 ALLOW FILTERING"); test("SELECT * FROM %s WHERE v1 = 1 AND v2 = 2 ALLOW FILTERING"); test("SELECT * FROM %s WHERE token(k) > 0 AND v1 = 1"); - test("SELECT * FROM %s WHERE k = 0 AND v1 = 1", - "SELECT * FROM %s WHERE token(k) >= token(0) AND token(k) <= token(0) AND v1 = 1"); + test("SELECT * FROM %s WHERE k = 0 AND v1 = 1"); test("SELECT * FROM %s WHERE k = 0 AND v1 = 1 AND c = 1", - "SELECT * FROM %s WHERE token(k) >= token(0) AND token(k) <= token(0) AND c = 1 AND v1 = 1 ALLOW FILTERING"); + "SELECT * FROM %s WHERE k = 0 AND c = 1 AND v1 = 1 ALLOW FILTERING"); // grouped partition-directed queries, maybe producing multiple queries test("SELECT * FROM %s WHERE k IN (0)", @@ -426,10 +423,8 @@ public class AbstractReadQueryToCQLStringTest extends CQLTester "SELECT * FROM %s WHERE (c1, c2, c3) = (1, 2, 3) ALLOW FILTERING"); test("SELECT * FROM %s WHERE v1 = 1 AND v2 = 2 ALLOW FILTERING"); test("SELECT * FROM %s WHERE token(k1, k2) > 0 AND v1 = 1"); - test("SELECT * FROM %s WHERE k1 = 1 AND k2 = 2 AND v1 = 1", - "SELECT * FROM %s WHERE token(k1, k2) >= token(1, 2) AND token(k1, k2) <= token(1, 2) AND v1 = 1"); - test("SELECT * FROM %s WHERE k1 = 1 AND k2 = 2 AND c1 = 1 AND v1 = 1", - "SELECT * FROM %s WHERE token(k1, k2) >= token(1, 2) AND token(k1, k2) <= token(1, 2) AND c1 = 1 AND v1 = 1 ALLOW FILTERING"); + test("SELECT * FROM %s WHERE k1 = 1 AND k2 = 2 AND v1 = 1"); + test("SELECT * FROM %s WHERE k1 = 1 AND k2 = 2 AND c1 = 1 AND v1 = 1"); // grouped partition-directed queries, maybe producing multiple queries test("SELECT * FROM %s WHERE k1 IN (1) AND k2 IN (2)", @@ -798,7 +793,7 @@ public class AbstractReadQueryToCQLStringTest extends CQLTester test(query, query); } - private void test(String query, String... expected) throws Throwable + private void test(String query, String... expected) { List<String> actual = toCQLString(query); List<String> fullExpected = Stream.of(expected) diff --git a/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerOutOfRangeTest.java b/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerOutOfRangeTest.java index 77ad4a6558..0462c6d61b 100644 --- a/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerOutOfRangeTest.java +++ b/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerOutOfRangeTest.java @@ -228,7 +228,8 @@ public class ReadCommandVerbHandlerOutOfRangeTest key(tmd, key), null, null, - false); + false, + null); this.tmd = tmd; } diff --git a/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerTest.java b/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerTest.java index 980f3e03c0..bc2b285d98 100644 --- a/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerTest.java +++ b/test/unit/org/apache/cassandra/db/ReadCommandVerbHandlerTest.java @@ -182,7 +182,8 @@ public class ReadCommandVerbHandlerTest KEY, new ClusteringIndexSliceFilter(Slices.ALL, false), null, - false); + false, + null); } @Override diff --git a/test/unit/org/apache/cassandra/db/ReadResponseTest.java b/test/unit/org/apache/cassandra/db/ReadResponseTest.java index 6a5d2e8ab4..e594369037 100644 --- a/test/unit/org/apache/cassandra/db/ReadResponseTest.java +++ b/test/unit/org/apache/cassandra/db/ReadResponseTest.java @@ -264,7 +264,8 @@ public class ReadResponseTest metadata.partitioner.decorateKey(ByteBufferUtil.bytes(key)), null, null, - false); + false, + null); } diff --git a/test/unit/org/apache/cassandra/service/reads/ReadExecutorTest.java b/test/unit/org/apache/cassandra/service/reads/ReadExecutorTest.java index 629df12a42..9dee28b16c 100644 --- a/test/unit/org/apache/cassandra/service/reads/ReadExecutorTest.java +++ b/test/unit/org/apache/cassandra/service/reads/ReadExecutorTest.java @@ -250,7 +250,7 @@ public class ReadExecutorTest MockSinglePartitionReadCommand(long timeout) { - super(cfs.metadata().epoch, false, 0, false, false, cfs.metadata(), 0, null, null, null, Util.dk("ry@n_luvs_teh_y@nk33z"), null, null, false); + super(cfs.metadata().epoch, false, 0, false, false, cfs.metadata(), 0, null, null, null, Util.dk("ry@n_luvs_teh_y@nk33z"), null, null, false, null); this.timeout = timeout; } diff --git a/test/unit/org/apache/cassandra/service/reads/repair/RepairedDataVerifierTest.java b/test/unit/org/apache/cassandra/service/reads/repair/RepairedDataVerifierTest.java index a478573503..7bdd08349a 100644 --- a/test/unit/org/apache/cassandra/service/reads/repair/RepairedDataVerifierTest.java +++ b/test/unit/org/apache/cassandra/service/reads/repair/RepairedDataVerifierTest.java @@ -290,7 +290,8 @@ public class RepairedDataVerifierTest metadata.partitioner.decorateKey(ByteBufferUtil.bytes(key)), new ClusteringIndexSliceFilter(Slices.ALL, false), null, - false); + false, + null); } } } --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
