From 066fd3acccc3888db7bca1f99951ed6625523af6 Mon Sep 17 00:00:00 2001 From: Davis Vann Bennett Date: Mon, 26 May 2025 09:16:28 +0200 Subject: [PATCH] remove usage of the _deprecate_positional_args decorator, and tests for its behavior --- src/zarr/api/synchronous.py | 5 -- src/zarr/core/array.py | 13 ----- src/zarr/core/group.py | 11 ----- tests/test_api.py | 41 ++-------------- tests/test_array.py | 94 +++++++++---------------------------- tests/test_group.py | 20 -------- tests/test_sync.py | 7 --- 7 files changed, 26 insertions(+), 165 deletions(-) diff --git a/src/zarr/api/synchronous.py b/src/zarr/api/synchronous.py index d4b652ad6e..1fe9487ed6 100644 --- a/src/zarr/api/synchronous.py +++ b/src/zarr/api/synchronous.py @@ -6,7 +6,6 @@ import zarr.api.asynchronous as async_api import zarr.core.array -from zarr._compat import _deprecate_positional_args from zarr.core.array import Array, AsyncArray, CompressorLike from zarr.core.group import Group from zarr.core.sync import sync @@ -154,7 +153,6 @@ def load( ) -@_deprecate_positional_args def open( store: StoreLike | None = None, *, @@ -248,7 +246,6 @@ def save( ) -@_deprecate_positional_args def save_array( store: StoreLike, arr: NDArrayLike, @@ -380,7 +377,6 @@ def array(data: npt.ArrayLike | Array, **kwargs: Any) -> Array: return Array(sync(async_api.array(data=data, **kwargs))) -@_deprecate_positional_args def group( store: StoreLike | None = None, *, @@ -448,7 +444,6 @@ def group( ) -@_deprecate_positional_args def open_group( store: StoreLike | None = None, *, diff --git a/src/zarr/core/array.py b/src/zarr/core/array.py index 62af644f7d..b3e0e56428 100644 --- a/src/zarr/core/array.py +++ b/src/zarr/core/array.py @@ -26,7 +26,6 @@ from typing_extensions import deprecated import zarr -from zarr._compat import _deprecate_positional_args from zarr.abc.codec import ArrayArrayCodec, ArrayBytesCodec, BytesBytesCodec, Codec from zarr.abc.store import Store, set_or_delete from zarr.codecs._v2 import V2Codec @@ -395,7 +394,6 @@ async def create( @classmethod @deprecated("Use zarr.api.asynchronous.create_array instead.") - @_deprecate_positional_args async def create( cls, store: StoreLike, @@ -1729,7 +1727,6 @@ class Array: @classmethod @deprecated("Use zarr.create_array instead.") - @_deprecate_positional_args def create( cls, store: StoreLike, @@ -2542,7 +2539,6 @@ def __setitem__(self, selection: Selection, value: npt.ArrayLike) -> None: else: self.set_basic_selection(cast("BasicSelection", pure_selection), value, fields=fields) - @_deprecate_positional_args def get_basic_selection( self, selection: BasicSelection = Ellipsis, @@ -2666,7 +2662,6 @@ def get_basic_selection( ) ) - @_deprecate_positional_args def set_basic_selection( self, selection: BasicSelection, @@ -2762,7 +2757,6 @@ def set_basic_selection( indexer = BasicIndexer(selection, self.shape, self.metadata.chunk_grid) sync(self._async_array._set_selection(indexer, value, fields=fields, prototype=prototype)) - @_deprecate_positional_args def get_orthogonal_selection( self, selection: OrthogonalSelection, @@ -2887,7 +2881,6 @@ def get_orthogonal_selection( ) ) - @_deprecate_positional_args def set_orthogonal_selection( self, selection: OrthogonalSelection, @@ -2998,7 +2991,6 @@ def set_orthogonal_selection( self._async_array._set_selection(indexer, value, fields=fields, prototype=prototype) ) - @_deprecate_positional_args def get_mask_selection( self, mask: MaskSelection, @@ -3081,7 +3073,6 @@ def get_mask_selection( ) ) - @_deprecate_positional_args def set_mask_selection( self, mask: MaskSelection, @@ -3160,7 +3151,6 @@ def set_mask_selection( indexer = MaskIndexer(mask, self.shape, self.metadata.chunk_grid) sync(self._async_array._set_selection(indexer, value, fields=fields, prototype=prototype)) - @_deprecate_positional_args def get_coordinate_selection( self, selection: CoordinateSelection, @@ -3250,7 +3240,6 @@ def get_coordinate_selection( out_array = np.array(out_array).reshape(indexer.sel_shape) return out_array - @_deprecate_positional_args def set_coordinate_selection( self, selection: CoordinateSelection, @@ -3348,7 +3337,6 @@ def set_coordinate_selection( sync(self._async_array._set_selection(indexer, value, fields=fields, prototype=prototype)) - @_deprecate_positional_args def get_block_selection( self, selection: BasicSelection, @@ -3447,7 +3435,6 @@ def get_block_selection( ) ) - @_deprecate_positional_args def set_block_selection( self, selection: BasicSelection, diff --git a/src/zarr/core/group.py b/src/zarr/core/group.py index 86cc6a3c6b..39278edfb5 100644 --- a/src/zarr/core/group.py +++ b/src/zarr/core/group.py @@ -16,7 +16,6 @@ from typing_extensions import deprecated import zarr.api.asynchronous as async_api -from zarr._compat import _deprecate_positional_args from zarr.abc.metadata import Metadata from zarr.abc.store import Store, set_or_delete from zarr.core._info import GroupInfo @@ -2366,7 +2365,6 @@ def create(self, *args: Any, **kwargs: Any) -> Array: # Backwards compatibility for 2.x return self.create_array(*args, **kwargs) - @_deprecate_positional_args def create_array( self, name: str, @@ -2572,7 +2570,6 @@ def require_array(self, name: str, *, shape: ShapeLike, **kwargs: Any) -> Array: """ return Array(self._sync(self._async_group.require_array(name, shape=shape, **kwargs))) - @_deprecate_positional_args def empty(self, *, name: str, shape: ChunkCoords, **kwargs: Any) -> Array: """Create an empty array with the specified shape in this Group. The contents will be filled with the array's fill value or zeros if no fill value is provided. @@ -2594,7 +2591,6 @@ def empty(self, *, name: str, shape: ChunkCoords, **kwargs: Any) -> Array: """ return Array(self._sync(self._async_group.empty(name=name, shape=shape, **kwargs))) - @_deprecate_positional_args def zeros(self, *, name: str, shape: ChunkCoords, **kwargs: Any) -> Array: """Create an array, with zero being used as the default value for uninitialized portions of the array. @@ -2614,7 +2610,6 @@ def zeros(self, *, name: str, shape: ChunkCoords, **kwargs: Any) -> Array: """ return Array(self._sync(self._async_group.zeros(name=name, shape=shape, **kwargs))) - @_deprecate_positional_args def ones(self, *, name: str, shape: ChunkCoords, **kwargs: Any) -> Array: """Create an array, with one being used as the default value for uninitialized portions of the array. @@ -2634,7 +2629,6 @@ def ones(self, *, name: str, shape: ChunkCoords, **kwargs: Any) -> Array: """ return Array(self._sync(self._async_group.ones(name=name, shape=shape, **kwargs))) - @_deprecate_positional_args def full( self, *, name: str, shape: ChunkCoords, fill_value: Any | None, **kwargs: Any ) -> Array: @@ -2662,7 +2656,6 @@ def full( ) ) - @_deprecate_positional_args def empty_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> Array: """Create an empty sub-array like `data`. The contents will be filled with the array's fill value or zeros if no fill value is provided. @@ -2689,7 +2682,6 @@ def empty_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> """ return Array(self._sync(self._async_group.empty_like(name=name, data=data, **kwargs))) - @_deprecate_positional_args def zeros_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> Array: """Create a sub-array of zeros like `data`. @@ -2710,7 +2702,6 @@ def zeros_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> return Array(self._sync(self._async_group.zeros_like(name=name, data=data, **kwargs))) - @_deprecate_positional_args def ones_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> Array: """Create a sub-array of ones like `data`. @@ -2730,7 +2721,6 @@ def ones_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> A """ return Array(self._sync(self._async_group.ones_like(name=name, data=data, **kwargs))) - @_deprecate_positional_args def full_like(self, *, name: str, data: async_api.ArrayLike, **kwargs: Any) -> Array: """Create a sub-array like `data` filled with the `fill_value` of `data` . @@ -2760,7 +2750,6 @@ def move(self, source: str, dest: str) -> None: return self._sync(self._async_group.move(source, dest)) @deprecated("Use Group.create_array instead.") - @_deprecate_positional_args def array( self, name: str, diff --git a/tests/test_api.py b/tests/test_api.py index 640478e9c1..4efb47fccd 100644 --- a/tests/test_api.py +++ b/tests/test_api.py @@ -13,7 +13,6 @@ from zarr.core.common import JSON, MemoryOrder, ZarrFormat import contextlib -import warnings from typing import Literal import numpy as np @@ -259,7 +258,7 @@ def test_save_errors() -> None: save_group("data/group.zarr") with pytest.raises(TypeError): # no array provided - save_array("data/group.zarr") + save_array("data/group.zarr") # type: ignore[call-arg] with pytest.raises(ValueError): # no arrays provided save("data/group.zarr") @@ -1080,40 +1079,6 @@ def test_tree() -> None: # copy(source["foo"], dest, dry_run=True, log=True) -def test_open_positional_args_deprecated() -> None: - store = MemoryStore() - with pytest.warns(FutureWarning, match="pass"): - zarr.api.synchronous.open(store, "w", shape=(1,)) - - -def test_save_array_positional_args_deprecated() -> None: - store = MemoryStore() - with warnings.catch_warnings(): - warnings.filterwarnings( - "ignore", message="zarr_version is deprecated", category=DeprecationWarning - ) - with pytest.warns(FutureWarning, match="pass"): - save_array( - store, - np.ones( - 1, - ), - 3, - ) - - -def test_group_positional_args_deprecated() -> None: - store = MemoryStore() - with pytest.warns(FutureWarning, match="pass"): - group(store, True) - - -def test_open_group_positional_args_deprecated() -> None: - store = MemoryStore() - with pytest.warns(FutureWarning, match="pass"): - open_group(store, "w") - - def test_open_falls_back_to_open_group() -> None: # https://github.com/zarr-developers/zarr-python/issues/2309 store = MemoryStore() @@ -1144,9 +1109,9 @@ def test_open_modes_creates_group(tmp_path: pathlib.Path, mode: str) -> None: if mode in ["r", "r+"]: # Expect FileNotFoundError to be raised if 'r' or 'r+' mode with pytest.raises(FileNotFoundError): - zarr.open(store=zarr_dir, mode=mode) + zarr.open(store=zarr_dir, mode=mode) # type: ignore[arg-type] else: - group = zarr.open(store=zarr_dir, mode=mode) + group = zarr.open(store=zarr_dir, mode=mode) # type: ignore[arg-type] assert isinstance(group, Group) diff --git a/tests/test_array.py b/tests/test_array.py index a6bcd17c4b..69654a6471 100644 --- a/tests/test_array.py +++ b/tests/test_array.py @@ -39,7 +39,6 @@ create_array, ) from zarr.core.buffer import NDArrayLike, NDArrayLikeOrScalar, default_buffer_prototype -from zarr.core.buffer.cpu import NDBuffer from zarr.core.chunk_grids import _auto_partition from zarr.core.chunk_key_encodings import ChunkKeyEncodingParams from zarr.core.common import JSON, MemoryOrder, ZarrFormat @@ -228,50 +227,6 @@ def test_array_v3_fill_value(store: MemoryStore, fill_value: int, dtype_str: str assert arr.fill_value.dtype == arr.dtype -async def test_create_deprecated() -> None: - with pytest.warns(DeprecationWarning): - with pytest.warns(FutureWarning, match=re.escape("Pass shape=(2, 2) as keyword args")): - await zarr.AsyncArray.create(MemoryStore(), (2, 2), dtype="f8") # type: ignore[call-overload] - with pytest.warns(DeprecationWarning): - with pytest.warns(FutureWarning, match=re.escape("Pass shape=(2, 2) as keyword args")): - zarr.Array.create(MemoryStore(), (2, 2), dtype="f8") - - -def test_selection_positional_args_deprecated() -> None: - store = MemoryStore() - arr = zarr.create_array(store, shape=(2, 2), dtype="f8") - - with pytest.warns(FutureWarning, match="Pass out"): - arr.get_basic_selection(..., NDBuffer(array=np.empty((2, 2)))) - - with pytest.warns(FutureWarning, match="Pass fields"): - arr.set_basic_selection(..., 1, None) - - with pytest.warns(FutureWarning, match="Pass out"): - arr.get_orthogonal_selection(..., NDBuffer(array=np.empty((2, 2)))) - - with pytest.warns(FutureWarning, match="Pass"): - arr.set_orthogonal_selection(..., 1, None) - - with pytest.warns(FutureWarning, match="Pass"): - arr.get_mask_selection(np.zeros((2, 2), dtype=bool), NDBuffer(array=np.empty((0,)))) - - with pytest.warns(FutureWarning, match="Pass"): - arr.set_mask_selection(np.zeros((2, 2), dtype=bool), 1, None) - - with pytest.warns(FutureWarning, match="Pass"): - arr.get_coordinate_selection(([0, 1], [0, 1]), NDBuffer(array=np.empty((2,)))) - - with pytest.warns(FutureWarning, match="Pass"): - arr.set_coordinate_selection(([0, 1], [0, 1]), 1, None) - - with pytest.warns(FutureWarning, match="Pass"): - arr.get_block_selection((0, slice(None)), NDBuffer(array=np.empty((2, 2)))) - - with pytest.warns(FutureWarning, match="Pass"): - arr.set_block_selection((0, slice(None)), 1, None) - - @pytest.mark.parametrize("store", ["memory"], indirect=True) async def test_array_v3_nan_fill_value(store: MemoryStore) -> None: shape = (10,) @@ -458,47 +413,44 @@ async def test_nbytes_stored_async() -> None: assert result == 902 # the size with all chunks filled. -def test_default_fill_values() -> None: - a = zarr.Array.create(MemoryStore(), shape=5, chunk_shape=5, dtype=" None: + a = zarr.Array.create(store=MemoryStore(), shape=(5,), chunk_shape=(5,), dtype=dtype_str) + assert a.fill_value == fill_value_expected def test_vlen_errors() -> None: + shape = (5,) + chunks = (5,) + dtype = " None: diff --git a/tests/test_group.py b/tests/test_group.py index b4dace2568..1c281ef2d4 100644 --- a/tests/test_group.py +++ b/tests/test_group.py @@ -1444,26 +1444,6 @@ def test_update_attrs() -> None: assert root.attrs["foo"] == "bar" -@pytest.mark.parametrize("method", ["empty", "zeros", "ones", "full"]) -def test_group_deprecated_positional_args(method: str) -> None: - if method == "full": - kwargs = {"fill_value": 0} - else: - kwargs = {} - - root = zarr.group() - with pytest.warns(FutureWarning, match=r"Pass name=.* as keyword args."): - arr = getattr(root, method)("foo", shape=1, **kwargs) - assert arr.shape == (1,) - - method += "_like" - data = np.ones(1) - - with pytest.warns(FutureWarning, match=r"Pass name=.*, data=.* as keyword args."): - arr = getattr(root, method)("foo_like", data, **kwargs) - assert arr.shape == data.shape - - @pytest.mark.parametrize("store", ["local", "memory"], indirect=["store"]) def test_delitem_removes_children(store: Store, zarr_format: ZarrFormat) -> None: # https://github.com/zarr-developers/zarr-python/issues/2191 diff --git a/tests/test_sync.py b/tests/test_sync.py index 13b475f8da..c5eadb0f4f 100644 --- a/tests/test_sync.py +++ b/tests/test_sync.py @@ -15,7 +15,6 @@ loop, sync, ) -from zarr.storage import MemoryStore @pytest.fixture(params=[True, False]) @@ -143,12 +142,6 @@ def bar(self) -> list[int]: assert foo.bar() == list(range(10)) -def test_open_positional_args_deprecate(): - store = MemoryStore() - with pytest.warns(FutureWarning, match="pass"): - zarr.open(store, "w", shape=(1,)) - - @pytest.mark.parametrize("workers", [None, 1, 2]) def test_threadpool_executor(clean_state, workers: int | None) -> None: with zarr.config.set({"threading.max_workers": workers}):