Skip to content

Commit 0c8e7f7

Browse files
committed
WIP - backwards compat
1 parent 61683be commit 0c8e7f7

File tree

10 files changed

+84
-53
lines changed

10 files changed

+84
-53
lines changed

pyproject.toml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -66,7 +66,8 @@ test = [
6666
"flask",
6767
"requests",
6868
"mypy",
69-
"hypothesis"
69+
"hypothesis",
70+
"universal-pathlib",
7071
]
7172

7273
jupyter = [

src/zarr/api/asynchronous.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -468,7 +468,7 @@ async def group(
468468
try:
469469
return await AsyncGroup.open(store=store_path, zarr_format=zarr_format)
470470
except (KeyError, FileNotFoundError):
471-
return await AsyncGroup.create(
471+
return await AsyncGroup.from_store(
472472
store=store_path,
473473
zarr_format=zarr_format,
474474
exists_ok=overwrite,
@@ -477,8 +477,8 @@ async def group(
477477

478478

479479
async def open_group(
480-
*, # Note: this is a change from v2
481480
store: StoreLike | None = None,
481+
*, # Note: this is a change from v2
482482
mode: AccessModeLiteral | None = None, # not used
483483
cache_attrs: bool | None = None, # not used, default changed
484484
synchronizer: Any = None, # not used
@@ -550,7 +550,7 @@ async def open_group(
550550
try:
551551
return await AsyncGroup.open(store_path, zarr_format=zarr_format)
552552
except (KeyError, FileNotFoundError):
553-
return await AsyncGroup.create(
553+
return await AsyncGroup.from_store(
554554
store_path, zarr_format=zarr_format, exists_ok=True, attributes=attributes
555555
)
556556

src/zarr/api/synchronous.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -62,8 +62,8 @@ def load(
6262

6363

6464
def open(
65-
*,
6665
store: StoreLike | None = None,
66+
*,
6767
mode: AccessModeLiteral | None = None, # type and value changed
6868
zarr_version: ZarrFormat | None = None, # deprecated
6969
zarr_format: ZarrFormat | None = None,
@@ -187,8 +187,8 @@ def group(
187187

188188

189189
def open_group(
190-
*, # Note: this is a change from v2
191190
store: StoreLike | None = None,
191+
*, # Note: this is a change from v2
192192
mode: AccessModeLiteral | None = None, # not used in async api
193193
cache_attrs: bool | None = None, # default changed, not used in async api
194194
synchronizer: Any = None, # not used in async api

src/zarr/core/attributes.py

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
from __future__ import annotations
22

3-
from collections.abc import MutableMapping
3+
from collections.abc import Mapping, MutableMapping
44
from typing import TYPE_CHECKING
55

66
from zarr.core.common import JSON
@@ -35,3 +35,9 @@ def __iter__(self) -> Iterator[str]:
3535

3636
def __len__(self) -> int:
3737
return len(self._obj.metadata.attributes)
38+
39+
def put(self, d: Mapping[str, JSON]) -> None:
40+
# Backwards compat for 2.x API.
41+
new_attrs = dict(self._obj.metadata.attributes)
42+
new_attrs.update(d)
43+
self._obj = self._obj.update_attributes(new_attrs)

src/zarr/core/group.py

Lines changed: 29 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212

1313
from zarr.abc.codec import Codec
1414
from zarr.abc.metadata import Metadata
15-
from zarr.abc.store import set_or_delete
15+
from zarr.abc.store import Store, set_or_delete
1616
from zarr.core.array import Array, AsyncArray
1717
from zarr.core.attributes import Attributes
1818
from zarr.core.buffer import default_buffer_prototype
@@ -122,8 +122,12 @@ class AsyncGroup:
122122
metadata: GroupMetadata
123123
store_path: StorePath
124124

125+
@property
126+
def store(self) -> Store:
127+
return self.store_path.store
128+
125129
@classmethod
126-
async def create(
130+
async def from_store(
127131
cls,
128132
store: StoreLike,
129133
*,
@@ -316,7 +320,7 @@ async def create_group(
316320
attributes: dict[str, Any] | None = None,
317321
) -> AsyncGroup:
318322
attributes = attributes or {}
319-
return await type(self).create(
323+
return await type(self).from_store(
320324
self.store_path / path,
321325
attributes=attributes,
322326
exists_ok=exists_ok,
@@ -533,8 +537,24 @@ async def move(self, source: str, dest: str) -> None:
533537
class Group(SyncMixin):
534538
_async_group: AsyncGroup
535539

540+
@property
541+
def store(self) -> Store:
542+
# Backwards compatibility for 2.x
543+
return self._async_group.store
544+
545+
@property
546+
def read_only(self) -> bool:
547+
# Backwards compatibility for 2.x
548+
return self._async_group.store.mode.readonly
549+
550+
@property
551+
def synchronizer(self) -> None:
552+
# Backwards compatibility for 2.x
553+
# Not implemented in 3.x yet.
554+
return None
555+
536556
@classmethod
537-
def create(
557+
def from_store(
538558
cls,
539559
store: StoreLike,
540560
*,
@@ -544,7 +564,7 @@ def create(
544564
) -> Group:
545565
attributes = attributes or {}
546566
obj = sync(
547-
AsyncGroup.create(
567+
AsyncGroup.from_store(
548568
store,
549569
attributes=attributes,
550570
exists_ok=exists_ok,
@@ -665,6 +685,10 @@ def tree(self, expand: bool = False, level: int | None = None) -> Any:
665685
def create_group(self, name: str, **kwargs: Any) -> Group:
666686
return Group(self._sync(self._async_group.create_group(name, **kwargs)))
667687

688+
def create(self, *args: Any, **kwargs: Any) -> Array:
689+
# Backwards compatibility for 2.x
690+
return self.create_array(*args, **kwargs)
691+
668692
def create_array(
669693
self,
670694
name: str,

src/zarr/store/consolidated.py

Whitespace-only changes.

src/zarr/testing/strategies.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ def arrays(
9898
expected_attrs = {} if attributes is None else attributes
9999

100100
array_path = path + ("/" if not path.endswith("/") else "") + name
101-
root = Group.create(store)
101+
root: Group = Group.from_store(store)
102102
fill_value_args: tuple[Any, ...] = tuple()
103103
if nparray.dtype.kind == "M":
104104
fill_value_args = ("ns",)

tests/v3/conftest.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ async def async_group(request: pytest.FixtureRequest, tmpdir: LEGACY_PATH) -> As
8181
param: AsyncGroupRequest = request.param
8282

8383
store = await parse_store(param.store, str(tmpdir))
84-
agroup = await AsyncGroup.create(
84+
agroup = await AsyncGroup.from_store(
8585
store,
8686
attributes=param.attributes,
8787
zarr_format=param.zarr_format,

tests/v3/test_array.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ def test_array_creation_existing_node(
2424
Check that an existing array or group is handled as expected during array creation.
2525
"""
2626
spath = StorePath(store)
27-
group = Group.create(spath, zarr_format=zarr_format)
27+
group = Group.from_store(spath, zarr_format=zarr_format)
2828
expected_exception: type[ContainsArrayError] | type[ContainsGroupError]
2929
if extant_node == "array":
3030
expected_exception = ContainsArrayError
@@ -75,7 +75,7 @@ def test_array_name_properties_no_group(
7575
def test_array_name_properties_with_group(
7676
store: LocalStore | MemoryStore, zarr_format: ZarrFormat
7777
) -> None:
78-
root = Group.create(store=store, zarr_format=zarr_format)
78+
root = Group.from_store(store=store, zarr_format=zarr_format)
7979
foo = root.create_array("foo", shape=(100,), chunks=(10,), dtype="i4")
8080
assert foo.path == "foo"
8181
assert foo.name == "/foo"

0 commit comments

Comments
 (0)