From 5b3ef5e1a8b89c9ec1b8642c7842c4f22078402b Mon Sep 17 00:00:00 2001 From: imam2004i <212503839+imam2004i@users.noreply.github.com> Date: Fri, 2 Oct 2026 09:56:30 +0530 Subject: [PATCH] Document that .item() is not implemented for lazy arrays (#7916) Improve the NotImplementedError raised for methods that do not work on dask arrays (e.g. .item()) to suggest loading the data into memory first, and add a note to the DataArray.item / Variable.item docstring pointing to .compute().item() / .as_numpy().item(). Co-authored-by: Claude --- doc/whats-new.rst | 5 +++++ xarray/computation/ops.py | 19 ++++++++++++++++++- xarray/core/duck_array_ops.py | 5 ++++- xarray/tests/test_dask.py | 2 +- 4 files changed, 28 insertions(+), 3 deletions(-) diff --git a/doc/whats-new.rst b/doc/whats-new.rst index 26fd9abbf44..92f04722c10 100644 --- a/doc/whats-new.rst +++ b/doc/whats-new.rst @@ -58,6 +58,11 @@ Bug Fixes Documentation ~~~~~~~~~~~~~ +- Clarified that :py:meth:`DataArray.item` and :py:meth:`Variable.item` are not + implemented for lazy (e.g. dask) arrays, both in the method docstring and in the + raised error message, which now suggests loading the data into memory first + (:issue:`7916`). + By `imam `_. Internal Changes diff --git a/xarray/computation/ops.py b/xarray/computation/ops.py index 0c7e8b16e1d..5f9f7916c4d 100644 --- a/xarray/computation/ops.py +++ b/xarray/computation/ops.py @@ -125,12 +125,29 @@ def _call_possibly_missing_method(arg, name, args, kwargs): return method(*args, **kwargs) +# Note appended to the inherited NumPy docstring of ``item``, which is not +# implemented for lazy (e.g. dask) arrays, see +# duck_array_ops.fail_on_dask_array_input. Inserted before the "Parameters" +# section so it renders near the top of the method documentation. +_ITEM_DASK_NOTE = ( + "\n.. note::\n" + " For xarray objects wrapping a lazy array such as a dask array,\n" + " ``item`` is not implemented and raises ``NotImplementedError``.\n" + " Load the data into memory first, for example with\n" + " ``obj.compute().item()`` or ``obj.as_numpy().item()``.\n" +) + + def _values_method_wrapper(name): def func(self, *args, **kwargs): return _call_possibly_missing_method(self.data, name, args, kwargs) func.__name__ = name - func.__doc__ = getattr(np.ndarray, name).__doc__ + doc = getattr(np.ndarray, name).__doc__ + if name == "item" and doc is not None: + anchor = "\nParameters\n" + doc = doc.replace(anchor, _ITEM_DASK_NOTE + anchor, 1) + func.__doc__ = doc return func diff --git a/xarray/core/duck_array_ops.py b/xarray/core/duck_array_ops.py index 90dfc5b78e0..7c58e68d4c8 100644 --- a/xarray/core/duck_array_ops.py +++ b/xarray/core/duck_array_ops.py @@ -121,7 +121,10 @@ def f(*args, **kwargs): def fail_on_dask_array_input(values, msg=None, func_name=None): if is_duck_dask_array(values): if msg is None: - msg = "%r is not yet a valid method on dask arrays" + msg = ( + "%r is not yet a valid method on dask arrays. Load the data into " + "memory first, e.g. with '.compute()' or '.load()'." + ) if func_name is None: func_name = inspect.stack()[1][3] raise NotImplementedError(msg % func_name) diff --git a/xarray/tests/test_dask.py b/xarray/tests/test_dask.py index cdb4d5d407c..27db4141963 100644 --- a/xarray/tests/test_dask.py +++ b/xarray/tests/test_dask.py @@ -270,7 +270,7 @@ def test_missing_methods(self): v = self.lazy_var with pytest.raises(NotImplementedError, match="dask"): v.argsort() - with pytest.raises(NotImplementedError, match="dask"): + with pytest.raises(NotImplementedError, match="Load the data into memory"): v[0].item() # type: ignore[attr-defined] def test_univariate_ufunc(self):