diff options
author | David Percy <david.percy@mongodb.com> | 2021-05-24 21:00:29 +0000 |
---|---|---|
committer | Evergreen Agent <no-reply@evergreen.mongodb.com> | 2021-05-26 16:04:14 +0000 |
commit | 2f4c2c6bdca301934d32a9f3a1f6fc76946f7b11 (patch) | |
tree | 1bee00cedf7e29ec5ad52554a58f40fc9b3a4847 /src | |
parent | c9c9efbde4fbb3d9e6f0def1ae97a8e27d15ef41 (diff) | |
download | mongo-2f4c2c6bdca301934d32a9f3a1f6fc76946f7b11.tar.gz |
SERVER-57164 isVariableReference includes system variables
This fixes an invariant failure in DocumentSourceGroup.
Diffstat (limited to 'src')
-rw-r--r-- | src/mongo/db/pipeline/expression.h | 18 | ||||
-rw-r--r-- | src/mongo/db/pipeline/semantic_analysis.cpp | 2 |
2 files changed, 17 insertions, 3 deletions
diff --git a/src/mongo/db/pipeline/expression.h b/src/mongo/db/pipeline/expression.h index 7abd72e8543..74ff64a9991 100644 --- a/src/mongo/db/pipeline/expression.h +++ b/src/mongo/db/pipeline/expression.h @@ -1526,12 +1526,26 @@ public: class ExpressionFieldPath final : public Expression { public: - bool isRootFieldPath() const { + /** + * Checks whether this field path is exactly "$$ROOT". + */ + bool isROOT() const { return _variable == Variables::kRootId && _fieldPath.getPathLength() == 1; } + /** + * Checks whether this field path starts with a variable besides ROOT. + * + * For example, these are variable references: + * "$$NOW" + * "$$NOW.x" + * and these are not: + * "$x" + * "$$ROOT" + * "$$ROOT.x" + */ bool isVariableReference() const { - return Variables::isUserDefinedVariable(_variable); + return _variable != Variables::kRootId; } boost::intrusive_ptr<Expression> optimize() final; diff --git a/src/mongo/db/pipeline/semantic_analysis.cpp b/src/mongo/db/pipeline/semantic_analysis.cpp index 36f1985a913..c1613a6a85f 100644 --- a/src/mongo/db/pipeline/semantic_analysis.cpp +++ b/src/mongo/db/pipeline/semantic_analysis.cpp @@ -130,7 +130,7 @@ boost::optional<std::string> replaceRootNestsRoot( } auto&& [nestedName, expression] = children[0]; if (!dynamic_cast<ExpressionFieldPath*>(expression.get()) || - !dynamic_cast<ExpressionFieldPath*>(expression.get())->isRootFieldPath()) { + !dynamic_cast<ExpressionFieldPath*>(expression.get())->isROOT()) { return boost::none; } return nestedName; |