-
Notifications
You must be signed in to change notification settings - Fork 10
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Array filtering support (Part #4): Postgres array filter impl. #191
Conversation
Codecov ReportAttention:
Additional details and impacted files@@ Coverage Diff @@
## main #191 +/- ##
=========================================
Coverage 79.57% 79.58%
- Complexity 956 957 +1
=========================================
Files 182 188 +6
Lines 4539 4623 +84
Branches 373 379 +6
=========================================
+ Hits 3612 3679 +67
- Misses 669 678 +9
- Partials 258 266 +8
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Sentry. |
Test Results 38 files ±0 38 suites ±0 32s ⏱️ ±0s Results for commit e63860b. ± Comparison against base commit 88a0440. This pull request removes 1 and adds 2 tests. Note that renamed tests count towards both.
♻️ This comment has been updated with latest results. |
|
||
@Override | ||
public PostgresQueryParser getPostgresQueryParser() { | ||
return baseVisitor.getPostgresQueryParser(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Curious: In the PostgresIdentifierReplacingExpressionVisitor
class, we initially verify the existence of the postgresQueryParser
. Afterward, we reference the baseVisitor
as follows:
postgresQueryParser != null ? postgresQueryParser : baseVisitor.getPostgresQueryParser()
Why aren't we doing the same here and directly accessing it from the baseVisitor
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, that is also not required as we are not passing in any baseVisitor
in the constructor. Updated there to get rid of the unnecessary conditional statement.
|
||
@Override | ||
public PostgresQueryParser getPostgresQueryParser() { | ||
return baseVisitor.getPostgresQueryParser(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same question as above: #191 (comment)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, that is also not required as we are not passing in any baseVisitor in the constructor. Updated there to get rid of the unnecessary conditional statement.
// Convert 'elements' to planets->'elements' where planets could be an alias for an upper | ||
// level array filter | ||
// Also, for the first time (if this was not under any nesting), use the field identifier | ||
// visitor to make it document->'elements' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
is this document->'elements'
correct? should it be `document->'planets'?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
document->'elements'
is correct. I've updated the code comments to be more clear.
.getArraySource() | ||
.accept(new PostgresIdentifierExpressionVisitor(postgresQueryParser)); | ||
|
||
// If the field name is 'elements.inner', just pick the last part as the alias ('inner') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could this be an issue if there are two array expressions, both having the same last part, such as inner
in planets.inner
and elements.inner
?
If so, creating an alias with the full path, like elements_inner
, might be a helpful solution.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, the alias is used within a smaller scope, so it shouldn't be an issue. But, yeah, it still makes sense to update it for clarity. Will do.
) | ||
*/ | ||
switch (expression.getOperator()) { | ||
case ANY: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If there are more operators, we should move the code for each operator to its dedicated function for readability? For instance, moving code of any operator to getFilterExpressionForAnyOperator()
here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sure
...ment-store/src/main/java/org/hypertrace/core/documentstore/postgres/utils/PostgresUtils.java
Outdated
Show resolved
Hide resolved
…/postgres/utils/PostgresUtils.java
So far, we do not have support for filtering by LHS arrays.
The PRs in this series aim to support LHS arrays in filters.
An LHS array can contain either primitives or documents.
In the case of a primitive LHS array, we can apply a relational operator on each element.
In the case of a document LHS array, we can apply a generic filter (including relational expression or logical expression or even another array filter expression)
Sample data:
Input query:
Get a list of solar systems with at least one planet not having either oxygen or water.
The filter API would look like
Sample MongoDB match stage query to be generated
Sample Postgres Query:
Notes:
ANY
operator is supported for nowNOT
logical operatorALL
can be achieved by usingNOT
twice to theANY
filter (before and after). E.g.:Fetch solar systems with all planets containing both oxygen and water
is equivalent toFetch solar systems with no planet without both oxygen and water
NONE
can be achieved by usingNOT
once beforeANY
, becauseNONE = NOT ANY
IN
instead ofOR
and=
, static importnot
andor
logical operators, etc.)This PR contains
Previous PRs
#173
#188
#189