Support ordered first/last groupby aggregations in cudf-polars - #23600
Support ordered first/last groupby aggregations in cudf-polars#23600rjzamora wants to merge 26 commits into
Conversation
|
Auto-sync is disabled for draft pull requests in this repository. Workflows must be run manually. Contributors can view more details about this message here. |
|
/ok to test |
|
/ok to test |
📝 WalkthroughSummary by CodeRabbit
WalkthroughThe change adds ChangesSorted groupby aggregation support
Estimated code review effort: 4 (Complex) | ~60 minutes Suggested reviewers: 🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches 💡 1🛠️ Fix failing CI checks 💡
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
🧹 Nitpick comments (3)
python/cudf_polars/cudf_polars/dsl/ir.py (1)
2346-2349: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low valueFix the
request_groupskey annotation.
tuple[bool]describes a one-element tuple.SortedAgg.optionsstores variable-length tuples ofnulls_lastanddescendingflags, one per order key. Usetuple[bool, ...].♻️ Proposed annotation fix
request_groups: dict[ - tuple[tuple[bool, tuple[bool], tuple[bool]], tuple[expr.Expr, ...]], + tuple[tuple[bool, tuple[bool, ...], tuple[bool, ...]], tuple[expr.Expr, ...]], list[expr.NamedExpr], ] = {}🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@python/cudf_polars/cudf_polars/dsl/ir.py` around lines 2346 - 2349, Update the request_groups type annotation in the surrounding request-grouping logic so the order-options component uses tuple[bool, ...] rather than tuple[bool], matching the variable-length nulls_last and descending flags stored by SortedAgg.options; leave the other key and value types unchanged.python/cudf_polars/tests/test_groupby.py (1)
436-441: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winAdd coverage for two sorted aggregations that use different order keys.
Every new test groups sorted aggregations under one
(options, by_exprs)key._evaluate_sorted_aggregationsinpython/cudf_polars/cudf_polars/dsl/ir.pybuilds onerequest_groupsentry per distinct option and order-key pair, and it sorts and re-groups each entry separately. A query such aspl.col("val").sort_by("idx").first()together withpl.col("val").sort_by("seq", descending=True).first()exercises the multi-entry alignment path.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@python/cudf_polars/tests/test_groupby.py` around lines 436 - 441, Add test coverage in the groupby aggregation tests for multiple sorted aggregations using different order keys and sort directions, such as aggregations ordered by “idx” and by descending “seq”. Build the query with both aggregations and validate it through assert_gpu_result_equal with row-order checking, exercising _evaluate_sorted_aggregations’ multi-entry alignment path.python/cudf_polars/cudf_polars/streaming/actor_graph/groupby.py (1)
501-504: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winReuse the shared stable-sorted-agg predicate.
_has_stable_sorted_agginpython/cudf_polars/cudf_polars/streaming/groupby.pyencodes the same rule, but it walks the expression tree withtraversal. This check inspects only the top-levelne.value. The two predicates can diverge if aSortedAggever appears below the top level. Import and call the shared helper here.♻️ Proposed change
def _maintain_order(ir: GroupBy | Distinct) -> bool: if isinstance(ir, GroupBy): - return ir.maintain_order or any( - isinstance(ne.value, SortedAgg) and ne.value.options[0] - for ne in ir.agg_requests - ) + return ir.maintain_order or _has_stable_sorted_agg(ir.agg_requests)Import the helper from
cudf_polars.streaming.groupbyand drop the now-unusedSortedAggimport if nothing else in this module uses it.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@python/cudf_polars/cudf_polars/streaming/actor_graph/groupby.py` around lines 501 - 504, Update the stable-order check around the return expression to import and call the shared _has_stable_sorted_agg helper from cudf_polars.streaming.groupby, passing the aggregation requests instead of inspecting only top-level values. Remove the SortedAgg import if it is unused after this change.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Nitpick comments:
In `@python/cudf_polars/cudf_polars/dsl/ir.py`:
- Around line 2346-2349: Update the request_groups type annotation in the
surrounding request-grouping logic so the order-options component uses
tuple[bool, ...] rather than tuple[bool], matching the variable-length
nulls_last and descending flags stored by SortedAgg.options; leave the other key
and value types unchanged.
In `@python/cudf_polars/cudf_polars/streaming/actor_graph/groupby.py`:
- Around line 501-504: Update the stable-order check around the return
expression to import and call the shared _has_stable_sorted_agg helper from
cudf_polars.streaming.groupby, passing the aggregation requests instead of
inspecting only top-level values. Remove the SortedAgg import if it is unused
after this change.
In `@python/cudf_polars/tests/test_groupby.py`:
- Around line 436-441: Add test coverage in the groupby aggregation tests for
multiple sorted aggregations using different order keys and sort directions,
such as aggregations ordered by “idx” and by descending “seq”. Build the query
with both aggregations and validate it through assert_gpu_result_equal with
row-order checking, exercising _evaluate_sorted_aggregations’ multi-entry
alignment path.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro Plus
Run ID: dedc9819-027a-4a8f-85c9-22cb34453cf4
📒 Files selected for processing (9)
python/cudf_polars/cudf_polars/dsl/expr.pypython/cudf_polars/cudf_polars/dsl/expressions/aggregation.pypython/cudf_polars/cudf_polars/dsl/ir.pypython/cudf_polars/cudf_polars/dsl/utils/aggregations.pypython/cudf_polars/cudf_polars/streaming/actor_graph/groupby.pypython/cudf_polars/cudf_polars/streaming/groupby.pypython/cudf_polars/tests/streaming/test_groupby.pypython/cudf_polars/tests/streaming/test_spmd.pypython/cudf_polars/tests/test_groupby.py
Closes #23592
Adds cudf-polars support for grouped
sort_by(...).first()andsort_by(...).last()aggregations, including streaming decomposition for multi-partition execution.This enables expressions like: