From c65a0a426d26054a5484ab2773582a811925b81b Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 18 Feb 2026 00:23:57 +0000 Subject: [PATCH 01/35] Remove scripts to tests rapidsmpf in separate jobs --- .github/workflows/pr.yaml | 11 ---- .github/workflows/test.yaml | 13 ----- ci/run_cudf_polars_pytests.sh | 9 ++- ci/run_cudf_polars_with_rapidsmpf_pytests.sh | 20 ------- ci/test_cudf_polars_with_rapidsmpf.sh | 60 -------------------- dependencies.yaml | 1 + 6 files changed, 9 insertions(+), 105 deletions(-) delete mode 100755 ci/run_cudf_polars_with_rapidsmpf_pytests.sh delete mode 100755 ci/test_cudf_polars_with_rapidsmpf.sh diff --git a/.github/workflows/pr.yaml b/.github/workflows/pr.yaml index 414b65bc1ff7..fa003e0a62a0 100644 --- a/.github/workflows/pr.yaml +++ b/.github/workflows/pr.yaml @@ -460,17 +460,6 @@ jobs: matrix_filter: map(select(.ARCH == "amd64")) | group_by(.CUDA_VER|split(".")|map(tonumber)|.[0]) | map(max_by([(.PY_VER|split(".")|map(tonumber)), (.CUDA_VER|split(".")|map(tonumber))])) build_type: pull-request script: "ci/test_wheel_cudf_polars.sh" - wheel-tests-cudf-polars-with-rapidsmpf: - needs: [wheel-build-cudf-polars, changed-files] - secrets: inherit - uses: rapidsai/shared-workflows/.github/workflows/wheels-test.yaml@main - if: fromJSON(needs.changed-files.outputs.changed_file_groups).test_python_wheels - with: - # This selects "ARCH=amd64 + the latest supported Python + CUDA" to minimize CI usage. - # (rapidsmpf compatibility already validated in rapidsmpf CI) - matrix_filter: map(select(.ARCH == "amd64")) | group_by(.CUDA_VER|split(".")|map(tonumber)|.[0]) | map(max_by([(.PY_VER|split(".")|map(tonumber)), (.CUDA_VER|split(".")|map(tonumber))])) - build_type: pull-request - script: "ci/test_cudf_polars_with_rapidsmpf.sh" cudf-polars-polars-tests: needs: [wheel-build-cudf-polars, changed-files] secrets: inherit diff --git a/.github/workflows/test.yaml b/.github/workflows/test.yaml index c79db0d0f761..87d06a219e6b 100644 --- a/.github/workflows/test.yaml +++ b/.github/workflows/test.yaml @@ -157,19 +157,6 @@ jobs: date: ${{ inputs.date }} sha: ${{ inputs.sha }} script: "ci/test_wheel_cudf_polars.sh" - wheel-tests-cudf-polars-with-rapidsmpf: - secrets: inherit - uses: rapidsai/shared-workflows/.github/workflows/wheels-test.yaml@main - with: - # This selects "ARCH=amd64 + the latest supported Python + CUDA" to minimize CI usage. - # (rapidsmpf compatibility already validated in rapidsmpf CI) - matrix_filter: map(select(.ARCH == "amd64")) | group_by(.CUDA_VER|split(".")|map(tonumber)|.[0]) | map(max_by([(.PY_VER|split(".")|map(tonumber)), (.CUDA_VER|split(".")|map(tonumber))])) - build_type: ${{ inputs.build_type }} - branch: ${{ inputs.branch }} - date: ${{ inputs.date }} - sha: ${{ inputs.sha }} - script: "ci/test_cudf_polars_with_rapidsmpf.sh" - continue-on-error: true cudf-polars-polars-tests: secrets: inherit uses: rapidsai/shared-workflows/.github/workflows/wheels-test.yaml@main diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index ce30428675e8..4e94fe61fa18 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -1,5 +1,5 @@ #!/bin/bash -# SPDX-FileCopyrightText: Copyright (c) 2024-2025, NVIDIA CORPORATION. +# SPDX-FileCopyrightText: Copyright (c) 2024-2026, NVIDIA CORPORATION. # SPDX-License-Identifier: Apache-2.0 set -euo pipefail @@ -18,6 +18,13 @@ python -m pytest --cache-clear "$@" tests --executor streaming # Test the "streaming" executor with small blocksize python -m pytest --cache-clear "$@" tests --executor streaming --blocksize-mode small +# Test the "streaming" executor with "rapidsmpf" runtime and the "single" cluster mode with dynamic planning +# TODO: Enable dynamic planning +python -m pytest --cache-clear "$@" tests \ + --executor streaming \ + --cluster single \ + --runtime rapidsmpf + # Run experimental tests with Distributed cluster python -m pytest --cache-clear "$@" "tests/experimental" \ --executor streaming \ diff --git a/ci/run_cudf_polars_with_rapidsmpf_pytests.sh b/ci/run_cudf_polars_with_rapidsmpf_pytests.sh deleted file mode 100755 index bff3ae9a7953..000000000000 --- a/ci/run_cudf_polars_with_rapidsmpf_pytests.sh +++ /dev/null @@ -1,20 +0,0 @@ -#!/bin/bash -# SPDX-FileCopyrightText: Copyright (c) 2025, NVIDIA CORPORATION. -# SPDX-License-Identifier: Apache-2.0 - -set -euo pipefail - -# Test cudf_polars with rapidsmpf integration -# This script runs experimental tests with single cluster mode and the rapidsmpf runtime - -# It is essential to cd into python/cudf_polars as `pytest-xdist` + `coverage` seem to work only at this directory level. - -# Support invoking run_cudf_polars_with_rapidsmpf_pytests.sh outside the script directory -cd "$(dirname "$(realpath "${BASH_SOURCE[0]}")")"/../python/cudf_polars/ - -# Run experimental tests with the "single" cluster mode and the "rapidsmpf" runtime -rapids-logger "Running experimental tests with the 'rapidsmpf' runtime" -timeout 10m python -m pytest --cache-clear "$@" "tests/experimental" \ - --executor streaming \ - --cluster single \ - --runtime rapidsmpf diff --git a/ci/test_cudf_polars_with_rapidsmpf.sh b/ci/test_cudf_polars_with_rapidsmpf.sh deleted file mode 100755 index 6e9ad45afe3d..000000000000 --- a/ci/test_cudf_polars_with_rapidsmpf.sh +++ /dev/null @@ -1,60 +0,0 @@ -#!/bin/bash -# SPDX-FileCopyrightText: Copyright (c) 2025-2026, NVIDIA CORPORATION. -# SPDX-License-Identifier: Apache-2.0 - -set -euo pipefail - -source rapids-init-pip - -rapids-logger "Download wheels" - -RAPIDS_PY_CUDA_SUFFIX="$(rapids-wheel-ctk-name-gen "${RAPIDS_CUDA_VERSION}")" -CUDF_POLARS_WHEELHOUSE=$(RAPIDS_PY_WHEEL_NAME="cudf_polars_${RAPIDS_PY_CUDA_SUFFIX}" RAPIDS_PY_WHEEL_PURE="1" rapids-download-wheels-from-github python) -LIBCUDF_WHEELHOUSE=$(RAPIDS_PY_WHEEL_NAME="libcudf_${RAPIDS_PY_CUDA_SUFFIX}" rapids-download-wheels-from-github cpp) -PYLIBCUDF_WHEELHOUSE=$(rapids-download-from-github "$(rapids-package-name "wheel_python" pylibcudf --stable --cuda "$RAPIDS_CUDA_VERSION")") - -rapids-logger "Installing cudf_polars and its dependencies (including rapidsmpf)" - -rapids-pip-retry install \ - -v \ - --constraint "${PIP_CONSTRAINT}" \ - "$(echo "${CUDF_POLARS_WHEELHOUSE}"/cudf_polars_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)[test,experimental,rapidsmpf]" \ - "$(echo "${LIBCUDF_WHEELHOUSE}"/libcudf_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)" \ - "$(echo "${PYLIBCUDF_WHEELHOUSE}"/pylibcudf_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)" - -rapids-logger "Run cudf_polars tests with rapidsmpf" - -# Get the latest polars version for testing -POLARS_VERSION=$(python ci/utils/fetch_polars_versions.py --latest-patch-only dependencies.yaml | awk '{print $NF}') - -rapids-logger "Installing polars==${POLARS_VERSION}" -pip install -U "polars==${POLARS_VERSION}" - -# shellcheck disable=SC2317 -function set_exitcode() -{ - EXITCODE=$? -} -EXITCODE=0 -trap set_exitcode ERR -set +e - -rapids-logger "Running cudf_polars tests with rapidsmpf" - -# Run cudf_polars tests with rapidsmpf using dedicated test runner -timeout 15m ./ci/run_cudf_polars_with_rapidsmpf_pytests.sh \ - --no-cov \ - --numprocesses=8 \ - --dist=worksteal \ - -v \ - --junitxml="${RAPIDS_TESTS_DIR}/junit-cudf-polars-rapidsmpf.xml" - -trap - ERR -set -e - -if [ ${EXITCODE} != 0 ]; then - rapids-logger "cudf_polars + rapidsmpf tests FAILED: exitcode ${EXITCODE}" -else - rapids-logger "cudf_polars + rapidsmpf tests PASSED" -fi -exit ${EXITCODE} diff --git a/dependencies.yaml b/dependencies.yaml index 0aae110609ee..4f5b57365624 100644 --- a/dependencies.yaml +++ b/dependencies.yaml @@ -114,6 +114,7 @@ files: - depends_on_cudf_kafka - depends_on_custreamz - depends_on_cudf_polars + - depends_on_rapidsmpf test_java: output: none includes: From 8fb8b7580a4c0647a9ee314c55e21033c82f31b0 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 18 Feb 2026 22:07:55 +0000 Subject: [PATCH 02/35] Ensure shuffle method is set to rapidsmpf --- ci/run_cudf_polars_pytests.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index 4e94fe61fa18..c2d8cedfb347 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -20,7 +20,7 @@ python -m pytest --cache-clear "$@" tests --executor streaming --blocksize-mode # Test the "streaming" executor with "rapidsmpf" runtime and the "single" cluster mode with dynamic planning # TODO: Enable dynamic planning -python -m pytest --cache-clear "$@" tests \ +CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD=rapidsmpf python -m pytest --cache-clear "$@" tests \ --executor streaming \ --cluster single \ --runtime rapidsmpf From 7452bd8fc0a78fc2d55f16617d47c93aa7bb9109 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 18 Feb 2026 22:39:16 +0000 Subject: [PATCH 03/35] Adjust some config tests --- python/cudf_polars/tests/test_config.py | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/test_config.py b/python/cudf_polars/tests/test_config.py index 6d2150becee2..9c5396ed0830 100644 --- a/python/cudf_polars/tests/test_config.py +++ b/python/cudf_polars/tests/test_config.py @@ -3,6 +3,7 @@ from __future__ import annotations +import os import sys from typing import Any, cast @@ -378,8 +379,12 @@ def test_scheduler_deprecated() -> None: def test_validate_shuffle_method_defaults( *, + monkeypatch: pytest.MonkeyPatch, rapidsmpf_distributed_available: bool, ) -> None: + # TODO: Can remove once removed from ci/run_cudf_polars_pytests.sh + # and the default shuffle method changes to "rapidsmpf" + monkeypatch.delenv("CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD", raising=False) config = ConfigOptions.from_polars_engine( pl.GPUEngine( executor="streaming", @@ -821,7 +826,12 @@ def test_cuda_stream_policy_from_env( elif runtime == "rapidsmpf": with pytest.raises(ValueError, match="The rapidsmpf streaming engine"): ConfigOptions.from_polars_engine(engine) - else: + elif ( + os.environ.get("CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD", "") != "rapidsmpf" + and not rapidsmpf_single_available + ): + # CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD set in ci/run_cudf_polars_pytests.sh + # Would raise since rapidsmpf shuffle requires rapidsmpf to be installed config = ConfigOptions.from_polars_engine(engine) assert config.cuda_stream_policy == env From 8623f22f11f7e6a751117daf5b2db1a5655e11f4 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 24 Feb 2026 01:28:04 +0000 Subject: [PATCH 04/35] Pass CUDF_POLARS__PARQUET_OPTIONS__USE_RAPIDSMPF_NATIVE --- ci/run_cudf_polars_pytests.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index c2d8cedfb347..9ac11b0dd93c 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -20,7 +20,7 @@ python -m pytest --cache-clear "$@" tests --executor streaming --blocksize-mode # Test the "streaming" executor with "rapidsmpf" runtime and the "single" cluster mode with dynamic planning # TODO: Enable dynamic planning -CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD=rapidsmpf python -m pytest --cache-clear "$@" tests \ +CUDF_POLARS__PARQUET_OPTIONS__USE_RAPIDSMPF_NATIVE=1 CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD=rapidsmpf python -m pytest --cache-clear "$@" tests \ --executor streaming \ --cluster single \ --runtime rapidsmpf From 6816244b820fd34461f008c285fb723e91e3ab1e Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Thu, 26 Feb 2026 18:32:38 +0000 Subject: [PATCH 05/35] Use small block size in unit tests --- ci/run_cudf_polars_pytests.sh | 1 + 1 file changed, 1 insertion(+) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index 31810f777bdd..646a6004c36e 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -22,6 +22,7 @@ python -m pytest --cache-clear "$@" tests --executor streaming --blocksize-mode # TODO: Enable dynamic planning CUDF_POLARS__PARQUET_OPTIONS__USE_RAPIDSMPF_NATIVE=1 CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD=rapidsmpf python -m pytest --cache-clear "$@" tests \ --executor streaming \ + --blocksize-mode small \ --cluster single \ --runtime rapidsmpf From 30294dd2b4dfac60f1aab2b72af37d427b82dfd1 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 19:45:09 +0000 Subject: [PATCH 06/35] Update test_log_query_plan after https://github.com/rapidsai/cudf/pull/21315 --- python/cudf_polars/tests/test_tracing.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/python/cudf_polars/tests/test_tracing.py b/python/cudf_polars/tests/test_tracing.py index f67fcda89a45..0cc6ed298d90 100644 --- a/python/cudf_polars/tests/test_tracing.py +++ b/python/cudf_polars/tests/test_tracing.py @@ -111,9 +111,9 @@ def test_log_query_plan() -> None: [sys.executable, "-c", code], env=env, stderr=subprocess.STDOUT ) - # Check for Query Plan event + # Check for Query Plan event generated from SerializablePlan assert b"Query Plan" in result assert b"scope=plan" in result or b"'scope': 'plan'" in result - assert b"ir_id" in result - assert b"ir_type" in result - assert b"children_ir_ids" in result + assert b"actor_ir_id" in result + assert b"actor_ir_type" in result + assert b"children" in result From 8e9cbd23d78b8f7fc084e8cab847b7e67c8f3863 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 19:51:23 +0000 Subject: [PATCH 07/35] Remove comment about dynamic planning --- ci/run_cudf_polars_pytests.sh | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index 646a6004c36e..6e1be8c7824c 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -18,8 +18,7 @@ python -m pytest --cache-clear "$@" tests --executor streaming # Test the "streaming" executor with small blocksize python -m pytest --cache-clear "$@" tests --executor streaming --blocksize-mode small -# Test the "streaming" executor with "rapidsmpf" runtime and the "single" cluster mode with dynamic planning -# TODO: Enable dynamic planning +# Test the "streaming" executor with "rapidsmpf" runtime and the "single" cluster mode CUDF_POLARS__PARQUET_OPTIONS__USE_RAPIDSMPF_NATIVE=1 CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD=rapidsmpf python -m pytest --cache-clear "$@" tests \ --executor streaming \ --blocksize-mode small \ From 2e30436d9ca148b1080d0931cb44fa9b083201f2 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 20:09:19 +0000 Subject: [PATCH 08/35] Fix shuffle fallback warning, check warning in test_grouped_rolling_unsorted_raises --- .../cudf_polars/experimental/sort.py | 4 ++-- python/cudf_polars/tests/conftest.py | 7 ++++++- python/cudf_polars/tests/test_rolling.py | 20 +++++++++++++++++-- 3 files changed, 26 insertions(+), 5 deletions(-) diff --git a/python/cudf_polars/cudf_polars/experimental/sort.py b/python/cudf_polars/cudf_polars/experimental/sort.py index a8fd2602a6ab..2f0f531a3fc9 100644 --- a/python/cudf_polars/cudf_polars/experimental/sort.py +++ b/python/cudf_polars/cudf_polars/experimental/sort.py @@ -566,8 +566,8 @@ def _( shuffle_method != config_options.executor.shuffle_method ): # pragma: no cover; Requires rapidsmpf _fallback_inform( - f"shuffle_method={shuffle_method} does not support maintain_order=True. " - "Falling back to shuffle_method='tasks'.", + f"shuffle_method={config_options.executor.shuffle_method} does not support maintain_order=True. " + f"Falling back to shuffle_method={shuffle_method}.", config_options, ) diff --git a/python/cudf_polars/tests/conftest.py b/python/cudf_polars/tests/conftest.py index 1a94eb038e13..de923c60cefd 100644 --- a/python/cudf_polars/tests/conftest.py +++ b/python/cudf_polars/tests/conftest.py @@ -1,4 +1,4 @@ -# SPDX-FileCopyrightText: Copyright (c) 2024-2025, NVIDIA CORPORATION & AFFILIATES. +# SPDX-FileCopyrightText: Copyright (c) 2024-2026, NVIDIA CORPORATION & AFFILIATES. # SPDX-License-Identifier: Apache-2.0 from __future__ import annotations @@ -28,6 +28,11 @@ def clear_memory_resource_cache(): cudf_polars.callback.default_memory_resource.cache_clear() +@pytest.fixture +def using_rapidsmpf(): + return cudf_polars.testing.asserts.DEFAULT_RUNTIME == "rapidsmpf" + + def pytest_addoption(parser): parser.addoption( "--executor", diff --git a/python/cudf_polars/tests/test_rolling.py b/python/cudf_polars/tests/test_rolling.py index a9a0617ff719..0b64ae031595 100644 --- a/python/cudf_polars/tests/test_rolling.py +++ b/python/cudf_polars/tests/test_rolling.py @@ -3,6 +3,7 @@ from __future__ import annotations +import contextlib from datetime import datetime import pytest @@ -133,7 +134,10 @@ def test_grouped_rolling(): assert_gpu_result_equal(q) -def test_grouped_rolling_unsorted_raises(): +@pytest.mark.filterwarnings( + "ignore:shuffle_method=tasks does not support maintain_order=True. Falling back to shuffle_method=tasks." +) +def test_grouped_rolling_unsorted_raises(using_rapidsmpf): df = pl.LazyFrame( { "keys": [1, None, 2, 1, 2, None], @@ -145,7 +149,19 @@ def test_grouped_rolling_unsorted_raises(): with pytest.raises(pl.exceptions.ComputeError): q.collect(engine="in-memory") - with pytest.raises(RuntimeError, match="Input for grouped rolling is not sorted"): + + fallback_warning = ( + pytest.warns( + UserWarning, + match="shuffle_method=rapidsmpf-single does not support maintain_order=True", + ) + if using_rapidsmpf + else contextlib.nullcontext() + ) + with ( + pytest.raises(RuntimeError, match="Input for grouped rolling is not sorted"), + fallback_warning, + ): q.collect(engine=pl.GPUEngine(raise_on_fail=True)) From b45dbd93a59c958197c94f0cc6d620620eb2da68 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 20:10:15 +0000 Subject: [PATCH 09/35] Try using threadpoolexecutor in contextmanager to fix resourcewarnings --- .../cudf_polars/cudf_polars/experimental/rapidsmpf/core.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/python/cudf_polars/cudf_polars/experimental/rapidsmpf/core.py b/python/cudf_polars/cudf_polars/experimental/rapidsmpf/core.py index 50df9f4d4ee7..d5a9316e3b94 100644 --- a/python/cudf_polars/cudf_polars/experimental/rapidsmpf/core.py +++ b/python/cudf_polars/cudf_polars/experimental/rapidsmpf/core.py @@ -273,11 +273,11 @@ def evaluate_pipeline( ) # Run the network - executor = ThreadPoolExecutor( + with ThreadPoolExecutor( max_workers=config_options.executor.rapidsmpf_py_executor_max_workers, thread_name_prefix="cpse", - ) - run_actor_network(actors=nodes, py_executor=executor) + ) as executor: + run_actor_network(actors=nodes, py_executor=executor) # Extract/return the concatenated result. # Keep chunks alive until after concatenation to prevent From acaef66bcc9384974cfeb60844d33153e5cc686f Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 22:42:27 +0000 Subject: [PATCH 10/35] Remove warning filter --- python/cudf_polars/tests/test_rolling.py | 3 --- 1 file changed, 3 deletions(-) diff --git a/python/cudf_polars/tests/test_rolling.py b/python/cudf_polars/tests/test_rolling.py index 0b64ae031595..792d83134e88 100644 --- a/python/cudf_polars/tests/test_rolling.py +++ b/python/cudf_polars/tests/test_rolling.py @@ -134,9 +134,6 @@ def test_grouped_rolling(): assert_gpu_result_equal(q) -@pytest.mark.filterwarnings( - "ignore:shuffle_method=tasks does not support maintain_order=True. Falling back to shuffle_method=tasks." -) def test_grouped_rolling_unsorted_raises(using_rapidsmpf): df = pl.LazyFrame( { From 2cd190bc81349e48971690045f3e823fe4d12b5f Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 22:49:18 +0000 Subject: [PATCH 11/35] Make warning more generic --- .../cudf_polars/tests/experimental/rapidsmpf/test_shuffler.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/experimental/rapidsmpf/test_shuffler.py b/python/cudf_polars/tests/experimental/rapidsmpf/test_shuffler.py index 23f38e2a6587..7927fc26efdd 100644 --- a/python/cudf_polars/tests/experimental/rapidsmpf/test_shuffler.py +++ b/python/cudf_polars/tests/experimental/rapidsmpf/test_shuffler.py @@ -198,7 +198,7 @@ def test_sort_stable_rapidsmpf_warns(): ) q = df.sort(by=["y", "z"], maintain_order=True) - with pytest.warns(UserWarning, match="Falling back to shuffle_method='tasks'."): + with pytest.warns(UserWarning, match="Falling back to shuffle_method"): assert_gpu_result_equal(q, engine=engine, check_row_order=True) From f6350880c8c1c534aec225029b9fb9e73254a81d Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 6 Mar 2026 23:50:49 +0000 Subject: [PATCH 12/35] Workaround xfail in test_merge_sorted_without_nulls --- python/cudf_polars/tests/test_merge_sorted.py | 21 ++++++++----------- 1 file changed, 9 insertions(+), 12 deletions(-) diff --git a/python/cudf_polars/tests/test_merge_sorted.py b/python/cudf_polars/tests/test_merge_sorted.py index 66c3a759f02e..ab654d8445eb 100644 --- a/python/cudf_polars/tests/test_merge_sorted.py +++ b/python/cudf_polars/tests/test_merge_sorted.py @@ -1,4 +1,4 @@ -# SPDX-FileCopyrightText: Copyright (c) 2025, NVIDIA CORPORATION & AFFILIATES. +# SPDX-FileCopyrightText: Copyright (c) 2025-2026, NVIDIA CORPORATION & AFFILIATES. # SPDX-License-Identifier: Apache-2.0 from __future__ import annotations @@ -9,17 +9,14 @@ from cudf_polars.testing.asserts import assert_gpu_result_equal -@pytest.mark.parametrize( - "descending", - [ - pytest.param( - True, - marks=pytest.mark.xfail(reason="polars/issues/21511"), - ), - False, - ], -) -def test_merge_sorted_without_nulls(descending): +@pytest.mark.parametrize("descending", [True, False]) +def test_merge_sorted_without_nulls(descending, request, using_rapidsmpf): + request.applymarker( + pytest.mark.xfail( + not using_rapidsmpf and descending, + reason="https://github.com/pola-rs/polars/issues/21511", + ) + ) df0 = pl.LazyFrame( {"name": ["steve", "elise", "bob"], "age": [42, 44, 18], "height": [5, 6, 5]} ).sort("age", descending=descending) From eeef8e88f31502b7d5df8632ccd2e5ab72a52bf8 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Sat, 7 Mar 2026 00:00:32 +0000 Subject: [PATCH 13/35] xfail the zero column, height tests for now --- python/cudf_polars/tests/test_dataframescan.py | 8 +++++++- python/cudf_polars/tests/test_scan.py | 8 +++++++- 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/python/cudf_polars/tests/test_dataframescan.py b/python/cudf_polars/tests/test_dataframescan.py index e002820fe383..2986c58b5fef 100644 --- a/python/cudf_polars/tests/test_dataframescan.py +++ b/python/cudf_polars/tests/test_dataframescan.py @@ -86,7 +86,13 @@ def test_dataframescan_with_decimals(): POLARS_VERSION_LT_138, reason="height parameter added in Polars 1.38", ) -def test_dataframescan_zero_width_with_rows(): +def test_dataframescan_zero_width_with_rows(request, using_rapidsmpf): + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf, + reason="https://github.com/rapidsai/cudf/issues/21644", + ) + ) df = pl.LazyFrame(height=5) q = df.select(pl.len()) assert_gpu_result_equal(q) diff --git a/python/cudf_polars/tests/test_scan.py b/python/cudf_polars/tests/test_scan.py index f2ab23468472..66f74b9bce12 100644 --- a/python/cudf_polars/tests/test_scan.py +++ b/python/cudf_polars/tests/test_scan.py @@ -702,7 +702,13 @@ def test_scan_tiny_file_not_compressed(tmp_path): reason="height parameter added in Polars 1.38", ) @pytest.mark.parametrize("engine", [None, NO_CHUNK_ENGINE]) -def test_scan_parquet_zero_width_with_limit(tmp_path, engine): +def test_scan_parquet_zero_width_with_limit(tmp_path, engine, request, using_rapidsmpf): + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf and engine is None, + reason="https://github.com/rapidsai/cudf/issues/21644", + ) + ) path = tmp_path / "zero_width.parquet" pl.LazyFrame(height=20).sink_parquet(path) q = pl.scan_parquet(path).head(5) From aa8c67bc47566447d101aad831019afbae241204 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Sat, 7 Mar 2026 00:13:05 +0000 Subject: [PATCH 14/35] Add cudf_polars trace to test_python_other, preemtive import or skip to tracing tests --- dependencies.yaml | 1 + .../cudf_polars/tests/experimental/rapidsmpf/test_tracing.py | 4 ++++ 2 files changed, 5 insertions(+) diff --git a/dependencies.yaml b/dependencies.yaml index b1dc716f0ee4..331ab54ccd0e 100644 --- a/dependencies.yaml +++ b/dependencies.yaml @@ -116,6 +116,7 @@ files: - depends_on_custreamz - depends_on_cudf_polars - depends_on_rapidsmpf + - cudf_polars_trace test_java: output: none includes: diff --git a/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py b/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py index eabb6c46e53f..041bd92e94a9 100644 --- a/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py +++ b/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py @@ -20,6 +20,8 @@ @pytest.mark.skipif(DEFAULT_CLUSTER != "single", reason="Requires 'single' cluster.") def test_structlog_streaming_node_events(): """Test that structlog emits 'Streaming Actor' events when tracing is enabled.""" + # TODO: Uncomment below once validated that structlog is in CI environments + # pytest.importorskip("structlog") # Run in subprocess to control CUDF_POLARS_LOG_TRACES environment variable code = textwrap.dedent("""\ import polars as pl @@ -62,6 +64,8 @@ def test_structlog_streaming_node_events(): @pytest.mark.skipif(DEFAULT_CLUSTER != "single", reason="Requires 'single' cluster.") def test_structlog_contains_expected_ir_types(): """Test that structlog output contains expected IR types for a query.""" + # TODO: Uncomment below once validated that structlog is in CI environments + # pytest.importorskip("structlog") code = textwrap.dedent("""\ import polars as pl import rmm From c02cb367745d33164650356acadedfaf54f5c3b4 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Mon, 9 Mar 2026 20:17:52 +0000 Subject: [PATCH 15/35] Re-enable importorskip --- .../tests/experimental/rapidsmpf/test_tracing.py | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py b/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py index 041bd92e94a9..1a445ba97a0d 100644 --- a/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py +++ b/python/cudf_polars/tests/experimental/rapidsmpf/test_tracing.py @@ -20,8 +20,7 @@ @pytest.mark.skipif(DEFAULT_CLUSTER != "single", reason="Requires 'single' cluster.") def test_structlog_streaming_node_events(): """Test that structlog emits 'Streaming Actor' events when tracing is enabled.""" - # TODO: Uncomment below once validated that structlog is in CI environments - # pytest.importorskip("structlog") + pytest.importorskip("structlog") # Run in subprocess to control CUDF_POLARS_LOG_TRACES environment variable code = textwrap.dedent("""\ import polars as pl @@ -64,8 +63,7 @@ def test_structlog_streaming_node_events(): @pytest.mark.skipif(DEFAULT_CLUSTER != "single", reason="Requires 'single' cluster.") def test_structlog_contains_expected_ir_types(): """Test that structlog output contains expected IR types for a query.""" - # TODO: Uncomment below once validated that structlog is in CI environments - # pytest.importorskip("structlog") + pytest.importorskip("structlog") code = textwrap.dedent("""\ import polars as pl import rmm From 931845771c961ac38dce5b7e22d544be8f4e2126 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 10 Mar 2026 01:09:05 +0000 Subject: [PATCH 16/35] Start adding xfails to failing rapidsmpf tests --- python/cudf_polars/tests/expressions/test_agg.py | 8 +++++++- python/cudf_polars/tests/expressions/test_len.py | 8 +++++++- python/cudf_polars/tests/test_drop_nulls.py | 10 +++++++++- python/cudf_polars/tests/test_select.py | 8 +++++++- 4 files changed, 30 insertions(+), 4 deletions(-) diff --git a/python/cudf_polars/tests/expressions/test_agg.py b/python/cudf_polars/tests/expressions/test_agg.py index f41130bb28ad..b367e14a2ba2 100644 --- a/python/cudf_polars/tests/expressions/test_agg.py +++ b/python/cudf_polars/tests/expressions/test_agg.py @@ -190,7 +190,13 @@ def test_implode_agg_unsupported(): assert_ir_translation_raises(q, NotImplementedError) -def test_decimal_aggs(decimal_df: pl.LazyFrame) -> None: +def test_decimal_aggs(decimal_df: pl.LazyFrame, using_rapidsmpf, request) -> None: + request.applymarker( + pytest.mark.xfail( + condition=using_rapidsmpf, + reason="https://github.com/rapidsai/cudf/issues/21645", + ) + ) q = decimal_df.with_columns( sum=pl.col("a").sum(), min=pl.col("a").min(), diff --git a/python/cudf_polars/tests/expressions/test_len.py b/python/cudf_polars/tests/expressions/test_len.py index ccc903aa99d8..10efadd879a0 100644 --- a/python/cudf_polars/tests/expressions/test_len.py +++ b/python/cudf_polars/tests/expressions/test_len.py @@ -30,7 +30,13 @@ def test_len(dtype, empty): @pytest.mark.parametrize("data", [[1, 2, 3], [1, 2, None]]) -def test_col_len(data): +def test_col_len(data, using_rapidsmpf, request): + request.applymarker( + pytest.mark.xfail( + condition=using_rapidsmpf, + reason="https://github.com/rapidsai/cudf/issues/21645", + ) + ) data = {"a": list("xyz"), "b": data} q = pl.LazyFrame(data).select( pl.col("a").len().alias("l"), diff --git a/python/cudf_polars/tests/test_drop_nulls.py b/python/cudf_polars/tests/test_drop_nulls.py index 0fe9b963eddb..56da63763b5b 100644 --- a/python/cudf_polars/tests/test_drop_nulls.py +++ b/python/cudf_polars/tests/test_drop_nulls.py @@ -42,7 +42,15 @@ def test_drop_null(null_data): [0, pl.col("a").mean(), pl.col("b")], ids=["scalar", "aggregation", "column_expression"], ) -def test_fill_null(null_data, value): +def test_fill_null(null_data, value, using_rapidsmpf, request): + request.applymarker( + pytest.mark.xfail( + condition=using_rapidsmpf + and "mean" in str(value) + and len(null_data.collect()) == 2, + reason="https://github.com/rapidsai/cudf/issues/21721", + ) + ) q = null_data.select(pl.col("a").fill_null(value)) assert_gpu_result_equal(q) diff --git a/python/cudf_polars/tests/test_select.py b/python/cudf_polars/tests/test_select.py index ac9dbb90d0c0..7f85e233de34 100644 --- a/python/cudf_polars/tests/test_select.py +++ b/python/cudf_polars/tests/test_select.py @@ -87,7 +87,13 @@ def test_select_with_cse_no_agg(): assert_gpu_result_equal(query) -def test_select_with_cse_with_agg(): +def test_select_with_cse_with_agg(using_rapidsmpf, request): + request.applymarker( + pytest.mark.xfail( + condition=using_rapidsmpf, + reason="https://github.com/rapidsai/cudf/issues/21645", + ) + ) df = pl.LazyFrame({"a": [1, 2, 3]}) expr = pl.col("a") + pl.col("a") asum = pl.col("a").sum() + pl.col("a").sum() From 202cca57214e2850370b2f63306094c3c4bb16ca Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 10 Mar 2026 18:11:40 +0000 Subject: [PATCH 17/35] Change comments to echo for log --- ci/run_cudf_polars_pytests.sh | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index 6e1be8c7824c..86fa655f2556 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -9,29 +9,29 @@ set -euo pipefail # Support invoking run_cudf_polars_pytests.sh outside the script directory cd "$(dirname "$(realpath "${BASH_SOURCE[0]}")")"/../python/cudf_polars/ -# Test the "in-memory" executor +echo "Test the in-memory executor" python -m pytest --cache-clear "$@" tests --executor in-memory -# Test the default "streaming" executor +echo "Test the default streaming executor" python -m pytest --cache-clear "$@" tests --executor streaming -# Test the "streaming" executor with small blocksize +echo "Test the streaming executor with small blocksize" python -m pytest --cache-clear "$@" tests --executor streaming --blocksize-mode small -# Test the "streaming" executor with "rapidsmpf" runtime and the "single" cluster mode +echo "Test the (future default) streaming executor with rapidsmpf" CUDF_POLARS__PARQUET_OPTIONS__USE_RAPIDSMPF_NATIVE=1 CUDF_POLARS__EXECUTOR__SHUFFLE_METHOD=rapidsmpf python -m pytest --cache-clear "$@" tests \ --executor streaming \ --blocksize-mode small \ --cluster single \ --runtime rapidsmpf -# Run experimental tests with Distributed cluster +echo "Run experimental tests with Distributed cluster" python -m pytest --cache-clear "$@" "tests/experimental" \ --executor streaming \ --cluster distributed \ --cov-fail-under=0 # No code-coverage requirement for these tests. -# Run experimental tests with the "distributed" cluster mode and the "rapidsmpf" runtime +echo "Run experimental tests with the distributed cluster mode and the rapidsmpf runtime" python -m pytest --cache-clear "$@" "tests/experimental" \ --executor streaming \ --cluster distributed \ From 415d5eafc0f540eb25aeec486ef2e234606078e9 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 10 Mar 2026 19:02:35 +0000 Subject: [PATCH 18/35] Add xfails to test_groupby_sorted_keys --- python/cudf_polars/tests/test_groupby.py | 28 +++++++++++++++++++++++- 1 file changed, 27 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index 8713185f56f5..d30de9660dfe 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -136,7 +136,33 @@ def test_groupby(df: pl.LazyFrame, maintain_order, keys, exprs): assert_gpu_result_equal(q, check_exact=False) -def test_groupby_sorted_keys(df: pl.LazyFrame, keys, exprs): +def test_groupby_sorted_keys(df: pl.LazyFrame, keys, exprs, using_rapidsmpf, request): + failing_rapidsmpf_nodeids = { + 'test_groupby_sorted_keys[col("key1")-]', + 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("int").first()-col("float").last()]', + 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("float").quantile()4]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-float-int]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[(col("float")) + (col("int"))]]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("int32").sum()]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("int32").mean()]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[([(col("float").max()) - (col("int").min())]) + (col("int").max())]]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[(col("float")) - (dyn int: 2)].max()]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").sum().round()0]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").round().sum()0]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("int").first()-col("float").last()]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").quantile()2]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-[([(col("float").max()) - (col("int").min())]) + (col("int").max())]]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("int").first()-col("float").last()]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()0]', + } + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf + and not exprs + and request.node.name in failing_rapidsmpf_nodeids, + reason="https://github.com/rapidsai/cudf/issues/21642", + ) + ) sorted_keys = [ key.sort(descending=descending) for key, descending in zip(keys, itertools.cycle([False, True])) From ab95752ffd0386b31a17044d7a9559ff7aa72bbc Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 10 Mar 2026 19:04:09 +0000 Subject: [PATCH 19/35] Missed 2 tests --- python/cudf_polars/tests/test_groupby.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index d30de9660dfe..02ce9036993c 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -139,6 +139,8 @@ def test_groupby(df: pl.LazyFrame, maintain_order, keys, exprs): def test_groupby_sorted_keys(df: pl.LazyFrame, keys, exprs, using_rapidsmpf, request): failing_rapidsmpf_nodeids = { 'test_groupby_sorted_keys[col("key1")-]', + 'test_groupby_sorted_keys[col("key2")-]', + 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-]', 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("int").first()-col("float").last()]', 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("float").quantile()4]', 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-float-int]', From 17f84a4d8067f436e2d45fced2accd4296eb11bc Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 10 Mar 2026 19:19:22 +0000 Subject: [PATCH 20/35] xfail tests in test_groupby with rapidsmpf --- python/cudf_polars/tests/test_groupby.py | 26 +++++++++++++++++++++++- 1 file changed, 25 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index 02ce9036993c..832d7130af65 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -126,7 +126,31 @@ def maintain_order(request): return request.param -def test_groupby(df: pl.LazyFrame, maintain_order, keys, exprs): +def test_groupby( + df: pl.LazyFrame, maintain_order, keys, exprs, using_rapidsmpf, request +): + failing_rapidsmpf_nodeids = { + 'test_groupby[maintain_order-col("key1")-col("int32").mean()]', + 'test_groupby[maintain_order-col("key1")-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby[maintain_order-col("key2")-col("int32").mean()]', + 'test_groupby[maintain_order-col("key2")-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby[maintain_order-col("key1")-dyn int: 1-col("int32").mean()]', + 'test_groupby[maintain_order-col("key1")-dyn int: 1-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby[maintain_order-[(col("key1")) * (col("key2"))]-col("int32").mean()]', + 'test_groupby[maintain_order-[(col("key1")) * (col("key2"))]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby[maintain_order-col("key1")-col("key2")-col("int32").mean()]', + 'test_groupby[maintain_order-col("key1")-col("key2")-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby[maintain_order-[(col("key1")) == (col("key2"))]-col("int32").mean()]', + 'test_groupby[maintain_order-[(col("key1")) == (col("key2"))]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby[maintain_order-col("key2")-[(col("key1")) == (1)]-col("int32").mean()]', + 'test_groupby[maintain_order-col("key2")-[(col("key1")) == (1)]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + } + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf and request.node.name in failing_rapidsmpf_nodeids, + reason="https://github.com/rapidsai/cudf/issues/21642 and probably mean calculation referenced in https://github.com/rapidsai/cudf/issues/21721", + ) + ) q = df.group_by(*keys, maintain_order=maintain_order).agg(*exprs) if not maintain_order: From 35e2d15d42ea3c0502f5f54d9a47a630d6370a82 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Tue, 10 Mar 2026 21:22:52 +0000 Subject: [PATCH 21/35] Remove not expr condition --- python/cudf_polars/tests/test_groupby.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index 832d7130af65..e3f323c99962 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -183,9 +183,7 @@ def test_groupby_sorted_keys(df: pl.LazyFrame, keys, exprs, using_rapidsmpf, req } request.applymarker( pytest.mark.xfail( - using_rapidsmpf - and not exprs - and request.node.name in failing_rapidsmpf_nodeids, + using_rapidsmpf and request.node.name in failing_rapidsmpf_nodeids, reason="https://github.com/rapidsai/cudf/issues/21642", ) ) From 70791cd108402dc446c2b75acb970656f383c73b Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 00:08:23 +0000 Subject: [PATCH 22/35] Change xfail nodes again, may need to skip due to unstable shuffling --- python/cudf_polars/tests/test_groupby.py | 28 ++++++++++++++---------- 1 file changed, 17 insertions(+), 11 deletions(-) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index e3f323c99962..2ec61a87a410 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -165,21 +165,27 @@ def test_groupby_sorted_keys(df: pl.LazyFrame, keys, exprs, using_rapidsmpf, req 'test_groupby_sorted_keys[col("key1")-]', 'test_groupby_sorted_keys[col("key2")-]', 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-]', - 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("int").first()-col("float").last()]', - 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("float").quantile()4]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-float-int]', 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[(col("float")) + (col("int"))]]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("int32").sum()]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("int32").mean()]', 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[([(col("float").max()) - (col("int").min())]) + (col("int").max())]]', 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[(col("float")) - (dyn int: 2)].max()]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").sum().round()0]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").round().sum()0]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("int").first()-col("float").last()]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").quantile()2]', 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-[([(col("float").max()) - (col("int").min())]) + (col("int").max())]]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("int").first()-col("float").last()]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()0]', + 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("float").sum().round()0]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").is_not_null()]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").mean()-col("int").std()]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").sum().round()1]', + 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").round().sum()1]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-int]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-[(col("float")) + (col("int"))]]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("int32").mean()]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").round().sum()0]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").sum().round()1]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").round().sum()1]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("int").sum()-col("string").str.replace(["h", "foo"])]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()1]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()3]', + 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()4]', } request.applymarker( pytest.mark.xfail( From 5da9dac417dee2fe5ae12f92f5b4f69f33324212 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 15:53:57 +0000 Subject: [PATCH 23/35] Mark test_groupby_sorted_keys as xfail strict=False --- python/cudf_polars/tests/test_groupby.py | 31 +++--------------------- 1 file changed, 3 insertions(+), 28 deletions(-) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index 2ec61a87a410..302c86740df5 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -161,36 +161,11 @@ def test_groupby( def test_groupby_sorted_keys(df: pl.LazyFrame, keys, exprs, using_rapidsmpf, request): - failing_rapidsmpf_nodeids = { - 'test_groupby_sorted_keys[col("key1")-]', - 'test_groupby_sorted_keys[col("key2")-]', - 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[(col("float")) + (col("int"))]]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[([(col("float").max()) - (col("int").min())]) + (col("int").max())]]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-[(col("float")) - (dyn int: 2)].max()]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-[([(col("float").max()) - (col("int").min())]) + (col("int").max())]]', - 'test_groupby_sorted_keys[[(col("key1")) * (col("key2"))]-col("float").sum().round()0]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").is_not_null()]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").mean()-col("int").std()]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").sum().round()1]', - 'test_groupby_sorted_keys[[(col("key1")) == (col("key2"))]-col("float").round().sum()1]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-int]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-[(col("float")) + (col("int"))]]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("int32").mean()]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").round().sum()0]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").sum().round()1]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").round().sum()1]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("int").sum()-col("string").str.replace(["h", "foo"])]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()1]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()3]', - 'test_groupby_sorted_keys[col("key2")-[(col("key1")) == (1)]-col("float").quantile()4]', - } request.applymarker( pytest.mark.xfail( - using_rapidsmpf and request.node.name in failing_rapidsmpf_nodeids, - reason="https://github.com/rapidsai/cudf/issues/21642", + using_rapidsmpf, + strict=False, + reason="https://github.com/rapidsai/cudf/issues/21642 - no deterministic sort for keys", ) ) sorted_keys = [ From 916b164265054b1103b4d3c8389b3e9a095409d8 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 15:56:14 +0000 Subject: [PATCH 24/35] xfail test_shift_by_expression_get --- python/cudf_polars/tests/expressions/test_shift.py | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/expressions/test_shift.py b/python/cudf_polars/tests/expressions/test_shift.py index dc7275c80508..e674b3fb4dba 100644 --- a/python/cudf_polars/tests/expressions/test_shift.py +++ b/python/cudf_polars/tests/expressions/test_shift.py @@ -117,7 +117,13 @@ def test_shift_by_expression_last(): assert_gpu_result_equal(q) -def test_shift_by_expression_get(): +def test_shift_by_expression_get(using_rapidsmpf, request): + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf, + reason="Shifts by 1 instead of 2 for rapidsmpf runtime", + ) + ) df = pl.LazyFrame({"a": [1, 2, 3, 4, 5], "b": [2, 2, 2, 2, 2]}) q = df.select(pl.col("a").shift(n=pl.col("b").get(2))) assert_gpu_result_equal(q) From 0990377340a70b500881cabdc14e44111dc7cbae Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 16:00:46 +0000 Subject: [PATCH 25/35] xfail params of test_non_coalesce_join --- python/cudf_polars/tests/test_join.py | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/test_join.py b/python/cudf_polars/tests/test_join.py index fc1a384957ea..49c3e981229f 100644 --- a/python/cudf_polars/tests/test_join.py +++ b/python/cudf_polars/tests/test_join.py @@ -70,7 +70,20 @@ def test_join_maintain_order(left, right, maintain_order): ["c", "a"], ], ) -def test_non_coalesce_join(left, right, how, nulls_equal, join_expr): +def test_non_coalesce_join( + left, right, how, nulls_equal, join_expr, request, using_rapidsmpf +): + failing_rapidsmpf_nodeids = { + "test_non_coalesce_join[full-nulls_not_equal-join_expr1]", + "test_non_coalesce_join[left-nulls_equal-join_expr1]", + "test_non_coalesce_join[left-nulls_not_equal-join_expr2]", + } + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf and request.node.name in failing_rapidsmpf_nodeids, + reason="Maybe https://github.com/rapidsai/cudf/issues/21742?", + ) + ) query = left.join( right, on=join_expr, how=how, nulls_equal=nulls_equal, coalesce=False ) From 0b54d5017ff37aecc98f68e668d1d7a906fa32fe Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 18:28:19 +0000 Subject: [PATCH 26/35] Revert xfails on test_shift_by_expression_get and test_non_coalesce_join --- .../cudf_polars/tests/expressions/test_shift.py | 8 +------- python/cudf_polars/tests/test_join.py | 15 +-------------- 2 files changed, 2 insertions(+), 21 deletions(-) diff --git a/python/cudf_polars/tests/expressions/test_shift.py b/python/cudf_polars/tests/expressions/test_shift.py index e674b3fb4dba..dc7275c80508 100644 --- a/python/cudf_polars/tests/expressions/test_shift.py +++ b/python/cudf_polars/tests/expressions/test_shift.py @@ -117,13 +117,7 @@ def test_shift_by_expression_last(): assert_gpu_result_equal(q) -def test_shift_by_expression_get(using_rapidsmpf, request): - request.applymarker( - pytest.mark.xfail( - using_rapidsmpf, - reason="Shifts by 1 instead of 2 for rapidsmpf runtime", - ) - ) +def test_shift_by_expression_get(): df = pl.LazyFrame({"a": [1, 2, 3, 4, 5], "b": [2, 2, 2, 2, 2]}) q = df.select(pl.col("a").shift(n=pl.col("b").get(2))) assert_gpu_result_equal(q) diff --git a/python/cudf_polars/tests/test_join.py b/python/cudf_polars/tests/test_join.py index 49c3e981229f..fc1a384957ea 100644 --- a/python/cudf_polars/tests/test_join.py +++ b/python/cudf_polars/tests/test_join.py @@ -70,20 +70,7 @@ def test_join_maintain_order(left, right, maintain_order): ["c", "a"], ], ) -def test_non_coalesce_join( - left, right, how, nulls_equal, join_expr, request, using_rapidsmpf -): - failing_rapidsmpf_nodeids = { - "test_non_coalesce_join[full-nulls_not_equal-join_expr1]", - "test_non_coalesce_join[left-nulls_equal-join_expr1]", - "test_non_coalesce_join[left-nulls_not_equal-join_expr2]", - } - request.applymarker( - pytest.mark.xfail( - using_rapidsmpf and request.node.name in failing_rapidsmpf_nodeids, - reason="Maybe https://github.com/rapidsai/cudf/issues/21742?", - ) - ) +def test_non_coalesce_join(left, right, how, nulls_equal, join_expr): query = left.join( right, on=join_expr, how=how, nulls_equal=nulls_equal, coalesce=False ) From c7b6d5d06c47d671a7f3b9a5da00249df4f66c55 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 20:52:28 +0000 Subject: [PATCH 27/35] xfail strict=False test_non_coalesce_join --- python/cudf_polars/tests/test_join.py | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/test_join.py b/python/cudf_polars/tests/test_join.py index fc1a384957ea..a891d669c901 100644 --- a/python/cudf_polars/tests/test_join.py +++ b/python/cudf_polars/tests/test_join.py @@ -70,7 +70,16 @@ def test_join_maintain_order(left, right, maintain_order): ["c", "a"], ], ) -def test_non_coalesce_join(left, right, how, nulls_equal, join_expr): +def test_non_coalesce_join( + left, right, how, nulls_equal, join_expr, using_rapidsmpf, request +): + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf, + strict=False, + reason="Non deterministic sort/join on nulls", + ) + ) query = left.join( right, on=join_expr, how=how, nulls_equal=nulls_equal, coalesce=False ) From b29fc5e05b7f0d8ff6bf6ccd1eaddf52aad4df03 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Wed, 11 Mar 2026 23:32:02 +0000 Subject: [PATCH 28/35] Ensure rapidsmpf is installed in cudf_polars wheels tests --- ci/test_wheel_cudf_polars.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ci/test_wheel_cudf_polars.sh b/ci/test_wheel_cudf_polars.sh index abdaeebd1659..5865468802b6 100755 --- a/ci/test_wheel_cudf_polars.sh +++ b/ci/test_wheel_cudf_polars.sh @@ -30,7 +30,7 @@ rapids-pip-retry install \ -v \ --constraint ./constraints.txt \ --constraint "${PIP_CONSTRAINT}" \ - "$(echo "${CUDF_POLARS_WHEELHOUSE}"/cudf_polars_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)[test,experimental]" \ + "$(echo "${CUDF_POLARS_WHEELHOUSE}"/cudf_polars_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)[test,experimental,rapidsmpf]" \ "$(echo "${LIBCUDF_WHEELHOUSE}"/libcudf_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)" \ "$(echo "${PYLIBCUDF_WHEELHOUSE}"/pylibcudf_"${RAPIDS_PY_CUDA_SUFFIX}"*.whl)" From 384f878d16241bb21a944b858a49f40f0e8c5e95 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 13 Mar 2026 18:46:32 +0000 Subject: [PATCH 29/35] Fix shift not passing stream to_py --- python/cudf_polars/cudf_polars/dsl/expressions/unary.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/python/cudf_polars/cudf_polars/dsl/expressions/unary.py b/python/cudf_polars/cudf_polars/dsl/expressions/unary.py index 70fc223d965c..275376c132a6 100644 --- a/python/cudf_polars/cudf_polars/dsl/expressions/unary.py +++ b/python/cudf_polars/cudf_polars/dsl/expressions/unary.py @@ -522,9 +522,7 @@ def do_evaluate( offset = n_expr.value else: n_col = n_expr.evaluate(df, context=context) - offset_py = plc.copying.get_element( - n_col.obj, 0, stream=df.stream - ).to_py() + offset_py = n_col.obj_scalar(stream=df.stream).to_py(stream=df.stream) assert isinstance(offset_py, int) offset = offset_py if self.name == "shift": From d2095ae0b9e0a9ddf5ff820654da6aaf890ed3df Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Fri, 13 Mar 2026 21:44:48 +0000 Subject: [PATCH 30/35] nocover a importerror, keep skipping test_groupby for older polars versions --- .../experimental/dask_registers.py | 4 ++-- python/cudf_polars/tests/test_groupby.py | 22 +++++++++++++++++++ 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/python/cudf_polars/cudf_polars/experimental/dask_registers.py b/python/cudf_polars/cudf_polars/experimental/dask_registers.py index 15895e209db0..94334ccbc57f 100644 --- a/python/cudf_polars/cudf_polars/experimental/dask_registers.py +++ b/python/cudf_polars/cudf_polars/experimental/dask_registers.py @@ -1,4 +1,4 @@ -# SPDX-FileCopyrightText: Copyright (c) 2024-2025, NVIDIA CORPORATION & AFFILIATES. +# SPDX-FileCopyrightText: Copyright (c) 2024-2026, NVIDIA CORPORATION & AFFILIATES. # SPDX-License-Identifier: Apache-2.0 """Dask function registrations such as serializers and dispatch implementations.""" @@ -215,7 +215,7 @@ def _(x: DataFrame) -> int: from rapidsmpf.integrations.dask.spilling import register_dask_serialize register_dask_serialize() # pragma: no cover; rapidsmpf dependency not included yet - except ImportError: + except ImportError: # pragma: no cover pass # Register the tokenizer for NamedExpr and DataType. This is a performance diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index 302c86740df5..60c5f173bf36 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -151,6 +151,28 @@ def test_groupby( reason="https://github.com/rapidsai/cudf/issues/21642 and probably mean calculation referenced in https://github.com/rapidsai/cudf/issues/21721", ) ) + failing_rapidsmpf_nodeids_lt_1_36 = { + 'test_groupby[maintain_order-col("key2")-[(col("key1")) == (dyn int: 1.strict_cast(Int64))]-col("uint16_with_null").sum()-col("uint16_with_null").mean().alias("mean")]' + } + request.applymarker( + pytest.mark.xfail( + using_rapidsmpf + and POLARS_VERSION_LT_136 + and request.node.name in failing_rapidsmpf_nodeids_lt_1_36, + reason="Type mismatch in columns to concatenate.", + ) + ) + segfaulting_rapidsmpf_nodeids = { + 'test_groupby[maintain_order-col("key2")-[(col("key1")) == (dyn int: 1.strict_cast(Int64))]-col("int32").mean()]' + } + if ( + using_rapidsmpf + and POLARS_VERSION_LT_136 + and request.node.name in segfaulting_rapidsmpf_nodeids + ): + pytest.skip( + "Usually raises 'Type mismatch in columns to concatenate' but can also segfault." + ) q = df.group_by(*keys, maintain_order=maintain_order).agg(*exprs) if not maintain_order: From d74ba8ba97f488ac14568b46a917ffb720fac2aa Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Mon, 16 Mar 2026 17:24:52 +0000 Subject: [PATCH 31/35] Ignore coverage requirements for new job --- ci/run_cudf_polars_pytests.sh | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index 86fa655f2556..8745a762bb11 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -23,7 +23,8 @@ CUDF_POLARS__PARQUET_OPTIONS__USE_RAPIDSMPF_NATIVE=1 CUDF_POLARS__EXECUTOR__SHUF --executor streaming \ --blocksize-mode small \ --cluster single \ - --runtime rapidsmpf + --runtime rapidsmpf \ + --cov-fail-under=0 # TODO? missing coverage may be due to old task-based paths echo "Run experimental tests with Distributed cluster" python -m pytest --cache-clear "$@" "tests/experimental" \ From 1144a2ade7b7251bcc698670f5ae0a09a7a51eb6 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Mon, 16 Mar 2026 20:14:14 +0000 Subject: [PATCH 32/35] Change more Rapidsmpf Shuffler.wait_on to Shuffler.wait --- python/cudf_polars/cudf_polars/experimental/shuffle.py | 2 +- python/cudf_polars/cudf_polars/experimental/sort.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/python/cudf_polars/cudf_polars/experimental/shuffle.py b/python/cudf_polars/cudf_polars/experimental/shuffle.py index 0cd70ea375ef..efb134abf7cd 100644 --- a/python/cudf_polars/cudf_polars/experimental/shuffle.py +++ b/python/cudf_polars/cudf_polars/experimental/shuffle.py @@ -104,7 +104,7 @@ def extract_partition( context = get_worker_context() - shuffler.wait_on(partition_id) + shuffler.wait() column_names = options["column_names"] dtypes = options["dtypes"] return DataFrame.from_table( diff --git a/python/cudf_polars/cudf_polars/experimental/sort.py b/python/cudf_polars/cudf_polars/experimental/sort.py index 2f0f531a3fc9..98b2cdb0f610 100644 --- a/python/cudf_polars/cudf_polars/experimental/sort.py +++ b/python/cudf_polars/cudf_polars/experimental/sort.py @@ -370,7 +370,7 @@ def extract_partition( context = get_worker_context() - shuffler.wait_on(partition_id) + shuffler.wait() column_names = options["column_names"] column_dtypes = options["column_dtypes"] From 609cf99eba923682fb81bdec8513c7a1bbc27afc Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Mon, 16 Mar 2026 20:15:22 +0000 Subject: [PATCH 33/35] Pass df.stream to to_py call in shift --- python/cudf_polars/cudf_polars/dsl/expressions/unary.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/python/cudf_polars/cudf_polars/dsl/expressions/unary.py b/python/cudf_polars/cudf_polars/dsl/expressions/unary.py index 70fc223d965c..275376c132a6 100644 --- a/python/cudf_polars/cudf_polars/dsl/expressions/unary.py +++ b/python/cudf_polars/cudf_polars/dsl/expressions/unary.py @@ -522,9 +522,7 @@ def do_evaluate( offset = n_expr.value else: n_col = n_expr.evaluate(df, context=context) - offset_py = plc.copying.get_element( - n_col.obj, 0, stream=df.stream - ).to_py() + offset_py = n_col.obj_scalar(stream=df.stream).to_py(stream=df.stream) assert isinstance(offset_py, int) offset = offset_py if self.name == "shift": From 804cf3b75144f915039db2bb92e9574c01af5086 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Mon, 16 Mar 2026 23:48:03 +0000 Subject: [PATCH 34/35] xfail test_groupby_aggs_keep_unsupported_as_null for quantile and polars 1.33.1 --- python/cudf_polars/tests/test_groupby.py | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/python/cudf_polars/tests/test_groupby.py b/python/cudf_polars/tests/test_groupby.py index 60c5f173bf36..e9400e22dbd1 100644 --- a/python/cudf_polars/tests/test_groupby.py +++ b/python/cudf_polars/tests/test_groupby.py @@ -17,6 +17,8 @@ ) from cudf_polars.utils.versions import ( POLARS_VERSION_LT_132, + POLARS_VERSION_LT_133, + POLARS_VERSION_LT_134, POLARS_VERSION_LT_136, POLARS_VERSION_LT_1321, ) @@ -435,7 +437,7 @@ def test_groupby_sum_all_null_group_returns_null(): ids=["sum", "mean", "median", "quantile-0.5"], ) def test_groupby_aggs_keep_unsupported_as_null( - request, df: pl.LazyFrame, agg_expr + request, df: pl.LazyFrame, agg_expr, using_rapidsmpf ) -> None: request.applymarker( pytest.mark.xfail( @@ -443,6 +445,15 @@ def test_groupby_aggs_keep_unsupported_as_null( reason="polars raises now", ) ) + request.applymarker( + pytest.mark.xfail( + condition=using_rapidsmpf + and "quantile" in str(agg_expr) + and POLARS_VERSION_LT_134 + and not POLARS_VERSION_LT_133, + reason="decimal precision is 38 instead of 9", + ) + ) lf = df.filter(pl.col("datetime") == date(2004, 12, 1)) q = lf.group_by("datetime").agg(agg_expr) assert_gpu_result_equal(q) From 8f642f32640e977f0440c3bd55175934445ce517 Mon Sep 17 00:00:00 2001 From: Matthew Roeschke <10647082+mroeschke@users.noreply.github.com> Date: Mon, 16 Mar 2026 23:48:38 +0000 Subject: [PATCH 35/35] add temp? no coverage failure to dask tests --- ci/run_cudf_polars_pytests.sh | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/ci/run_cudf_polars_pytests.sh b/ci/run_cudf_polars_pytests.sh index 8745a762bb11..a1b06fd2fc56 100755 --- a/ci/run_cudf_polars_pytests.sh +++ b/ci/run_cudf_polars_pytests.sh @@ -36,4 +36,5 @@ echo "Run experimental tests with the distributed cluster mode and the rapidsmpf python -m pytest --cache-clear "$@" "tests/experimental" \ --executor streaming \ --cluster distributed \ - --runtime rapidsmpf + --runtime rapidsmpf \ + --cov-fail-under=0 # No code-coverage requirement for these tests(?)