diff options
| author | Lucas de Castro Borges <lucas@gnuabordo.com.br> | 2025-02-11 15:07:35 -0300 |
|---|---|---|
| committer | Lucas de Castro Borges <lucas@gnuabordo.com.br> | 2025-02-11 15:07:35 -0300 |
| commit | 4cb8841196d0625dfa3825aa326f071cd27c7b8b (patch) | |
| tree | 1682a647d4463397c119183369ae6f750d5fdcff /src/mongo/db/query/plan_cache_key_info_test.cpp | |
| parent | aa03c6362cbaa767638e6eed9b031d86dd2643d1 (diff) | |
| parent | 8f0827553e09872941945a093b647a4211a9db7f (diff) | |
Update upstream source from tag 'upstream/6.0.0'master
Update to upstream version '6.0.0'
with Debian dir 5604a80ec1c96ca76f25f40d78e6ef855abec322
Diffstat (limited to 'src/mongo/db/query/plan_cache_key_info_test.cpp')
| -rw-r--r-- | src/mongo/db/query/plan_cache_key_info_test.cpp | 133 |
1 files changed, 16 insertions, 117 deletions
diff --git a/src/mongo/db/query/plan_cache_key_info_test.cpp b/src/mongo/db/query/plan_cache_key_info_test.cpp index a13616e12c4..7235386e7f4 100644 --- a/src/mongo/db/query/plan_cache_key_info_test.cpp +++ b/src/mongo/db/query/plan_cache_key_info_test.cpp @@ -194,107 +194,6 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyPartialIndex) { makeKey(*cqGtZero, indexCores)); } -TEST(PlanCacheKeyInfoTest, ComputeKeyPartialIndexConjunction) { - BSONObj filterObj = fromjson("{f: {$gt: 0, $lt: 10}}"); - unique_ptr<MatchExpression> filterExpr(parseMatchExpression(filterObj)); - - const auto keyPattern = BSON("a" << 1); - const std::vector<CoreIndexInfo> indexCores = { - CoreIndexInfo(keyPattern, - IndexNames::nameToType(IndexNames::findPluginName(keyPattern)), - false, // sparse - IndexEntry::Identifier{""}, // name - filterExpr.get())}; // filterExpr - - unique_ptr<CanonicalQuery> satisfySinglePredicate(canonicalize("{f: {$gt: 0}}")); - ASSERT_EQ(makeKey(*satisfySinglePredicate, indexCores).getIndexabilityDiscriminators(), "(0)"); - - unique_ptr<CanonicalQuery> satisfyBothPredicates(canonicalize("{f: {$eq: 5}}")); - ASSERT_EQ(makeKey(*satisfyBothPredicates, indexCores).getIndexabilityDiscriminators(), "(1)"); - - unique_ptr<CanonicalQuery> conjSingleField(canonicalize("{f: {$gt: 2, $lt: 9}}")); - ASSERT_EQ(makeKey(*conjSingleField, indexCores).getIndexabilityDiscriminators(), "(1)"); - - unique_ptr<CanonicalQuery> conjSingleFieldNoMatch(canonicalize("{f: {$gt: 2, $lt: 11}}")); - ASSERT_EQ(makeKey(*conjSingleFieldNoMatch, indexCores).getIndexabilityDiscriminators(), "(0)"); - - // Note that these queries get optimized to a single $in over 'f'. - unique_ptr<CanonicalQuery> disjSingleFieldBothSatisfy( - canonicalize("{$or: [{f: {$eq: 2}}, {f: {$eq: 3}}]}")); - ASSERT_EQ(makeKey(*disjSingleFieldBothSatisfy, indexCores).getIndexabilityDiscriminators(), - "(1)"); - - unique_ptr<CanonicalQuery> disjSingleFieldNotSubset( - canonicalize("{$or: [{f: {$eq: 2}}, {f: {$eq: 11}}]}")); - ASSERT_EQ(makeKey(*disjSingleFieldNotSubset, indexCores).getIndexabilityDiscriminators(), - "(0)"); -} - -TEST(PlanCacheKeyInfoTest, ComputeKeyPartialIndexDisjunction) { - BSONObj filterObj = fromjson("{$or: [{f: {$gt: 10}}, {f: {$lt: 0}}]}"); - unique_ptr<MatchExpression> filterExpr(parseMatchExpression(filterObj)); - - const auto keyPattern = BSON("a" << 1); - const std::vector<CoreIndexInfo> indexCores = { - CoreIndexInfo(keyPattern, - IndexNames::nameToType(IndexNames::findPluginName(keyPattern)), - false, // sparse - IndexEntry::Identifier{""}, // name - filterExpr.get())}; // filterExpr - - unique_ptr<CanonicalQuery> satisfySinglePredicate(canonicalize("{f: {$eq: 11}}")); - ASSERT_EQ(makeKey(*satisfySinglePredicate, indexCores).getIndexabilityDiscriminators(), "(1)"); - - unique_ptr<CanonicalQuery> satisfyNeither(canonicalize("{f: {$eq: 5}}")); - ASSERT_EQ(makeKey(*satisfyNeither, indexCores).getIndexabilityDiscriminators(), "(0)"); - - unique_ptr<CanonicalQuery> conjSingleFieldMatch(canonicalize("{f: {$lt: 20, $gt: 10}}")); - ASSERT_EQ(makeKey(*conjSingleFieldMatch, indexCores).getIndexabilityDiscriminators(), "(1)"); - - unique_ptr<CanonicalQuery> conjSingleFieldNoMatch(canonicalize("{f: {$gt: 2, $lt: 10}}")); - ASSERT_EQ(makeKey(*conjSingleFieldNoMatch, indexCores).getIndexabilityDiscriminators(), "(0)"); - - unique_ptr<CanonicalQuery> conjSingleFieldOverlap(canonicalize("{f: {$gt: 2, $lt: 12}}")); - ASSERT_EQ(makeKey(*conjSingleFieldOverlap, indexCores).getIndexabilityDiscriminators(), "(0)"); - - // Although this query is technically a subset of the partial filter, the logic to determine - // such ('isSubsetOf' in the code) is conservative in how it compares certain shapes of - // expression trees. - unique_ptr<CanonicalQuery> disjSingleFieldBothSatisfy( - canonicalize("{$or: [{f: {$eq: -1}}, {f: {$gt: 10}}]}")); - ASSERT_EQ(makeKey(*disjSingleFieldBothSatisfy, indexCores).getIndexabilityDiscriminators(), - "(0)"); - - unique_ptr<CanonicalQuery> disjSingleFieldNotSubset( - canonicalize("{$or: [{f: {$eq: 2}}, {f: {$eq: 11}}]}")); - ASSERT_EQ(makeKey(*disjSingleFieldNotSubset, indexCores).getIndexabilityDiscriminators(), - "(0)"); -} - -TEST(PlanCacheKeyInfoTest, ComputeKeyPartialIndexNestedDisjunction) { - BSONObj filterObj = fromjson(R"( - {$and: [ - {$or: [{f: {$gt: 10}}, {f: {$lt: 0}}]}, - {$or: [{f: {$gt: 11}}, {f: {$lt: 1}}]} - ]})"); - unique_ptr<MatchExpression> filterExpr(parseMatchExpression(filterObj)); - - const auto keyPattern = BSON("a" << 1); - const std::vector<CoreIndexInfo> indexCores = { - CoreIndexInfo(keyPattern, - IndexNames::nameToType(IndexNames::findPluginName(keyPattern)), - false, // sparse - IndexEntry::Identifier{""}, // name - filterExpr.get())}; // filterExpr - - - unique_ptr<CanonicalQuery> satisfySinglePredicate(canonicalize("{f: {$eq: 11}}")); - ASSERT_EQ(makeKey(*satisfySinglePredicate, indexCores).getIndexabilityDiscriminators(), "(0)"); - - unique_ptr<CanonicalQuery> notCompat(canonicalize("{f: {$eq: 12}}")); - ASSERT_EQ(makeKey(*notCompat, indexCores).getIndexabilityDiscriminators(), "(1)"); -} - // Query shapes should get the same plan cache key if they have the same collation indexability. TEST(PlanCacheKeyInfoTest, ComputeKeyCollationIndex) { CollatorInterfaceMock collator(CollatorInterfaceMock::MockType::kReverseString); @@ -467,8 +366,8 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyBasedOnPartia // The discriminator strings have the format "<xx>". That is, there are two discriminator // bits for the "x" predicate, the first pertaining to the partialFilterExpression and the // second around applicability to the wildcard index. - ASSERT_EQ(compatibleKey.getIndexabilityDiscriminators(), "(1)<1>"); - ASSERT_EQ(incompatibleKey.getIndexabilityDiscriminators(), "(0)<1>"); + ASSERT_EQ(compatibleKey.getIndexabilityDiscriminators(), "<11>"); + ASSERT_EQ(incompatibleKey.getIndexabilityDiscriminators(), "<01>"); } // The partialFilterExpression should lead to a discriminator over field 'x', but not over 'y'. @@ -483,8 +382,8 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyBasedOnPartia // The discriminator strings have the format "<xx><y>". That is, there are two discriminator // bits for the "x" predicate (the first pertaining to the partialFilterExpression, the // second around applicability to the wildcard index) and one discriminator bit for "y". - ASSERT_EQ(compatibleKey.getIndexabilityDiscriminators(), "(1)<1><1>"); - ASSERT_EQ(incompatibleKey.getIndexabilityDiscriminators(), "(0)<1><1>"); + ASSERT_EQ(compatibleKey.getIndexabilityDiscriminators(), "<11><1>"); + ASSERT_EQ(incompatibleKey.getIndexabilityDiscriminators(), "<01><1>"); } // $eq:null predicates cannot be assigned to a wildcard index. Make sure that this is @@ -499,8 +398,8 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyBasedOnPartia // The discriminator strings have the format "<xx><y>". That is, there are two discriminator // bits for the "x" predicate (the first pertaining to the partialFilterExpression, the // second around applicability to the wildcard index) and one discriminator bit for "y". - ASSERT_EQ(compatibleKey.getIndexabilityDiscriminators(), "(1)<1><1>"); - ASSERT_EQ(incompatibleKey.getIndexabilityDiscriminators(), "(1)<1><0>"); + ASSERT_EQ(compatibleKey.getIndexabilityDiscriminators(), "<11><1>"); + ASSERT_EQ(incompatibleKey.getIndexabilityDiscriminators(), "<11><0>"); } // Test that the discriminators are correct for an $eq:null predicate on 'x'. This predicate is @@ -509,7 +408,7 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyBasedOnPartia // result in two "0" bits inside the discriminator string. { auto key = makeKey(*canonicalize("{x: {$eq: null}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(0)<0>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<00>"); } } @@ -550,11 +449,11 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyWithPartialFi const std::vector<CoreIndexInfo> indexCores = {indexInfo}; { - // TODO update The discriminators should have the format <xx><yy><z>. The 'z' predicate has - // just one discriminator because it is not referenced in the partial filter expression. All + // The discriminators should have the format <xx><yy><z>. The 'z' predicate has just one + // discriminator because it is not referenced in the partial filter expression. All // predicates are compatible. auto key = makeKey(*canonicalize("{x: {$eq: 1}, y: {$eq: 2}, z: {$eq: 3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(1)<1><1><1>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<11><11><1>"); } { @@ -562,7 +461,7 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyWithPartialFi // compatible with the partial filter expression, leading to one of the 'y' bits being set // to zero. auto key = makeKey(*canonicalize("{x: {$eq: 1}, y: {$eq: -2}, z: {$eq: 3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(0)<1><1><1>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<11><01><1>"); } } @@ -581,20 +480,20 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyDiscriminatesCorrectlyWithPartialFilterAndW // the predicate is compatible with the partial filter expression, whereas the disciminator // for 'y' is about compatibility with the wildcard index. auto key = makeKey(*canonicalize("{x: {$eq: 1}, y: {$eq: 2}, z: {$eq: 3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(1)<1>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<1><1>"); } { // Similar to the previous case, except with an 'x' predicate that is incompatible with the // partial filter expression. auto key = makeKey(*canonicalize("{x: {$eq: -1}, y: {$eq: 2}, z: {$eq: 3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(0)<1>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<0><1>"); } { // Case where the 'y' predicate is not compatible with the wildcard index. auto key = makeKey(*canonicalize("{x: {$eq: 1}, y: {$eq: null}, z: {$eq: 3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(1)<0>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<1><0>"); } } @@ -612,14 +511,14 @@ TEST(PlanCacheKeyInfoTest, ComputeKeyWildcardDiscriminatesCorrectlyWithPartialFi // The discriminators have the format <x><(x.y)(x.y)<y>. All predicates are compatible auto key = makeKey(*canonicalize("{x: {$eq: 1}, y: {$eq: 2}, 'x.y': {$eq: 3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(1)<1><1><1>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<1><11><1>"); } { // Here, the predicate on "x.y" is not compatible with the partial filter expression. auto key = makeKey(*canonicalize("{x: {$eq: 1}, y: {$eq: 2}, 'x.y': {$eq: -3}}"), indexCores); - ASSERT_EQ(key.getIndexabilityDiscriminators(), "(0)<1><1><1>"); + ASSERT_EQ(key.getIndexabilityDiscriminators(), "<1><01><1>"); } } |
