add marks to all tests

This commit is contained in:
sneakers-the-rat 2024-09-23 13:28:38 -07:00
parent 9026eb700f
commit 8cc2574399
Signed by untrusted user who does not match committer: jonny
GPG key ID: 6DCB96EF1E4D232D
14 changed files with 101 additions and 36 deletions

View file

@ -116,7 +116,13 @@ markers = [
"dtype: mark test related to dtype validation",
"shape: mark test related to shape validation",
"json_schema: mark test related to json schema generation",
"serialization: mark test related to serialization"
"serialization: mark test related to serialization",
"proxy: test for proxy class in any interface",
"dask: dask interface",
"hdf5: hdf5 interface",
"numpy: numpy interface",
"video: video interface",
"zarr: zarr interface",
]
[tool.ruff]

View file

@ -61,7 +61,7 @@ class DaskInterface(Interface):
"""
check if array is a dask array
"""
if DaskArray is None:
if DaskArray is None: # pragma: no cover - no tests for interface deps atm
return False
elif isinstance(array, DaskArray):
return True

View file

@ -83,6 +83,7 @@ STRING: TypeAlias = NDArray[Shape["*, *, *"], str]
MODEL: TypeAlias = NDArray[Shape["*, *, *"], BasicModel]
@pytest.mark.shape
@pytest.fixture(
scope="module",
params=[
@ -120,6 +121,7 @@ def shape_cases(request) -> ValidationCase:
return request.param
@pytest.mark.dtype
@pytest.fixture(
scope="module",
params=[

View file

@ -104,6 +104,7 @@ def model_blank() -> Type[BaseModel]:
return BlankModel
@pytest.mark.hdf5
@pytest.fixture(scope="function")
def hdf5_file(tmp_output_dir_func) -> h5py.File:
h5f_file = tmp_output_dir_func / "h5f.h5"
@ -112,6 +113,7 @@ def hdf5_file(tmp_output_dir_func) -> h5py.File:
h5f.close()
@pytest.mark.hdf5
@pytest.fixture(scope="function")
def hdf5_array(
hdf5_file, request
@ -154,6 +156,7 @@ def hdf5_array(
return _hdf5_array
@pytest.mark.zarr
@pytest.fixture(scope="function")
def zarr_nested_array(tmp_output_dir_func) -> ZarrArrayPath:
"""Zarr array within a nested array"""
@ -164,6 +167,7 @@ def zarr_nested_array(tmp_output_dir_func) -> ZarrArrayPath:
return ZarrArrayPath(file=file, path=path)
@pytest.mark.zarr
@pytest.fixture(scope="function")
def zarr_array(tmp_output_dir_func) -> Path:
file = tmp_output_dir_func / "array.zarr"
@ -172,6 +176,7 @@ def zarr_array(tmp_output_dir_func) -> Path:
return file
@pytest.mark.video
@pytest.fixture(scope="function")
def avi_video(tmp_path) -> Callable[[Tuple[int, int], int, bool], Path]:
video_path = tmp_path / "test.avi"

View file

@ -12,24 +12,44 @@ from numpydantic import interface, NDArray
@pytest.fixture(
scope="function",
params=[
([[1, 2], [3, 4]], interface.NumpyInterface),
(np.zeros((3, 4)), interface.NumpyInterface),
("hdf5_array", interface.H5Interface),
(da.random.random((10, 10)), interface.DaskInterface),
(zarr.ones((10, 10)), interface.ZarrInterface),
("zarr_nested_array", interface.ZarrInterface),
("zarr_array", interface.ZarrInterface),
("avi_video", interface.VideoInterface),
],
ids=[
"numpy_list",
"numpy",
"H5ArrayPath",
"dask",
"zarr_memory",
"zarr_nested",
"zarr_array",
"video",
pytest.param(
([[1, 2], [3, 4]], interface.NumpyInterface),
marks=pytest.mark.numpy,
id="numpy-list",
),
pytest.param(
(np.zeros((3, 4)), interface.NumpyInterface),
marks=pytest.mark.numpy,
id="numpy",
),
pytest.param(
("hdf5_array", interface.H5Interface),
marks=pytest.mark.hdf5,
id="h5-array-path",
),
pytest.param(
(da.random.random((10, 10)), interface.DaskInterface),
marks=pytest.mark.dask,
id="dask",
),
pytest.param(
(zarr.ones((10, 10)), interface.ZarrInterface),
marks=pytest.mark.zarr,
id="zarr-memory",
),
pytest.param(
("zarr_nested_array", interface.ZarrInterface),
marks=pytest.mark.zarr,
id="zarr-nested",
),
pytest.param(
("zarr_array", interface.ZarrInterface),
marks=pytest.mark.zarr,
id="zarr-array",
),
pytest.param(
("avi_video", interface.VideoInterface), marks=pytest.mark.video, id="video"
),
],
)
def interface_type(request) -> Tuple[NDArray, Type[interface.Interface]]:

View file

@ -1,5 +1,3 @@
import pdb
import pytest
import json
@ -11,6 +9,8 @@ from numpydantic.exceptions import DtypeError, ShapeError
from tests.conftest import ValidationCase
pytestmark = pytest.mark.dask
def dask_array(case: ValidationCase) -> da.Array:
if issubclass(case.dtype, BaseModel):
@ -42,14 +42,17 @@ def test_dask_check(interface_type):
assert not DaskInterface.check(interface_type[0])
@pytest.mark.shape
def test_dask_shape(shape_cases):
_test_dask_case(shape_cases)
@pytest.mark.dtype
def test_dask_dtype(dtype_cases):
_test_dask_case(dtype_cases)
@pytest.mark.serialization
def test_dask_to_json(array_model):
array_list = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
array = da.array(array_list)

View file

@ -1,10 +0,0 @@
"""
Tests for dunder methods on all interfaces
"""
def test_dunder_len(all_interfaces):
"""
Each interface or proxy type should support __len__
"""
assert len(all_interfaces.array) == all_interfaces.array.shape[0]

View file

@ -14,6 +14,8 @@ from numpydantic.exceptions import DtypeError, ShapeError
from tests.conftest import ValidationCase
pytestmark = pytest.mark.hdf5
def hdf5_array_case(
case: ValidationCase, array_func, compound: bool = False
@ -72,11 +74,13 @@ def test_hdf5_check_not_hdf5(tmp_path):
assert not H5Interface.check(spec)
@pytest.mark.shape
@pytest.mark.parametrize("compound", [True, False])
def test_hdf5_shape(shape_cases, hdf5_array, compound):
_test_hdf5_case(shape_cases, hdf5_array, compound)
@pytest.mark.dtype
@pytest.mark.parametrize("compound", [True, False])
def test_hdf5_dtype(dtype_cases, hdf5_array, compound):
_test_hdf5_case(dtype_cases, hdf5_array, compound)
@ -90,6 +94,7 @@ def test_hdf5_dataset_not_exists(hdf5_array, model_blank):
assert "no array found" in e
@pytest.mark.proxy
def test_assignment(hdf5_array, model_blank):
array = hdf5_array()
@ -101,6 +106,7 @@ def test_assignment(hdf5_array, model_blank):
assert (model.array[1:3, 2:4] == 10).all()
@pytest.mark.serialization
@pytest.mark.parametrize("round_trip", (True, False))
def test_to_json(hdf5_array, array_model, round_trip):
"""
@ -125,6 +131,8 @@ def test_to_json(hdf5_array, array_model, round_trip):
assert json_dumped == instance.array[:].tolist()
@pytest.mark.dtype
@pytest.mark.proxy
def test_compound_dtype(tmp_path):
"""
hdf5 proxy indexes compound dtypes as single fields when field is given
@ -159,6 +167,8 @@ def test_compound_dtype(tmp_path):
assert all(instance.array[1] == 2)
@pytest.mark.dtype
@pytest.mark.proxy
@pytest.mark.parametrize("compound", [True, False])
def test_strings(hdf5_array, compound):
"""
@ -178,6 +188,8 @@ def test_strings(hdf5_array, compound):
assert all(instance.array[1] == "sup")
@pytest.mark.dtype
@pytest.mark.proxy
@pytest.mark.parametrize("compound", [True, False])
def test_datetime(hdf5_array, compound):
"""

View file

@ -66,3 +66,10 @@ def test_interface_roundtrip_json(all_interfaces, round_trip):
assert model.array.dtype == all_interfaces.array.dtype
else:
assert np.array_equal(model.array, np.array(all_interfaces.array))
def test_dunder_len(all_interfaces):
"""
Each interface or proxy type should support __len__
"""
assert len(all_interfaces.array) == all_interfaces.array.shape[0]

View file

@ -5,6 +5,8 @@ from numpydantic.exceptions import DtypeError, ShapeError
from tests.conftest import ValidationCase
pytestmark = pytest.mark.numpy
def numpy_array(case: ValidationCase) -> np.ndarray:
if issubclass(case.dtype, BaseModel):
@ -22,10 +24,12 @@ def _test_np_case(case: ValidationCase):
case.model(array=array)
@pytest.mark.shape
def test_numpy_shape(shape_cases):
_test_np_case(shape_cases)
@pytest.mark.dtype
def test_numpy_dtype(dtype_cases):
_test_np_case(dtype_cases)

View file

@ -14,6 +14,8 @@ from numpydantic import NDArray, Shape
from numpydantic import dtype as dt
from numpydantic.interface.video import VideoProxy
pytestmark = pytest.mark.video
@pytest.mark.parametrize("input_type", [str, Path])
def test_video_validation(avi_video, input_type):
@ -49,6 +51,7 @@ def test_video_from_videocapture(avi_video):
opened_vid.release()
@pytest.mark.shape
def test_video_wrong_shape(avi_video):
shape = (100, 50)
@ -65,6 +68,7 @@ def test_video_wrong_shape(avi_video):
instance = MyModel(array=vid)
@pytest.mark.proxy
def test_video_getitem(avi_video):
"""
Should be able to get individual frames and slices as if it were a normal array
@ -127,6 +131,7 @@ def test_video_getitem(avi_video):
instance.array[5] = 10
@pytest.mark.proxy
def test_video_attrs(avi_video):
"""Should be able to access opencv properties"""
shape = (100, 50)
@ -142,6 +147,7 @@ def test_video_attrs(avi_video):
assert int(instance.array.get(cv2.CAP_PROP_POS_FRAMES)) == 5
@pytest.mark.proxy
def test_video_close(avi_video):
"""Should close and reopen video file if needed"""
shape = (100, 50)

View file

@ -6,13 +6,14 @@ import zarr
from pydantic import BaseModel, ValidationError
from numcodecs import Pickle
from numpydantic.interface import ZarrInterface
from numpydantic.interface.zarr import ZarrArrayPath
from numpydantic.exceptions import DtypeError, ShapeError
from tests.conftest import ValidationCase
pytestmark = pytest.mark.zarr
@pytest.fixture()
def dir_array(tmp_output_dir_func) -> zarr.DirectoryStore:
@ -87,10 +88,12 @@ def test_zarr_check(interface_type):
assert not ZarrInterface.check(interface_type[0])
@pytest.mark.shape
def test_zarr_shape(store, shape_cases):
_test_zarr_case(shape_cases, store)
@pytest.mark.dtype
def test_zarr_dtype(dtype_cases, store):
_test_zarr_case(dtype_cases, store)

View file

@ -41,6 +41,7 @@ def test_ndarray_type():
instance = Model(array=np.zeros((2, 3)), array_any=np.ones((3, 4, 5)))
@pytest.mark.dtype
@pytest.mark.json_schema
def test_schema_unsupported_type():
"""
@ -57,10 +58,11 @@ def test_schema_unsupported_type():
}
@pytest.mark.dtype
@pytest.mark.json_schema
def test_schema_tuple():
"""
Types specified as tupled should have their schemas as a union
Types specified as tuples should have their schemas as a union
"""
class Model(BaseModel):
@ -75,6 +77,7 @@ def test_schema_tuple():
assert all([i["minimum"] == 0 for i in conditions])
@pytest.mark.dtype
@pytest.mark.json_schema
def test_schema_number():
"""
@ -119,12 +122,12 @@ def test_ndarray_union():
instance = Model(array=np.random.random((5, 10, 4, 6)))
@pytest.mark.shape
@pytest.mark.dtype
@pytest.mark.parametrize("dtype", dtype.Number)
def test_ndarray_unparameterized(dtype):
"""
NDArray without any parameters is any shape, any type
Returns:
"""
class Model(BaseModel):
@ -138,6 +141,7 @@ def test_ndarray_unparameterized(dtype):
_ = Model(array=np.zeros(dim_sizes, dtype=dtype))
@pytest.mark.shape
def test_ndarray_any():
"""
using :class:`typing.Any` in for the shape means any shape
@ -249,6 +253,7 @@ def test_json_schema_dtype_single(dtype, array_model):
@pytest.mark.dtype
@pytest.mark.json_schema
@pytest.mark.parametrize(
"dtype,expected",
[

View file

@ -9,6 +9,8 @@ import numpy as np
from numpydantic import NDArray, Shape
pytestmark = pytest.mark.shape
@pytest.mark.parametrize(
"shape,valid",