From 041aaf31f0e7b0bb638cadd969d92944b11511e9 Mon Sep 17 00:00:00 2001 From: Matthew Boros Date: Tue, 26 May 2026 13:30:02 -0400 Subject: [PATCH] SERVER-112823 Make deferred get_executor flag an IFR flag (#54369) GitOrigin-RevId: 978ae0b95e8902c4f48a849a2e80c15ceba969bd --- .../and_hash_reports_memory_metrics.js | 2 +- .../merge_join_reports_memory_metrics.js | 2 +- .../classic_runtime_planner/cached_planner.cpp | 3 ++- .../classic_runtime_planner/idhack_planner.cpp | 3 ++- .../cached_planner.cpp | 12 +++++++----- .../engine_selection_planner.cpp | 5 +++++ .../multi_planner.cpp | 3 ++- .../planner_interface.cpp | 5 +++++ .../single_solution_passthrough_planner.cpp | 3 ++- .../sub_planner.cpp | 3 ++- src/mongo/db/query/canonical_query.cpp | 4 ++-- src/mongo/db/query/canonical_query_encoder.cpp | 6 +++--- src/mongo/db/query/engine_selection.cpp | 10 ++++++---- src/mongo/db/query/engine_selection_plan.cpp | 2 +- src/mongo/db/query/engine_selection_plan.h | 2 +- .../db/query/engine_selection_plan_test.cpp | 10 +++++----- src/mongo/db/query/get_executor.cpp | 3 ++- src/mongo/db/query/get_executor_helpers.cpp | 18 ++++++++++-------- src/mongo/db/query/query_feature_flags.idl | 1 + 19 files changed, 60 insertions(+), 37 deletions(-) diff --git a/jstests/noPassthrough/memory_tracking/and_hash_reports_memory_metrics.js b/jstests/noPassthrough/memory_tracking/and_hash_reports_memory_metrics.js index 2816a884adf..ad81b3fe889 100644 --- a/jstests/noPassthrough/memory_tracking/and_hash_reports_memory_metrics.js +++ b/jstests/noPassthrough/memory_tracking/and_hash_reports_memory_metrics.js @@ -58,7 +58,7 @@ assert( ); // Skip if AND_HASH did not execute in SBE. When featureFlagGetExecutorDeferredEngineChoice is -// enabled, isPlanSbeEligible() rejects AND_HASH plans via AndHashOrSortedRule (SERVER-90818), +// enabled, isPlanSbeCompatible() rejects AND_HASH plans via AndHashOrSortedRule (SERVER-90818), // causing them to fall back to the classic engine even with trySbeEngine set. const execExplain = coll.explain("executionStats").aggregate(pipeline, {allowDiskUse: false}); if (execExplain.explainVersion !== "2") { diff --git a/jstests/noPassthrough/memory_tracking/merge_join_reports_memory_metrics.js b/jstests/noPassthrough/memory_tracking/merge_join_reports_memory_metrics.js index 859079ce3c6..50d7cc685fb 100644 --- a/jstests/noPassthrough/memory_tracking/merge_join_reports_memory_metrics.js +++ b/jstests/noPassthrough/memory_tracking/merge_join_reports_memory_metrics.js @@ -58,7 +58,7 @@ assert( ); // Skip if AND_SORTED did not execute in SBE. When featureFlagGetExecutorDeferredEngineChoice is -// enabled, isPlanSbeEligible() rejects AND_SORTED plans via AndHashOrSortedRule (SERVER-90818), +// enabled, isPlanSbeCompatible() rejects AND_SORTED plans via AndHashOrSortedRule (SERVER-90818), // causing them to fall back to the classic engine even with trySbeEngine set. const execExplain = coll.explain("executionStats").aggregate(pipeline, {allowDiskUse: false}); if (execExplain.explainVersion !== "2") { diff --git a/src/mongo/db/exec/runtime_planners/classic_runtime_planner/cached_planner.cpp b/src/mongo/db/exec/runtime_planners/classic_runtime_planner/cached_planner.cpp index 08ce07d9881..6db9daed26f 100644 --- a/src/mongo/db/exec/runtime_planners/classic_runtime_planner/cached_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/classic_runtime_planner/cached_planner.cpp @@ -63,7 +63,8 @@ PlanRankingResult CachedPlanner::extractPlanRankingResult() { tassert(11756603, "Expected `extractPlanRankingResult` to only be called with get executor deferred " "feature flag enabled.", - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()); + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); std::vector> solutions; solutions.push_back(extractQuerySolution()); return PlanRankingResult{ diff --git a/src/mongo/db/exec/runtime_planners/classic_runtime_planner/idhack_planner.cpp b/src/mongo/db/exec/runtime_planners/classic_runtime_planner/idhack_planner.cpp index 22fcb99c04a..3a03771dede 100644 --- a/src/mongo/db/exec/runtime_planners/classic_runtime_planner/idhack_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/classic_runtime_planner/idhack_planner.cpp @@ -110,7 +110,8 @@ PlanRankingResult IdHackPlanner::extractPlanRankingResult() { tassert(11974301, "Expected `extractPlanRankingResult` to only be called with get executor deferred " "feature flag enabled.", - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()); + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); return PlanRankingResult{.usedIdhack = true, .execState = SavedExecState{ClassicExecState{.workingSet = extractWs(), .root = extractRoot()}}, diff --git a/src/mongo/db/exec/runtime_planners/classic_runtime_planner_for_sbe/cached_planner.cpp b/src/mongo/db/exec/runtime_planners/classic_runtime_planner_for_sbe/cached_planner.cpp index f317f49a329..27e1fdde6f7 100644 --- a/src/mongo/db/exec/runtime_planners/classic_runtime_planner_for_sbe/cached_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/classic_runtime_planner_for_sbe/cached_planner.cpp @@ -78,7 +78,8 @@ public: tassert(11756604, "Expected `extractPlanRankingResult` to only be called with get executor deferred " "feature flag enabled.", - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()); + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); std::vector> v; v.push_back(std::move(_candidate.solution)); return PlanRankingResult{ @@ -259,6 +260,9 @@ std::unique_ptr attemptToUsePlan( .planSummary; }; + const bool deferredExecutorEnabled = + plannerData.cq->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice); if (!candidate.status.isOK()) { // On failure, fall back to replanning the whole query. We neither evict the existing cache // entry, nor cache the result of replanning. @@ -271,8 +275,7 @@ std::unique_ptr attemptToUsePlan( std::string replanReason = str::stream() << "cached plan returned: " << candidate.status; recoverWhereExpression(plannerData.cq, std::move(candidate)); - if (MONGO_unlikely( - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled())) { + if (deferredExecutorEnabled) { // If we're using the deferred get_executor, we throw an exception which is caught be a // higher level replanning try/catch, and will reuse the top-level planning path. If // we're using the regular get_executor, this counter is incremented in `replan`. @@ -313,8 +316,7 @@ std::unique_ptr attemptToUsePlan( << decisionReads << " reads but it took at least " << numReads << " reads"; recoverWhereExpression(plannerData.cq, std::move(candidate)); - if (MONGO_unlikely( - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled())) { + if (deferredExecutorEnabled) { incrementReplanCounterCb(); uassertStatusOK(Status(ReplanningRequiredInfo(plan_cache_util::CacheMode::AlwaysCache, *plannerData.cachedPlanSolutionHash), diff --git a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/engine_selection_planner.cpp b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/engine_selection_planner.cpp index b0cb6190070..00d88820e1a 100644 --- a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/engine_selection_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/engine_selection_planner.cpp @@ -71,6 +71,11 @@ EngineSelectionPlanner::EngineSelectionPlanner(std::unique_ptr CanonicalQuery* cq, Pipeline* pipeline, const MultipleCollectionAccessor& collections) { + tassert(11282303, + "Only expected an EngineSelectionPlanner to be created when the deferred get_executor " + "is enabled.", + cq->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); _result = innerPlanner->extractPlanRankingResult(); // Engine selection is only needed for non-trivial cases. ID hack and cached planners already diff --git a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/multi_planner.cpp b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/multi_planner.cpp index c64475a1191..692aa4016f1 100644 --- a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/multi_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/multi_planner.cpp @@ -68,7 +68,8 @@ PlanRankingResult MultiPlanner::extractPlanRankingResult() { tassert(11974300, "Expected `extractPlanRankingResult` to only be called with get executor deferred " "feature flag enabled.", - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()); + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); auto querySolution = _multiplanStage->extractBestSolution(); if (!_maybeExplainData.has_value()) { diff --git a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/planner_interface.cpp b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/planner_interface.cpp index 2313e476bbc..61a59d981fe 100644 --- a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/planner_interface.cpp +++ b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/planner_interface.cpp @@ -59,6 +59,11 @@ PreComputedRankingResultPlanner::PreComputedRankingResultPlanner(PlannerData pla : DeferredEngineChoicePlannerInterface(std::move(plannerData)), _result(std::move(result)) {} PlanRankingResult PreComputedRankingResultPlanner::extractPlanRankingResult() { + tassert(11282302, + "Expected `extractPlanRankingResult` to only be called with get executor deferred " + "feature flag enabled.", + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); return std::move(_result); } diff --git a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/single_solution_passthrough_planner.cpp b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/single_solution_passthrough_planner.cpp index 19d62f57eaf..aa7587c578e 100644 --- a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/single_solution_passthrough_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/single_solution_passthrough_planner.cpp @@ -43,7 +43,8 @@ PlanRankingResult SingleSolutionPassthroughPlanner::extractPlanRankingResult() { tassert(11974302, "Expected `extractPlanRankingResult` to only be called with get executor deferred " "feature flag enabled.", - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()); + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); return PlanRankingResult{.solutions = makeQsnResult(std::move(_querySolution)), .maybeExplainData = std::move(_maybeExplainData), .plannerParams = extractPlannerParams(), diff --git a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/sub_planner.cpp b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/sub_planner.cpp index f3f4324c35d..d3ba7866029 100644 --- a/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/sub_planner.cpp +++ b/src/mongo/db/exec/runtime_planners/exec_deferred_engine_choice_runtime_planner/sub_planner.cpp @@ -69,7 +69,8 @@ PlanRankingResult SubPlanner::extractPlanRankingResult() { tassert(11974303, "Expected `extractPlanRankingResult` to only be called with get executor deferred " "feature flag enabled.", - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()); + cq()->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)); auto querySolution = _subPlanStage->extractBestWholeQuerySolution(); return PlanRankingResult{.solutions = makeQsnResult(std::move(querySolution)), diff --git a/src/mongo/db/query/canonical_query.cpp b/src/mongo/db/query/canonical_query.cpp index b1812f675b5..d8104f1186d 100644 --- a/src/mongo/db/query/canonical_query.cpp +++ b/src/mongo/db/query/canonical_query.cpp @@ -179,8 +179,8 @@ void CanonicalQuery::initCq(boost::intrusive_ptr expCtx, // When the deferred engine choice path is enabled, it is safe to always optimize because // the SBE plan cache is not used, so there is no risk of caching an optimized-away // variable reference. - bool shouldOptimizeProj = - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled() || + bool shouldOptimizeProj = expCtx->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice) || expCtx->getSbeCompatibility() == SbeCompatibility::notCompatible || !_findCommand->getLet(); if (parsedFind->proj->requiresMatchDetails()) { diff --git a/src/mongo/db/query/canonical_query_encoder.cpp b/src/mongo/db/query/canonical_query_encoder.cpp index fa17b335de1..b16fabd8524 100644 --- a/src/mongo/db/query/canonical_query_encoder.cpp +++ b/src/mongo/db/query/canonical_query_encoder.cpp @@ -1355,10 +1355,10 @@ CanonicalQuery::QueryShapeString encodeClassic(const CanonicalQuery& cq) { // Encode the deferred engine selection feature flag so that cache entries cannot be shared when // the flag is changed. This could lead to unpredictable scenarios. - const bool deferredGetExecutorEnabled = - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled(); + const bool deferredGetExecutorEnabled = cq.getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice); keyBuilder << (deferredGetExecutorEnabled ? "t" : "f"); - if (MONGO_unlikely(deferredGetExecutorEnabled)) { + if (deferredGetExecutorEnabled) { encodeDeferredGetExecutorSubplanningData(cq, &keyBuilder); } else { encodeLegacyGetExecutorSubplanningData(cq, &keyBuilder); diff --git a/src/mongo/db/query/engine_selection.cpp b/src/mongo/db/query/engine_selection.cpp index d8aedf96098..b1a914d3968 100644 --- a/src/mongo/db/query/engine_selection.cpp +++ b/src/mongo/db/query/engine_selection.cpp @@ -125,7 +125,9 @@ bool isQuerySbeCompatible(const CollectionPtr& collection, // Queries against collections with a particular shape of compound hashed indexes are not // supported. - if (!feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled() && collection && + const bool deferredExecutorEnabled = cq.getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice); + if (!deferredExecutorEnabled && collection && collectionHasIndexWithHashedPathPrefixOfNonHashedPath(collection, expCtx)) { return false; } @@ -140,7 +142,7 @@ bool isQuerySbeCompatible(const CollectionPtr& collection, return false; } - if (solution && !isPlanSbeEligible(solution)) { + if (solution && !isPlanSbeCompatible(solution)) { return false; } @@ -220,8 +222,8 @@ EngineSelectionResult chooseEngine(OperationContext* opCtx, const QuerySolution* solution, const std::function& extendSolutionWithPipelineFn) { const bool hasSolution = solution != nullptr; - const bool deferredEngineChoice = - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled(); + const bool deferredEngineChoice = cq->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice); tassert(11742301, "Expected to choose engine based on solution only if " "featureFlagGetExecutorDeferredEngineChoice is " diff --git a/src/mongo/db/query/engine_selection_plan.cpp b/src/mongo/db/query/engine_selection_plan.cpp index 0f7ddb5e60d..c0d1c3c9e9b 100644 --- a/src/mongo/db/query/engine_selection_plan.cpp +++ b/src/mongo/db/query/engine_selection_plan.cpp @@ -602,7 +602,7 @@ static_assert(HasPreVisit); static_assert(HasPreVisit); } // namespace -bool isPlanSbeEligible(const QuerySolution* solution) { +bool isPlanSbeCompatible(const QuerySolution* solution) { return !treeMatchesAny( solution->root(), DistinctScanRule(), HashedIndexScanPatternRule(), AndHashOrSortedRule()); } diff --git a/src/mongo/db/query/engine_selection_plan.h b/src/mongo/db/query/engine_selection_plan.h index e627fc4223b..8f63d2db58d 100644 --- a/src/mongo/db/query/engine_selection_plan.h +++ b/src/mongo/db/query/engine_selection_plan.h @@ -38,7 +38,7 @@ namespace mongo { /** * Returns 'false' for query plans that can not be executed in SBE. */ -bool isPlanSbeEligible(const QuerySolution* solution); +bool isPlanSbeCompatible(const QuerySolution* solution); /** * Returns the engine of choice for executing the specified query plan. diff --git a/src/mongo/db/query/engine_selection_plan_test.cpp b/src/mongo/db/query/engine_selection_plan_test.cpp index b3b9ba19fe0..ebdd99e5ef6 100644 --- a/src/mongo/db/query/engine_selection_plan_test.cpp +++ b/src/mongo/db/query/engine_selection_plan_test.cpp @@ -140,7 +140,7 @@ TEST_F(EngineSelectionPlanFixture, DistinctScanEligibility) { BSONObj indexFields = fromjson("{a: 1}"); std::unique_ptr solution = makeDistinctScanPlan(indexFields); - ASSERT_FALSE(isPlanSbeEligible(solution.get())); + ASSERT_FALSE(isPlanSbeCompatible(solution.get())); } // Test eligibility of FETCH + IXSCAN plans with hashed indexes. @@ -149,14 +149,14 @@ TEST_F(EngineSelectionPlanFixture, HashedIndexIxScanEligibility) { { BSONObj indexFields = fromjson("{a: 1, m: 'hashed', 'm.m1': 1}"); std::unique_ptr solution = makeIndexScanFetchPlan(indexFields); - ASSERT_FALSE(isPlanSbeEligible(solution.get())); + ASSERT_FALSE(isPlanSbeCompatible(solution.get())); } // Single hashed index. { BSONObj indexFields = fromjson("{a: 'hashed'}"); std::unique_ptr solution = makeIndexScanFetchPlan(indexFields); - ASSERT_TRUE(isPlanSbeEligible(solution.get())); + ASSERT_TRUE(isPlanSbeCompatible(solution.get())); } } @@ -170,7 +170,7 @@ TEST_F(EngineSelectionPlanFixture, AndHashEligibility) { auto solution = std::make_unique(); solution->setRoot(std::move(andHash)); - ASSERT_FALSE(isPlanSbeEligible(solution.get())); + ASSERT_FALSE(isPlanSbeCompatible(solution.get())); } // Test eligibility of AND_SORTED plans. @@ -183,7 +183,7 @@ TEST_F(EngineSelectionPlanFixture, AndSortedEligibility) { auto solution = std::make_unique(); solution->setRoot(std::move(andSorted)); - ASSERT_FALSE(isPlanSbeEligible(solution.get())); + ASSERT_FALSE(isPlanSbeCompatible(solution.get())); } // Test selection of IXSCAN + FETCH plans. diff --git a/src/mongo/db/query/get_executor.cpp b/src/mongo/db/query/get_executor.cpp index d2db740587a..209761e32f9 100644 --- a/src/mongo/db/query/get_executor.cpp +++ b/src/mongo/db/query/get_executor.cpp @@ -1176,7 +1176,8 @@ StatusWith> getExecutorFind // paths. maybeUpgradeIdHackFlag(*canonicalQuery, collections.getMainCollection()); - if (MONGO_unlikely(feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled())) { + if (canonicalQuery->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice)) { return exec_deferred_engine_choice::getExecutorFindDeferredEngineChoice( opCtx, collections, diff --git a/src/mongo/db/query/get_executor_helpers.cpp b/src/mongo/db/query/get_executor_helpers.cpp index 2e9839eb976..f3658d4e928 100644 --- a/src/mongo/db/query/get_executor_helpers.cpp +++ b/src/mongo/db/query/get_executor_helpers.cpp @@ -92,11 +92,7 @@ void inspectPlannerResult( const std::unique_ptr& result, const boost::optional& replanningData) { // These assertions relate to replanning, so bail if the query did not replan. - // Also, these assertions do not apply to the deferred get_executor. The solution hash is - // checked after the plan ranking result is created, to update - // `replannedPlanIsCachedPlanCounter`. - if (!replanningData.has_value() || - feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()) { + if (!replanningData.has_value()) { return; } @@ -172,6 +168,9 @@ std::unique_ptr retryMakePlanner( CanonicalQuery* canonicalQuery, std::size_t plannerOptions, Pipeline* pipeline) { + const bool deferredExecutorEnabled = + canonicalQuery->getExpCtx()->getIfrContext()->getSavedFlagValue( + feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice); // We create this once on replanning and then make a copy for each QueryPlannerParams to own for // subsequent calls. boost::optional replanningData = boost::none; @@ -182,14 +181,17 @@ std::unique_ptr retryMakePlanner( // First try the single collection query parameters, as these would have been // generated with query settings if present. auto result = makePlanner(std::move(plannerParams)); - inspectPlannerResult(result, replanningData); + // The assertions in `inspectPlannerResult` do not apply when the deferred executor is + // enabled. + if (!deferredExecutorEnabled) { + inspectPlannerResult(result, replanningData); + } return result; } catch (const ExceptionFor&) { // The planner failed to generate a DISTINCT_SCAN for a distinct-like query. Remove // the distinct property and replan using SBE or subplanning as applicable. canonicalQuery->resetDistinct(); - if (canonicalQuery->isSbeCompatible() && - !feature_flags::gFeatureFlagGetExecutorDeferredEngineChoice.isEnabled()) { + if (canonicalQuery->isSbeCompatible() && !deferredExecutorEnabled) { // Stages still need to be finalized for SBE since classic was used previously. In // the deferred get_executor, the stages are finalized during lowering. finalizePipelineStages(pipeline, canonicalQuery); diff --git a/src/mongo/db/query/query_feature_flags.idl b/src/mongo/db/query/query_feature_flags.idl index fb7a0655d90..68e4fbb6d16 100644 --- a/src/mongo/db/query/query_feature_flags.idl +++ b/src/mongo/db/query/query_feature_flags.idl @@ -445,6 +445,7 @@ feature_flags: cpp_varname: gFeatureFlagGetExecutorDeferredEngineChoice fcv_gated: false default: false + incremental_rollout_phase: in_development featureFlagImprovedDepsAnalysis: description: "Feature flag to enable pipeline rewrites that require a dependency graph"