diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index cd459f6e8..6926b0459 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -1,8 +1,8 @@ repos: - repo: https://github.com/astral-sh/ruff-pre-commit - rev: v0.12.12 + rev: v0.13.0 hooks: - - id: ruff + - id: ruff-check args: ["--fix"] - id: ruff-format # The following can be removed once PLR0917 is out of preview diff --git a/benchmarks/benchmarks/anndata.py b/benchmarks/benchmarks/anndata.py index a6a036f24..e4855e078 100644 --- a/benchmarks/benchmarks/anndata.py +++ b/benchmarks/benchmarks/anndata.py @@ -13,18 +13,16 @@ class GarbargeCollectionSuite: # custom because `memory_profiler` is a line-by-line profiler (also: https://github.com/pythonprofilers/memory_profiler/issues/402) def track_peakmem_garbage_collection(self, *_): def display_top(snapshot, key_type="lineno"): - snapshot = snapshot.filter_traces( - ( - tracemalloc.Filter( - inclusive=False, - filename_pattern="", - ), - tracemalloc.Filter( - inclusive=False, - filename_pattern="", - ), - ) - ) + snapshot = snapshot.filter_traces(( + tracemalloc.Filter( + inclusive=False, + filename_pattern="", + ), + tracemalloc.Filter( + inclusive=False, + filename_pattern="", + ), + )) top_stats = snapshot.statistics(key_type) total = sum(stat.size for stat in top_stats) return total diff --git a/benchmarks/benchmarks/readwrite.py b/benchmarks/benchmarks/readwrite.py index c85de41f8..f2f1289b9 100644 --- a/benchmarks/benchmarks/readwrite.py +++ b/benchmarks/benchmarks/readwrite.py @@ -171,9 +171,11 @@ def peakmem_write_compressed(self, *_): self.adata.write_h5ad(self.writepth, compression="gzip") def track_peakmem_write_compressed(self, *_): - return get_peak_mem( - (sedate(self.adata.write_h5ad), (self.writepth,), {"compression": "gzip"}) - ) + return get_peak_mem(( + sedate(self.adata.write_h5ad), + (self.writepth,), + {"compression": "gzip"}, + )) class H5ADBackedWriteSuite(H5ADWriteSuite): diff --git a/benchmarks/benchmarks/sparse_dataset.py b/benchmarks/benchmarks/sparse_dataset.py index aa57872dc..c40e99b73 100644 --- a/benchmarks/benchmarks/sparse_dataset.py +++ b/benchmarks/benchmarks/sparse_dataset.py @@ -21,18 +21,16 @@ def make_alternating_mask(n): class SparseCSRContiguousSlice: - _slices = MappingProxyType( - { - "0:1000": slice(0, 1000), - "0:9000": slice(0, 9000), - ":9000:-1": slice(None, 9000, -1), - "::-2": slice(None, None, 2), - "array": np.array([0, 5000, 9999]), - "arange": np.arange(0, 1000), - "first": 0, - "alternating": make_alternating_mask(10), - } - ) + _slices = MappingProxyType({ + "0:1000": slice(0, 1000), + "0:9000": slice(0, 9000), + ":9000:-1": slice(None, 9000, -1), + "::-2": slice(None, None, 2), + "array": np.array([0, 5000, 9999]), + "arange": np.arange(0, 1000), + "first": 0, + "alternating": make_alternating_mask(10), + }) params = ( [ (10_000, 10_000), diff --git a/pyproject.toml b/pyproject.toml index 14b0a890c..dfba09811 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -177,6 +177,7 @@ markers = [ "gpu: mark test to run on GPU", "zarr_io: mark tests that involve za src = [ "src" ] [tool.ruff.format] +preview = true docstring-code-format = true [tool.ruff.lint] diff --git a/src/anndata/_core/merge.py b/src/anndata/_core/merge.py index c1753bcc2..53117b230 100644 --- a/src/anndata/_core/merge.py +++ b/src/anndata/_core/merge.py @@ -1748,15 +1748,10 @@ def concat( # noqa: PLR0912, PLR0913, PLR0915 for r, a in zip(reindexers, adatas, strict=True) ], ) - alt_pairwise = merge( - [ - { - k: r(r(v, axis=0), axis=1) - for k, v in getattr(a, f"{alt_axis_name}p").items() - } - for r, a in zip(reindexers, adatas, strict=True) - ] - ) + alt_pairwise = merge([ + {k: r(r(v, axis=0), axis=1) for k, v in getattr(a, f"{alt_axis_name}p").items()} + for r, a in zip(reindexers, adatas, strict=True) + ]) uns = uns_merge([a.uns for a in adatas]) raw = None @@ -1785,17 +1780,15 @@ def concat( # noqa: PLR0912, PLR0913, PLR0915 "not concatenating `.raw` attributes." ) warn(msg, UserWarning, stacklevel=2) - return AnnData( - **{ - "X": X, - "layers": layers, - axis_name: concat_annot, - alt_axis_name: alt_annot, - f"{axis_name}m": concat_mapping, - f"{alt_axis_name}m": alt_mapping, - f"{axis_name}p": concat_pairwise, - f"{alt_axis_name}p": alt_pairwise, - "uns": uns, - "raw": raw, - } - ) + return AnnData(**{ + "X": X, + "layers": layers, + axis_name: concat_annot, + alt_axis_name: alt_annot, + f"{axis_name}m": concat_mapping, + f"{alt_axis_name}m": alt_mapping, + f"{axis_name}p": concat_pairwise, + f"{alt_axis_name}p": alt_pairwise, + "uns": uns, + "raw": raw, + }) diff --git a/src/anndata/_core/sparse_dataset.py b/src/anndata/_core/sparse_dataset.py index a1959bb42..fcdd80dd3 100644 --- a/src/anndata/_core/sparse_dataset.py +++ b/src/anndata/_core/sparse_dataset.py @@ -278,9 +278,9 @@ def get_compressed_vectors( indptr_slices = [slice(*(x.indptr[i : i + 2])) for i in row_idxs] # HDF5 cannot handle out-of-order integer indexing if isinstance(x.data, ZarrArray): - as_np_indptr = np.concatenate( - [np.arange(s.start, s.stop) for s in indptr_slices] - ) + as_np_indptr = np.concatenate([ + np.arange(s.start, s.stop) for s in indptr_slices + ]) data = x.data[as_np_indptr] indices = x.indices[as_np_indptr] else: @@ -309,9 +309,9 @@ def get_compressed_vectors_for_slices( start_indptr = indptr_indices[0] - next(offsets) if len(slices) < 2: # there is only one slice so no need to concatenate return data, indices, start_indptr - end_indptr = np.concatenate( - [s[1:] - o for s, o in zip(indptr_indices[1:], offsets, strict=True)] - ) + end_indptr = np.concatenate([ + s[1:] - o for s, o in zip(indptr_indices[1:], offsets, strict=True) + ]) indptr = np.concatenate([start_indptr, end_indptr]) return data, indices, indptr diff --git a/src/anndata/_core/views.py b/src/anndata/_core/views.py index 9801d28af..755866de8 100644 --- a/src/anndata/_core/views.py +++ b/src/anndata/_core/views.py @@ -100,7 +100,7 @@ def __init__( # TODO: This makes `deepcopy(obj)` return `obj._view_args.parent._adata_ref`, fix it def __deepcopy__(self, memo): - parent, attrname, keys = self._view_args + parent, attrname, _keys = self._view_args return deepcopy(getattr(parent._adata_ref, attrname)) diff --git a/src/anndata/_io/h5ad.py b/src/anndata/_io/h5ad.py index 6c33e1ba9..1a842a4b4 100644 --- a/src/anndata/_io/h5ad.py +++ b/src/anndata/_io/h5ad.py @@ -264,15 +264,13 @@ def read_h5ad( def callback(func, elem_name: str, elem, iospec): if iospec.encoding_type == "anndata" or elem_name.endswith("/"): - return AnnData( - **{ - # This is covering up backwards compat in the anndata initializer - # In most cases we should be able to call `func(elen[k])` instead - k: read_dispatched(elem[k], callback) - for k in elem - if not k.startswith("raw.") - } - ) + return AnnData(**{ + # This is covering up backwards compat in the anndata initializer + # In most cases we should be able to call `func(elen[k])` instead + k: read_dispatched(elem[k], callback) + for k in elem + if not k.startswith("raw.") + }) elif elem_name.startswith("/raw."): return None elif elem_name == "/X" and "X" in as_sparse: diff --git a/src/anndata/_io/specs/lazy_methods.py b/src/anndata/_io/specs/lazy_methods.py index b6ad2e591..a42687686 100644 --- a/src/anndata/_io/specs/lazy_methods.py +++ b/src/anndata/_io/specs/lazy_methods.py @@ -37,7 +37,7 @@ from .registry import LazyDataStructures, LazyReader BlockInfo = Mapping[ - Literal[None], + None, dict[str, Sequence[tuple[int, int]]], ] diff --git a/src/anndata/_io/specs/registry.py b/src/anndata/_io/specs/registry.py index d9d2f5714..789f1847b 100644 --- a/src/anndata/_io/specs/registry.py +++ b/src/anndata/_io/specs/registry.py @@ -241,12 +241,9 @@ def proc_spec_mapping(spec: Mapping[str, str]) -> IOSpec: def get_spec( elem: StorageType, ) -> IOSpec: - return proc_spec( - { - k: _read_attr(elem.attrs, k, "") - for k in ["encoding-type", "encoding-version"] - } - ) + return proc_spec({ + k: _read_attr(elem.attrs, k, "") for k in ["encoding-type", "encoding-version"] + }) def _iter_patterns( diff --git a/src/anndata/_io/zarr.py b/src/anndata/_io/zarr.py index 531d34bc0..a1bbb8a35 100644 --- a/src/anndata/_io/zarr.py +++ b/src/anndata/_io/zarr.py @@ -77,13 +77,11 @@ def read_zarr(store: PathLike[str] | str | MutableMapping | zarr.Group) -> AnnDa # Read with handling for backwards compat def callback(func, elem_name: str, elem, iospec): if iospec.encoding_type == "anndata" or elem_name.endswith("/"): - return AnnData( - **{ - k: read_dispatched(v, callback) - for k, v in dict(elem).items() - if not k.startswith("raw.") - } - ) + return AnnData(**{ + k: read_dispatched(v, callback) + for k, v in dict(elem).items() + if not k.startswith("raw.") + }) elif elem_name.startswith("/raw."): return None elif elem_name in {"/obs", "/var"}: diff --git a/src/anndata/experimental/merge.py b/src/anndata/experimental/merge.py index 2a74f8c53..017345906 100644 --- a/src/anndata/experimental/merge.py +++ b/src/anndata/experimental/merge.py @@ -193,9 +193,10 @@ def write_concat_dense( # noqa: PLR0917 axis=axis, ) write_elem(output_group, output_path, res) - output_group[output_path].attrs.update( - {"encoding-type": "array", "encoding-version": "0.2.0"} - ) + output_group[output_path].attrs.update({ + "encoding-type": "array", + "encoding-version": "0.2.0", + }) def write_concat_sparse( # noqa: PLR0917 @@ -259,12 +260,10 @@ def _write_concat_mappings( # noqa: PLR0913, PLR0917 Write a list of mappings to a zarr/h5 group. """ mapping_group = output_group.create_group(path) - mapping_group.attrs.update( - { - "encoding-type": "dict", - "encoding-version": "0.1.0", - } - ) + mapping_group.attrs.update({ + "encoding-type": "dict", + "encoding-version": "0.1.0", + }) for k in keys: elems = [m[k] for m in mappings] _write_concat_sequence( diff --git a/tests/lazy/test_read.py b/tests/lazy/test_read.py index 9624668d6..953ee6e55 100644 --- a/tests/lazy/test_read.py +++ b/tests/lazy/test_read.py @@ -66,9 +66,10 @@ def test_access_count_subset( adata_remote_tall_skinny: AnnData, ): non_obs_elem_names = filter(lambda e: e != "obs", ANNDATA_ELEMS) - remote_store_tall_skinny.initialize_key_trackers( - ["obs/cat/codes", *non_obs_elem_names] - ) + remote_store_tall_skinny.initialize_key_trackers([ + "obs/cat/codes", + *non_obs_elem_names, + ]) adata_remote_tall_skinny[adata_remote_tall_skinny.obs["cat"] == "a", :] # all codes read in for subset (from 4 chunks as set in the fixture) remote_store_tall_skinny.assert_access_count("obs/cat/codes", 4) diff --git a/tests/test_awkward.py b/tests/test_awkward.py index 4650fa6f9..20b67bdee 100644 --- a/tests/test_awkward.py +++ b/tests/test_awkward.py @@ -53,12 +53,10 @@ ), # UnionType of two regular types with same dimension ( - ak.concatenate( - [ - ak.Array(np.ones((2, 2))), - ak.Array(np.array([["a", "a"], ["a", "a"]])), - ] - ), + ak.concatenate([ + ak.Array(np.ones((2, 2))), + ak.Array(np.array([["a", "a"], ["a", "a"]])), + ]), (4, 2), ), # Array of string types @@ -200,44 +198,40 @@ def reversed(self): # UnionType of two regular types with different dimensions ak.concatenate([ak.Array(np.ones((2, 2))), ak.Array(np.ones((2, 3)))]), # UnionType of two regular types with same dimension - ak.concatenate( - [ - ak.Array(np.ones((2, 2))), - ak.Array(np.array([["a", "a"], ["a", "a"]])), - ] - ), + ak.concatenate([ + ak.Array(np.ones((2, 2))), + ak.Array(np.array([["a", "a"], ["a", "a"]])), + ]), # categorical array ak.str.to_categorical(ak.Array([["a", "b", "c"], ["a", "b"]])), ak.str.to_categorical(ak.Array([[1, 1, 2], [3, 3]])), # tyical record type with AIRR data consisting of different dtypes - ak.Array( + ak.Array([ [ - [ - { - "v_call": "TRV1", - "junction_aa": "ADDEEKK", - "productive": True, - "locus": None, - "consensus_count": 3, - }, - { - "v_call": "TRV2", - "productive": False, - "locus": "TRA", - "consensus_count": 4, - }, - ], - [ - { - "v_call": None, - "junction_aa": "ADDEKK", - "productive": None, - "locus": "IGK", - "consensus_count": 3, - } - ], - ] - ), + { + "v_call": "TRV1", + "junction_aa": "ADDEEKK", + "productive": True, + "locus": None, + "consensus_count": 3, + }, + { + "v_call": "TRV2", + "productive": False, + "locus": "TRA", + "consensus_count": 4, + }, + ], + [ + { + "v_call": None, + "junction_aa": "ADDEKK", + "productive": None, + "locus": "IGK", + "consensus_count": 3, + } + ], + ]), ], ) def test_awkward_io(tmp_path, array): @@ -280,9 +274,11 @@ def test_awkward_io_view(tmp_path): pytest.param( [ak.Array([{"a": [1, 2], "b": [1, 2]}, {"a": [3], "b": [4]}]), None], "outer", - ak.Array( - [{"a": [1, 2], "b": [1, 2]}, {"a": [3], "b": [4]}, None, None, None] - ), + ak.Array([ + {"a": [1, 2], "b": [1, 2]}, + {"a": [3], "b": [4]}, + *[None, None, None], + ]), # maybe should return: ak.Array([{"a": [1, 2], "b": [1, 2]}, {"a": [3], "b": [4]}, {}, {}, {}]), id="awk:recordoflists_null-outer", ), @@ -302,9 +298,11 @@ def test_awkward_io_view(tmp_path): pytest.param( [None, ak.Array([{"a": [1, 2], "b": [1, 2]}, {"a": [3], "b": [4]}])], "outer", - ak.Array( - [None, None, None, {"a": [1, 2], "b": [1, 2]}, {"a": [3], "b": [4]}] - ), + ak.Array([ + *[None, None, None], + {"a": [1, 2], "b": [1, 2]}, + {"a": [3], "b": [4]}, + ]), # maybe should return: ak.Array([{}, {}, {}, {"a": [1, 2], "b": [1, 2]}, {"a": [3], "b": [4]}]), id="null_awk:recordoflists-outer", ), diff --git a/tests/test_backed_sparse.py b/tests/test_backed_sparse.py index 79d64ee4a..cda621d8c 100644 --- a/tests/test_backed_sparse.py +++ b/tests/test_backed_sparse.py @@ -83,12 +83,9 @@ def read_zarr_backed(path): # Read with handling for backwards compat def callback(func, elem_name, elem, iospec): if iospec.encoding_type == "anndata" or elem_name.endswith("/"): - return AnnData( - **{ - k: read_dispatched(v, callback) - for k, v in dict(elem).items() - } - ) + return AnnData(**{ + k: read_dispatched(v, callback) for k, v in dict(elem).items() + }) if iospec.encoding_type in {"csc_matrix", "csr_matrix"}: return sparse_dataset(elem) return func(elem) diff --git a/tests/test_base.py b/tests/test_base.py index f181b76a5..37cc8ff7e 100644 --- a/tests/test_base.py +++ b/tests/test_base.py @@ -508,7 +508,7 @@ def test_append_col(): # adata.obs[['new2', 'new3']] = [['A', 'B'], ['c', 'd']] with pytest.raises( - ValueError, match="Length of values.*does not match length of index" + ValueError, match=r"Length of values.*does not match length of index" ): adata.obs["new4"] = ["far", "too", "long"] diff --git a/tests/test_concatenate.py b/tests/test_concatenate.py index afdb4de70..3185b2a3f 100644 --- a/tests/test_concatenate.py +++ b/tests/test_concatenate.py @@ -218,7 +218,7 @@ def test_concat_interface_errors(use_xdataset): gen_adata((5, 10), obs_xdataset=use_xdataset, var_xdataset=use_xdataset), ] - with pytest.raises(ValueError, match="`axis` must be.*0, 1, 'obs', or 'var'"): + with pytest.raises(ValueError, match=r"`axis` must be.*0, 1, 'obs', or 'var'"): concat(adatas, axis=3) with pytest.raises(ValueError, match="'inner' or 'outer'"): concat(adatas, join="not implemented") @@ -331,27 +331,23 @@ def test_concatenate_dense(): # outer join adata = adata1.concatenate(adata2, adata3, join="outer") - X_ref = np.array( - [ - [1.0, 2.0, 3.0, np.nan], - [4.0, 5.0, 6.0, np.nan], - [np.nan, 3.0, 2.0, 1.0], - [np.nan, 6.0, 5.0, 4.0], - [np.nan, 3.0, 2.0, 1.0], - [np.nan, 6.0, 5.0, 4.0], - ] - ) + X_ref = np.array([ + [1.0, 2.0, 3.0, np.nan], + [4.0, 5.0, 6.0, np.nan], + [np.nan, 3.0, 2.0, 1.0], + [np.nan, 6.0, 5.0, 4.0], + [np.nan, 3.0, 2.0, 1.0], + [np.nan, 6.0, 5.0, 4.0], + ]) np.testing.assert_equal(adata.X, X_ref) var_ma = ma.masked_invalid(adata.var.values.tolist()) var_ma_ref = ma.masked_invalid( - np.array( - [ - [0.0, np.nan, np.nan], - [1.0, 2.0, 2.0], - [2.0, 1.0, 1.0], - [np.nan, 0.0, 0.0], - ] - ) + np.array([ + [0.0, np.nan, np.nan], + [1.0, 2.0, 2.0], + [2.0, 1.0, 1.0], + [np.nan, 0.0, 0.0], + ]) ) assert np.array_equal(var_ma.mask, var_ma_ref.mask) assert np.allclose(var_ma.compressed(), var_ma_ref.compressed()) @@ -464,37 +460,33 @@ def test_concatenate_obsm_outer(obsm_adatas, fill_val): assert isinstance(outer.obsm["dense"], np.ndarray) np.testing.assert_equal( outer.obsm["dense"], - np.array( - [ - [0, 1, fill_val], - [2, 3, fill_val], - [4, 5, fill_val], - [0, 1, 2], - [3, 4, 5], - [6, 7, 8], - [9, 10, 11], - [4, 5, fill_val], - [6, 7, fill_val], - ] - ), + np.array([ + [0, 1, fill_val], + [2, 3, fill_val], + [4, 5, fill_val], + [0, 1, 2], + [3, 4, 5], + [6, 7, 8], + [9, 10, 11], + [4, 5, fill_val], + [6, 7, fill_val], + ]), ) assert isinstance(outer.obsm["sparse"], CSMatrix) np.testing.assert_equal( outer.obsm["sparse"].toarray(), - np.array( - [ - [0, 1, fill_val, fill_val], - [2, 3, fill_val, fill_val], - [4, 5, fill_val, fill_val], - [fill_val, fill_val, fill_val, fill_val], - [fill_val, fill_val, fill_val, fill_val], - [fill_val, fill_val, fill_val, fill_val], - [fill_val, fill_val, fill_val, fill_val], - [0, 1, 2, 3], - [4, 5, 6, 7], - ] - ), + np.array([ + [0, 1, fill_val, fill_val], + [2, 3, fill_val, fill_val], + [4, 5, fill_val, fill_val], + [fill_val, fill_val, fill_val, fill_val], + [fill_val, fill_val, fill_val, fill_val], + [fill_val, fill_val, fill_val, fill_val], + [fill_val, fill_val, fill_val, fill_val], + [0, 1, 2, 3], + [4, 5, 6, 7], + ]), ) # fmt: off @@ -819,27 +811,23 @@ def test_concatenate_awkward(join_type): import awkward as ak a = ak.Array([[{"a": 1, "b": "foo"}], [{"a": 2, "b": "bar"}, {"a": 3, "b": "baz"}]]) - b = ak.Array( - [ - [{"a": 4}, {"a": 5}], - [{"a": 6}], - [{"a": 7}], - ] - ) + b = ak.Array([ + [{"a": 4}, {"a": 5}], + [{"a": 6}], + [{"a": 7}], + ]) adata_a = AnnData(np.zeros((2, 0), dtype=float), obsm={"awk": a}) adata_b = AnnData(np.zeros((3, 0), dtype=float), obsm={"awk": b}) if join_type == "inner": - expected = ak.Array( - [ - [{"a": 1}], - [{"a": 2}, {"a": 3}], - [{"a": 4}, {"a": 5}], - [{"a": 6}], - [{"a": 7}], - ] - ) + expected = ak.Array([ + [{"a": 1}], + [{"a": 2}, {"a": 3}], + [{"a": 4}, {"a": 5}], + [{"a": 6}], + [{"a": 7}], + ]) elif join_type == "outer": # TODO: This is what we would like to return, but waiting on: # * https://github.com/scikit-hep/awkward/issues/2182 and awkward 2.1.0 @@ -853,22 +841,18 @@ def test_concatenate_awkward(join_type): # [{"a": 7, "b": None}], # ] # ) - expected = ak.concatenate( - [ # I don't think I can construct a UnionArray directly - ak.Array( - [ - [{"a": 1, "b": "foo"}], - [{"a": 2, "b": "bar"}, {"a": 3, "b": "baz"}], - ] - ), - ak.Array( - [ - [{"a": 4}, {"a": 5}], - [{"a": 6}], - [{"a": 7}], - ] - ), - ] + expected = ( + ak.concatenate([ # I don't think I can construct a UnionArray directly + ak.Array([ + [{"a": 1, "b": "foo"}], + [{"a": 2, "b": "bar"}, {"a": 3, "b": "baz"}], + ]), + ak.Array([ + [{"a": 4}, {"a": 5}], + [{"a": 6}], + [{"a": 7}], + ]), + ]) ) result = concat([adata_a, adata_b], join=join_type).obsm["awk"] @@ -887,9 +871,10 @@ def test_concatenate_awkward(join_type): def test_awkward_does_not_mix(join_type, other): import awkward as ak - awk = ak.Array( - [[{"a": 1, "b": "foo"}], [{"a": 2, "b": "bar"}, {"a": 3, "b": "baz"}]] - ) + awk = ak.Array([ + [{"a": 1, "b": "foo"}], + [{"a": 2, "b": "bar"}, {"a": 3, "b": "baz"}], + ]) adata_a = AnnData( np.zeros((2, 3), dtype=float), @@ -991,9 +976,10 @@ def test_nan_merge(axis_name, join_type, array_type): assert_equal(getattr(orig1, mapping_attr), getattr(result, mapping_attr)) - orig_nonan = AnnData( - **{"X": sparse.csr_matrix(adata_shape), mapping_attr: {"arr": arr}} - ) + orig_nonan = AnnData(**{ + "X": sparse.csr_matrix(adata_shape), + mapping_attr: {"arr": arr}, + }) result_nonan = concat([orig1, orig_nonan], axis=axis, merge="same") assert len(getattr(result_nonan, mapping_attr)) == 0 @@ -1010,17 +996,16 @@ def test_merge_unique(): "a": {"b": "c"} } - assert merge_unique( - [{"a": {"b": {"c": {"d": "e"}}}}, {"a": {"b": {"c": {"d": "e"}}}}] - ) == {"a": {"b": {"c": {"d": "e"}}}} + assert merge_unique([ + {"a": {"b": {"c": {"d": "e"}}}}, + {"a": {"b": {"c": {"d": "e"}}}}, + ]) == {"a": {"b": {"c": {"d": "e"}}}} assert ( - merge_unique( - [ - {"a": {"b": {"c": {"d": "e"}}}}, - {"a": {"b": {"c": {"d": "f"}}}}, - {"a": {"b": {"c": {"d": "e"}}}}, - ] - ) + merge_unique([ + {"a": {"b": {"c": {"d": "e"}}}}, + {"a": {"b": {"c": {"d": "f"}}}}, + {"a": {"b": {"c": {"d": "e"}}}}, + ]) == {} ) @@ -1050,9 +1035,10 @@ def test_merge_same(): assert merge_same([{"a": {"b": "c"}, "d": "e"}, {"a": {"b": "c"}, "d": 2}]) == { "a": {"b": "c"} } - assert merge_same( - [{"a": {"b": {"c": {"d": "e"}}}}, {"a": {"b": {"c": {"d": "e"}}}}] - ) == {"a": {"b": {"c": {"d": "e"}}}} + assert merge_same([ + {"a": {"b": {"c": {"d": "e"}}}}, + {"a": {"b": {"c": {"d": "e"}}}}, + ]) == {"a": {"b": {"c": {"d": "e"}}}} assert merge_same([{"a": 1}, {"b": 2}]) == {} assert merge_same([{"a": 1}, {"b": 2}, {"a": 1, "b": {"c": 2, "d": 3}}]) == {} diff --git a/tests/test_extensions.py b/tests/test_extensions.py index e8e98448c..790e113e7 100644 --- a/tests/test_extensions.py +++ b/tests/test_extensions.py @@ -168,7 +168,7 @@ def test_missing_param() -> None: """Test that a namespace missing the second parameter is rejected.""" with pytest.raises( TypeError, - match="Namespace initializer must accept an AnnData instance as the second parameter.", + match=r"Namespace initializer must accept an AnnData instance as the second parameter\.", ): @ad.register_anndata_namespace("missing_param") @@ -181,7 +181,7 @@ def test_wrong_name() -> None: """Test that a namespace with wrong parameter name is rejected.""" with pytest.raises( TypeError, - match="Namespace initializer's second parameter must be named 'adata', got 'notadata'.", + match=r"Namespace initializer's second parameter must be named 'adata', got 'notadata'\.", ): @ad.register_anndata_namespace("wrong_name") @@ -194,7 +194,7 @@ def test_wrong_annotation() -> None: """Test that a namespace with wrong parameter annotation is rejected.""" with pytest.raises( TypeError, - match="Namespace initializer's second parameter must be annotated as the 'AnnData' class, got 'int'.", + match=r"Namespace initializer's second parameter must be annotated as the 'AnnData' class, got 'int'\.", ): @ad.register_anndata_namespace("wrong_annotation") diff --git a/tests/test_io_warnings.py b/tests/test_io_warnings.py index 5a12cb6e1..30f7d431c 100644 --- a/tests/test_io_warnings.py +++ b/tests/test_io_warnings.py @@ -54,9 +54,9 @@ def test_old_format_warning_not_thrown(tmp_path: Path) -> None: ad.read_h5ad(pth) if len(record) != 0: - msg_content = "\n".join( - [f"\t{w.category.__name__}('{w.message}')" for w in record] - ) + msg_content = "\n".join([ + f"\t{w.category.__name__}('{w.message}')" for w in record + ]) pytest.fail( f"Warnings were thrown when they shouldn't be. Got:\n\n{msg_content}" ) diff --git a/tests/test_readwrite.py b/tests/test_readwrite.py index 567d66629..c92d408ea 100644 --- a/tests/test_readwrite.py +++ b/tests/test_readwrite.py @@ -313,9 +313,10 @@ def test_read_full_io_error(tmp_path, name, read, write): # with re-opening without syncing attributes explicitly # TODO: Having to fully specify attributes to not override fixed in zarr v3.0.5 # See https://github.com/zarr-developers/zarr-python/pull/2870 - store["obs"].update_attributes( - {**dict(store["obs"].attrs), "encoding-type": "invalid"} - ) + store["obs"].update_attributes({ + **dict(store["obs"].attrs), + "encoding-type": "invalid", + }) zarr.consolidate_metadata(store.store) else: store["obs"].attrs["encoding-type"] = "invalid"