diff --git a/changes/3251.fix.rst b/changes/3251.fix.rst new file mode 100644 index 0000000000..92f19ae326 --- /dev/null +++ b/changes/3251.fix.rst @@ -0,0 +1 @@ +Ensure that all abstract methods of ``ZDType`` raise a ``NotImplementedError`` when invoked. \ No newline at end of file diff --git a/src/zarr/core/dtype/wrapper.py b/src/zarr/core/dtype/wrapper.py index b53018c137..776aea81d8 100644 --- a/src/zarr/core/dtype/wrapper.py +++ b/src/zarr/core/dtype/wrapper.py @@ -102,9 +102,6 @@ def from_native_dtype(cls: type[Self], dtype: TBaseDType) -> Self: """ Create a ZDType instance from a native data type. - The base implementation first performs a type check via ``cls._check_native_dtype``. - If that type check succeeds, the ZDType class instance is created. - This method is used when taking a user-provided native data type, like a NumPy data type, and creating the corresponding ZDType instance from them. @@ -123,7 +120,7 @@ def from_native_dtype(cls: type[Self], dtype: TBaseDType) -> Self: TypeError If the native data type is not consistent with the wrapped data type. """ - ... + raise NotImplementedError # pragma: no cover @abstractmethod def to_native_dtype(self: Self) -> TDType_co: @@ -135,15 +132,17 @@ def to_native_dtype(self: Self) -> TDType_co: TDType The native data type wrapped by this ZDType. """ - ... + raise NotImplementedError # pragma: no cover @classmethod @abstractmethod - def _from_json_v2(cls: type[Self], data: DTypeJSON) -> Self: ... + def _from_json_v2(cls: type[Self], data: DTypeJSON) -> Self: + raise NotImplementedError # pragma: no cover @classmethod @abstractmethod - def _from_json_v3(cls: type[Self], data: DTypeJSON) -> Self: ... + def _from_json_v3(cls: type[Self], data: DTypeJSON) -> Self: + raise NotImplementedError # pragma: no cover @classmethod def from_json(cls: type[Self], data: DTypeJSON, *, zarr_format: ZarrFormat) -> Self: @@ -190,7 +189,7 @@ def to_json(self, zarr_format: ZarrFormat) -> DTypeSpec_V2 | DTypeSpec_V3: DTypeJSON_V2 | DTypeJSON_V3 The JSON-serializable representation of the wrapped data type """ - ... + raise NotImplementedError # pragma: no cover @abstractmethod def _check_scalar(self, data: object) -> bool: @@ -207,7 +206,7 @@ def _check_scalar(self, data: object) -> bool: Bool True if the object is valid, False otherwise. """ - ... + raise NotImplementedError # pragma: no cover @abstractmethod def cast_scalar(self, data: object) -> TScalar_co: @@ -227,6 +226,7 @@ def cast_scalar(self, data: object) -> TScalar_co: TScalar The cast value. """ + raise NotImplementedError # pragma: no cover @abstractmethod def default_scalar(self) -> TScalar_co: @@ -242,7 +242,7 @@ def default_scalar(self) -> TScalar_co: TScalar The default value for this data type. """ - ... + raise NotImplementedError # pragma: no cover @abstractmethod def from_json_scalar(self: Self, data: JSON, *, zarr_format: ZarrFormat) -> TScalar_co: @@ -262,7 +262,7 @@ def from_json_scalar(self: Self, data: JSON, *, zarr_format: ZarrFormat) -> TSca TScalar The deserialized scalar value. """ - ... + raise NotImplementedError # pragma: no cover @abstractmethod def to_json_scalar(self, data: object, *, zarr_format: ZarrFormat) -> JSON: @@ -285,7 +285,7 @@ def to_json_scalar(self, data: object, *, zarr_format: ZarrFormat) -> JSON: JSON The JSON-serialized scalar. """ - ... + raise NotImplementedError # pragma: no cover def scalar_failed_type_check_msg(