mirror of
https://github.com/scylladb/scylladb.git
synced 2026-04-23 18:10:39 +00:00
A global index has a primary key of the form (indexed_column, token, partition_key_column..., clustering_key_column...) The primary key columns are used to point at the base table row, and the token (computed as token(partition_key_column...) is used to maintain sort order. The query planner has an optimization: if the partition key is fully constrained to a unique value, then we compute the token from the partition key and use that to seek directly into the clustering row range for that base table partition. If the clustering key is also partially constrained, it is used to refine the index clustering key. Currently, this optimization is implemented as a hack: the partition key is extracted from the prepared statement + query options in get_global_index_token_clustering_ranges(), then used to calculate the token, which is then substituted in the expression passed to get_single_column_clustering_bounds() (the expression is shared across all running queries, so this is quite dangerous). We simplify the whole thing: - Let prepare_index_global() recognize that if the partition key is not fully constrained, then there is no way that we'll be able to compute the token (as it needs all partition key columns). Since the token is the first clustering key column of the index table, we can truncate it to length zero and bail out. - Otherwise, the partition key is fully constrained. We refactor the predicate (pk1 = :a AND pk2 = :b) to (pk1, pk2) := (:a, :b). We then pass expressions representing the partition key to the token function, ending up with token(:a, :b). We then substitute this expression into (*_idx_tbl_ck_prefix)[0], which computes the first clustering key column for the index table. - Remove the runtime component in get_global_index_clustering_ranges(). Note this include the early return if the partition key wasn't fully constrained (though the comment only mentions over-constraining), and the token computation, which is now done by evaluate(). Closes scylladb/scylladb#20733