Skip to content

Commit f8be6ca

Browse files
adelapenamichaelsembwever
authored andcommitted
CNDB-15578: CNDB-15381: Port CASSANDRA-20888 index hints improvements (#2004)
Port some of the improvements for index hints done by [CASSANDRA-20888](https://issues.apache.org/jira/browse/CASSANDRA-20888), especially the ones in messaging. Also clean up unused methods in index hints.
1 parent 9c35a64 commit f8be6ca

File tree

7 files changed

+84
-78
lines changed

7 files changed

+84
-78
lines changed

src/java/org/apache/cassandra/cql3/restrictions/MultiColumnRestriction.java

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -147,9 +147,14 @@ public boolean needsFiltering(Index.Group indexGroup, IndexHints indexHints)
147147

148148
private boolean isSupportedBy(Index.Group indexGroup, IndexHints indexHints, ColumnMetadata column)
149149
{
150-
for (Index index : indexGroup.getNotExcludedIndexes(indexHints))
150+
for (Index index : indexGroup.getIndexes())
151+
{
152+
if (indexHints.excludes(index))
153+
continue;
154+
151155
if (isSupportedBy(index, column))
152156
return true;
157+
}
153158

154159
return false;
155160
}
@@ -680,7 +685,7 @@ public final void addToRowFilter(RowFilter.Builder filter,
680685
throw new UnsupportedOperationException("Secondary indexes do not support IS NOT NULL restrictions");
681686
}
682687
}
683-
688+
684689
@Override
685690
public String toString()
686691
{

src/java/org/apache/cassandra/cql3/restrictions/SingleColumnRestriction.java

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,9 +96,14 @@ public Index findSupportingIndex(IndexRegistry indexRegistry, IndexHints indexHi
9696
@Override
9797
public boolean needsFiltering(Index.Group indexGroup, IndexHints indexHints)
9898
{
99-
for (Index index : indexGroup.getNotExcludedIndexes(indexHints))
99+
for (Index index : indexGroup.getIndexes())
100+
{
101+
if (indexHints.excludes(index))
102+
continue;
103+
100104
if (isSupportedBy(index))
101105
return false;
106+
}
102107

103108
return true;
104109
}

src/java/org/apache/cassandra/db/filter/IndexHints.java

Lines changed: 16 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030
import com.google.common.collect.Iterables;
3131
import com.google.common.collect.Sets;
3232

33+
import org.apache.cassandra.config.DatabaseDescriptor;
3334
import org.apache.cassandra.cql3.QualifiedName;
3435
import org.apache.cassandra.db.TypeSizes;
3536
import org.apache.cassandra.exceptions.InvalidRequestException;
@@ -42,6 +43,7 @@
4243
import org.apache.cassandra.schema.IndexMetadata;
4344
import org.apache.cassandra.schema.TableMetadata;
4445
import org.apache.cassandra.utils.FBUtilities;
46+
import org.apache.cassandra.utils.vint.VIntCoding;
4547

4648
import static java.lang.String.format;
4749

@@ -71,12 +73,6 @@ public boolean includes(String indexName)
7173
return false;
7274
}
7375

74-
@Override
75-
public Set<Index> includedIn(Collection<Index> indexes)
76-
{
77-
return Collections.emptySet();
78-
}
79-
8076
@Override
8177
public boolean includesAnyOf(Collection<Index> indexes)
8278
{
@@ -95,12 +91,6 @@ public boolean excludes(String indexName)
9591
return false;
9692
}
9793

98-
@Override
99-
public <T extends Index> Set<T> notExcluded(Iterable<T> indexes)
100-
{
101-
return Sets.newHashSet(indexes);
102-
}
103-
10494
@Override
10595
public void validate(@Nullable Index.QueryPlan queryPlan)
10696
{
@@ -156,23 +146,6 @@ public boolean includes(String indexName)
156146
return false;
157147
}
158148

159-
/**
160-
* Returns the indexes in the specified collection of indexes that are included by these hints.
161-
*
162-
* @param indexes a collection of indexes
163-
* @return the indexes that are included by these hints
164-
*/
165-
public Set<Index> includedIn(Collection<Index> indexes)
166-
{
167-
Set<Index> result = new HashSet<>();
168-
for (Index index : indexes)
169-
{
170-
if (includes(index))
171-
result.add(index);
172-
}
173-
return result;
174-
}
175-
176149
/**
177150
* @param indexes a collection of indexes
178151
* @return {@code true} if any of the indexes is included, {@code false} otherwise
@@ -210,21 +183,6 @@ public boolean excludes(String indexName)
210183
return false;
211184
}
212185

213-
/**
214-
* @param indexes a set of indexes
215-
* @return the indexes that are not excluded by these hints
216-
*/
217-
public <T extends Index> Set<T> notExcluded(Iterable<T> indexes)
218-
{
219-
Set<T> result = new HashSet<>();
220-
for (T index : indexes)
221-
{
222-
if (!excludes(index))
223-
result.add(index);
224-
}
225-
return result;
226-
}
227-
228186
/**
229187
* Returns the best of the specified indexes that satisfies the specified filter and is not excluded.
230188
* The order of preference to determine whether an index is better than another is:
@@ -422,10 +380,10 @@ public static IndexHints fromCQLNames(Set<QualifiedName> included,
422380
TableMetadata table,
423381
IndexRegistry indexRegistry)
424382
{
425-
if (included != null && included.size() > Short.MAX_VALUE)
383+
if (included != null && included.size() > maxIncludedOrExcludedIndexCount())
426384
throw new InvalidRequestException(TOO_MANY_INDEXES_ERROR + included.size());
427385

428-
if (excluded != null && excluded.size() > Short.MAX_VALUE)
386+
if (excluded != null && excluded.size() > maxIncludedOrExcludedIndexCount())
429387
throw new InvalidRequestException(TOO_MANY_INDEXES_ERROR + excluded.size());
430388

431389
IndexHints hints = IndexHints.create(fetchIndexes(included, table, indexRegistry),
@@ -451,6 +409,14 @@ public static IndexHints fromCQLNames(Set<QualifiedName> included,
451409
return hints;
452410
}
453411

412+
private static int maxIncludedOrExcludedIndexCount()
413+
{
414+
int guardrail = DatabaseDescriptor.getGuardrailsConfig().getSecondaryIndexesPerTableFailThreshold();
415+
416+
// If no guardrail is configured, use a value that safely fits in a single byte for serialization:
417+
return guardrail > 0 ? guardrail : 128;
418+
}
419+
454420
private static Set<IndexMetadata> fetchIndexes(Set<QualifiedName> indexNames, TableMetadata table, IndexRegistry indexRegistry)
455421
{
456422
if (indexNames == null || indexNames.isEmpty())
@@ -626,16 +592,16 @@ private void serialize(Set<IndexMetadata> indexes, DataOutputPlus out, int versi
626592
return;
627593

628594
int n = indexes.size();
629-
assert n < Short.MAX_VALUE : TOO_MANY_INDEXES_ERROR + n;
595+
assert n < maxIncludedOrExcludedIndexCount() : TOO_MANY_INDEXES_ERROR + n;
630596

631-
out.writeShort(n);
597+
out.writeVInt32(n);
632598
for (IndexMetadata index : indexes)
633599
IndexMetadata.serializer.serialize(index, out, version);
634600
}
635601

636602
private Set<IndexMetadata> deserialize(DataInputPlus in, int version, TableMetadata table) throws IOException
637603
{
638-
short n = in.readShort();
604+
int n = (int) in.readVInt();
639605
Set<IndexMetadata> indexes = new HashSet<>(n);
640606
for (short i = 0; i < n; i++)
641607
{
@@ -650,8 +616,7 @@ private long serializedSize(Set<IndexMetadata> indexes, int version)
650616
if (indexes.isEmpty())
651617
return 0;
652618

653-
long size = 0;
654-
size += TypeSizes.SHORT_SIZE; // number of indexes
619+
long size = VIntCoding.computeVIntSize(indexes.size());
655620
for (IndexMetadata index : indexes)
656621
size += IndexMetadata.serializer.serializedSize(index, version);
657622
return size;

src/java/org/apache/cassandra/index/Index.java

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,6 @@
4545
import org.apache.cassandra.db.ReadExecutionController;
4646
import org.apache.cassandra.db.RegularAndStaticColumns;
4747
import org.apache.cassandra.db.WriteContext;
48-
import org.apache.cassandra.db.filter.IndexHints;
4948
import org.apache.cassandra.db.filter.RowFilter;
5049
import org.apache.cassandra.db.lifecycle.LifecycleNewTracker;
5150
import org.apache.cassandra.db.marshal.AbstractType;
@@ -850,17 +849,6 @@ public int hashCode()
850849
*/
851850
Set<? extends Index> getIndexes();
852851

853-
/**
854-
* Returns the indexes that are members of this group that are not excluded by the hints.
855-
*
856-
* @param hints the index hints with the indexes to exclude.
857-
* @return the indexes that are members of this group that are not excluded by the hints.
858-
*/
859-
default Set<? extends Index> getNotExcludedIndexes(IndexHints hints)
860-
{
861-
return hints.notExcluded(getIndexes());
862-
}
863-
864852
/**
865853
* Adds the specified {@link Index} as a member of this group.
866854
*

src/java/org/apache/cassandra/index/IndexRegistry.java

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,12 @@ public Collection<Index> listIndexes()
8484
return Collections.emptyList();
8585
}
8686

87+
@Override
88+
public Collection<Index> listNotExcludedIndexes(IndexHints hints)
89+
{
90+
return Collections.emptyList();
91+
}
92+
8793
@Override
8894
public Collection<Index.Group> listIndexGroups()
8995
{
@@ -306,6 +312,14 @@ public Collection<Index> listIndexes()
306312
return Collections.singletonList(index);
307313
}
308314

315+
@Override
316+
public Collection<Index> listNotExcludedIndexes(IndexHints hints)
317+
{
318+
return hints.excludes(index)
319+
? Collections.emptyList()
320+
: Collections.singletonList(index);
321+
}
322+
309323
@Override
310324
public Collection<Index.Group> listIndexGroups()
311325
{
@@ -349,10 +363,7 @@ default void registerIndex(Index index)
349363
* @param hints the index hints with the indexes to exclude.
350364
* @return the indexes in this registry that are not excluded by the hints.
351365
*/
352-
default Collection<Index> listNotExcludedIndexes(IndexHints hints)
353-
{
354-
return hints.notExcluded(listIndexes());
355-
}
366+
Collection<Index> listNotExcludedIndexes(IndexHints hints);
356367

357368
default Optional<Index.Analyzer> getAnalyzerFor(ColumnMetadata column, Operator operator, ByteBuffer value)
358369
{

src/java/org/apache/cassandra/index/SecondaryIndexManager.java

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -201,7 +201,7 @@ public class SecondaryIndexManager implements IndexRegistry, INotificationConsum
201201
* The indexes that are available for querying.
202202
*/
203203
private final Set<String> queryableIndexes = Sets.newConcurrentHashSet();
204-
204+
205205
/**
206206
* The indexes that are available for writing.
207207
*/
@@ -659,7 +659,7 @@ public void onSuccess(Object o)
659659
* <p>
660660
* If the index doesn't support ALL {@link Index.LoadType} it performs a recovery {@link Index#getRecoveryTaskSupport()}
661661
* instead of a build {@link Index#getBuildTaskSupport()}
662-
*
662+
*
663663
* @param sstables the SSTables to be (re)indexed
664664
* @param indexes the indexes to be (re)built for the specifed SSTables
665665
* @param isFullRebuild True if this method is invoked as a full index rebuild, false otherwise
@@ -1470,6 +1470,24 @@ public Collection<Index> listIndexes()
14701470
return ImmutableSet.copyOf(indexes.values());
14711471
}
14721472

1473+
@Override
1474+
public Collection<Index> listNotExcludedIndexes(IndexHints hints)
1475+
{
1476+
if (indexes.isEmpty())
1477+
return Collections.emptySet();
1478+
1479+
if (hints == IndexHints.NONE || hints.excluded.isEmpty())
1480+
return listIndexes();
1481+
1482+
ImmutableSet.Builder<Index> builder = ImmutableSet.builder();
1483+
for (Index index : indexes.values())
1484+
{
1485+
if (!hints.excludes(index))
1486+
builder.add(index);
1487+
}
1488+
return builder.build();
1489+
}
1490+
14731491
public Set<Index.Group> listIndexGroups()
14741492
{
14751493
return ImmutableSet.copyOf(indexGroups.values());
@@ -1973,4 +1991,5 @@ public void makeIndexQueryable(Index index, Index.Status status)
19731991
logger.info("Index [{}] became writable after successful build.", name);
19741992
}
19751993
}
1994+
19761995
}

src/java/org/apache/cassandra/net/MessagingService.java

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -798,13 +798,26 @@ public Set<InetAddressAndPort> endpointsWithConnectionsOnVersionBelow(String key
798798
Set<InetAddressAndPort> nodes = new HashSet<>();
799799
for (InetAddressAndPort node : StorageService.instance.getTokenMetadataForKeyspace(keyspace).getAllEndpoints())
800800
{
801-
ConnectionType.MESSAGING_TYPES.forEach(type -> {
802-
OutboundConnections connections = getOutbound(node, false);
803-
OutboundConnection connection = connections != null ? connections.connectionFor(type) : null;
804-
if (connection != null && connection.messagingVersion() < version)
805-
nodes.add(node);
806-
});
801+
if (hasConnectionWithVersionBelow(node, version))
802+
nodes.add(node);
807803
}
808804
return nodes;
809805
}
806+
807+
private boolean hasConnectionWithVersionBelow(InetAddressAndPort node, int version)
808+
{
809+
OutboundConnections connections = getOutbound(node, false);
810+
811+
if (connections == null)
812+
return false;
813+
814+
for (ConnectionType type : ConnectionType.MESSAGING_TYPES)
815+
{
816+
OutboundConnection connection = connections.connectionFor(type);
817+
if (connection != null && connection.messagingVersion() < version)
818+
return true;
819+
}
820+
821+
return false;
822+
}
810823
}

0 commit comments

Comments
 (0)