diff --git a/.github/workflows/mypy-type-check.yml b/.github/workflows/mypy-type-check.yml index 3bdd2ab7e..b7c15a5ec 100644 --- a/.github/workflows/mypy-type-check.yml +++ b/.github/workflows/mypy-type-check.yml @@ -40,7 +40,7 @@ jobs: mypy --install-types --non-interactive --follow-imports=skip \ tiatoolbox/__init__.py \ tiatoolbox/__main__.py \ - tiatoolbox/typing.py \ + tiatoolbox/type_hints.py \ tiatoolbox/tiatoolbox.py \ tiatoolbox/utils \ tiatoolbox/tools \ diff --git a/.github/workflows/python-package.yml b/.github/workflows/python-package.yml index 19e12a787..afccd6512 100644 --- a/.github/workflows/python-package.yml +++ b/.github/workflows/python-package.yml @@ -30,7 +30,7 @@ jobs: sudo apt update sudo apt-get install -y libopenslide-dev openslide-tools libopenjp2-7 libopenjp2-tools python -m pip install --upgrade pip - python -m pip install ruff==0.8.2 pytest pytest-cov pytest-runner + python -m pip install ruff==0.9.4 pytest pytest-cov pytest-runner pip install -r requirements/requirements.txt - name: Cache tiatoolbox static assets uses: actions/cache@v3 diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index ec5afa6fd..687d3fef9 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -23,7 +23,7 @@ repos: - mdformat-black - mdformat-myst - repo: https://github.com/executablebooks/mdformat - rev: 0.7.21 + rev: 0.7.22 hooks: - id: mdformat # Optionally add plugins @@ -60,7 +60,7 @@ repos: - id: rst-inline-touching-normal # Detect mistake of inline code touching normal text in rst. - repo: https://github.com/astral-sh/ruff-pre-commit # Ruff version. - rev: v0.8.6 + rev: v0.9.4 hooks: - id: ruff args: [--fix, --exit-non-zero-on-fix] diff --git a/pre-commit/notebook_urls.py b/pre-commit/notebook_urls.py index cc59dbeb1..c8b0f04fb 100644 --- a/pre-commit/notebook_urls.py +++ b/pre-commit/notebook_urls.py @@ -197,7 +197,9 @@ def check_notebook( for line_num, line in enumerate(cell["source"]): new_line = replace_line(line, to_ref, replacements) if new_line != line: - print(f"{path.name}: Changed (cell {cell_num+1}, line {line_num+1})") + print( + f"{path.name}: Changed (cell {cell_num + 1}, line {line_num + 1})" + ) changed = True cell["source"][line_num] = new_line return changed, notebook diff --git a/requirements/requirements_dev.txt b/requirements/requirements_dev.txt index 73d4bc1e4..5396121a4 100644 --- a/requirements/requirements_dev.txt +++ b/requirements/requirements_dev.txt @@ -10,7 +10,7 @@ pytest>=7.2.0 pytest-cov>=4.0.0 pytest-runner>=6.0 pytest-xdist[psutil] -ruff==0.8.2 # This will be updated by pre-commit bot to latest version +ruff==0.9.4 # This will be updated by pre-commit bot to latest version toml>=0.10.2 twine>=4.0.1 wheel>=0.37.1 diff --git a/tests/models/test_multi_task_segmentor.py b/tests/models/test_multi_task_segmentor.py index 1f135b303..8b234ac55 100644 --- a/tests/models/test_multi_task_segmentor.py +++ b/tests/models/test_multi_task_segmentor.py @@ -128,9 +128,9 @@ def test_functionality_hovernetplus(remote_sample: Callable, tmp_path: Path) -> assert len(inst_dict) > 0, "Must have some nuclei." assert layer_map is not None, "Must have some layers." - assert ( - layer_map.shape == required_dims - ), "Output layer map dimensions must be same as the expected output shape" + assert layer_map.shape == required_dims, ( + "Output layer map dimensions must be same as the expected output shape" + ) def test_functionality_hovernet(remote_sample: Callable, tmp_path: Path) -> None: diff --git a/tests/test_annotation_stores.py b/tests/test_annotation_stores.py index 66c990161..c3879c39f 100644 --- a/tests/test_annotation_stores.py +++ b/tests/test_annotation_stores.py @@ -40,7 +40,7 @@ if TYPE_CHECKING: # pragma: no cover from numbers import Number - from tiatoolbox.typing import Geometry + from tiatoolbox.type_hints import Geometry sqlite3.enable_callback_tracebacks(True) # noqa: FBT003 diff --git a/tests/test_docs.py b/tests/test_docs.py index 20880482b..4cf96e6a9 100644 --- a/tests/test_docs.py +++ b/tests/test_docs.py @@ -141,7 +141,7 @@ def raise_source_exception( for n, line in enumerate(source.splitlines()) ] if source_offset: - source_lines.insert(source_lineno, f"{' '*(source_offset+3)}^ {message}") + source_lines.insert(source_lineno, f"{' ' * (source_offset + 3)}^ {message}") annotated_source = "\n".join(source_lines) exception = type(exception) if exception else SyntaxError msg = f"{rel_path}:{file_lineno}: {message}\n{annotated_source}" diff --git a/tests/test_patch_extraction.py b/tests/test_patch_extraction.py index 2609b9a48..a8535f7b1 100644 --- a/tests/test_patch_extraction.py +++ b/tests/test_patch_extraction.py @@ -21,7 +21,7 @@ ) if TYPE_CHECKING: - from tiatoolbox.typing import IntPair, Resolution, Units + from tiatoolbox.type_hints import IntPair, Resolution, Units def read_points_patches( diff --git a/tests/test_tileserver.py b/tests/test_tileserver.py index 5451f716f..8a8d784af 100644 --- a/tests/test_tileserver.py +++ b/tests/test_tileserver.py @@ -461,7 +461,7 @@ def test_change_overlay( # noqa: PLR0915 assert response.status_code == 200 assert response.content_type == "text/html; charset=utf-8" # check that the overlay has been correctly added - lname = f"layer{len(empty_app.pyramids[session_id])-1}" + lname = f"layer{len(empty_app.pyramids[session_id]) - 1}" layer = empty_app.pyramids[session_id][lname] assert layer.wsi.info.file_path == overlay_path @@ -493,7 +493,7 @@ def test_change_overlay( # noqa: PLR0915 data={"overlay_path": safe_str(jpg_path)}, ) # check that the overlay has been correctly added - lname = f"layer{len(empty_app.pyramids[session_id])-1}" + lname = f"layer{len(empty_app.pyramids[session_id]) - 1}" layer = empty_app.pyramids[session_id][lname] assert np.all(layer.wsi.img == imread(jpg_path)) @@ -517,7 +517,7 @@ def test_change_overlay( # noqa: PLR0915 data={"overlay_path": safe_str(tiff_path)}, ) # check that the overlay has been correctly added - lname = f"layer{len(empty_app.pyramids[session_id])-1}" + lname = f"layer{len(empty_app.pyramids[session_id]) - 1}" layer = empty_app.pyramids[session_id][lname] assert layer.wsi.info.file_path == tiff_path diff --git a/tests/test_utils.py b/tests/test_utils.py index 95e6ee520..a06d57d90 100644 --- a/tests/test_utils.py +++ b/tests/test_utils.py @@ -28,7 +28,7 @@ from tiatoolbox.utils.transforms import locsize2bounds if TYPE_CHECKING: - from tiatoolbox.typing import IntBounds + from tiatoolbox.type_hints import IntBounds RNG = np.random.default_rng() # Numpy Random Generator diff --git a/tests/test_wsireader.py b/tests/test_wsireader.py index f43368406..e156f8990 100644 --- a/tests/test_wsireader.py +++ b/tests/test_wsireader.py @@ -52,7 +52,7 @@ import requests from openslide import OpenSlide - from tiatoolbox.typing import IntBounds, IntPair + from tiatoolbox.type_hints import IntBounds, IntPair from tiatoolbox.wsicore.wsimeta import WSIMeta # ------------------------------------------------------------------------------------- diff --git a/tiatoolbox/annotation/storage.py b/tiatoolbox/annotation/storage.py index 058b65b71..5834e2640 100644 --- a/tiatoolbox/annotation/storage.py +++ b/tiatoolbox/annotation/storage.py @@ -83,10 +83,10 @@ py_regexp, ) from tiatoolbox.enums import GeometryType -from tiatoolbox.typing import CallablePredicate, CallableSelect, Geometry +from tiatoolbox.type_hints import CallablePredicate, CallableSelect, Geometry if TYPE_CHECKING: # pragma: no cover - from tiatoolbox.typing import ( + from tiatoolbox.type_hints import ( Predicate, Properties, QueryGeometry, diff --git a/tiatoolbox/models/architecture/hovernet.py b/tiatoolbox/models/architecture/hovernet.py index 2853c4946..9798df62a 100644 --- a/tiatoolbox/models/architecture/hovernet.py +++ b/tiatoolbox/models/architecture/hovernet.py @@ -338,8 +338,7 @@ def __init__( if mode not in ["original", "fast"]: msg = ( - f"Invalid mode {mode} for HoVerNet. " - f"Only support `original` or `fast`." + f"Invalid mode {mode} for HoVerNet. Only support `original` or `fast`." ) raise ValueError( msg, diff --git a/tiatoolbox/models/architecture/nuclick.py b/tiatoolbox/models/architecture/nuclick.py index 77f4ad993..0be45a8e1 100644 --- a/tiatoolbox/models/architecture/nuclick.py +++ b/tiatoolbox/models/architecture/nuclick.py @@ -24,7 +24,7 @@ from tiatoolbox.models.models_abc import ModelABC if TYPE_CHECKING: # pragma: no cover - from tiatoolbox.typing import IntPair + from tiatoolbox.type_hints import IntPair bn_axis = 1 diff --git a/tiatoolbox/models/architecture/utils.py b/tiatoolbox/models/architecture/utils.py index e918a70d8..1f5cbfd64 100644 --- a/tiatoolbox/models/architecture/utils.py +++ b/tiatoolbox/models/architecture/utils.py @@ -88,14 +88,6 @@ def compile_model( logger.warning(msg=msg) return model - # This check will be removed when torch.compile is supported in Python 3.12+ - if sys.version_info > (3, 12): # pragma: no cover - msg = "torch-compile is currently not supported in Python 3.12+." - logger.warning( - msg=msg, - ) - return model - if isinstance( # pragma: no cover model, torch._dynamo.eval_frame.OptimizedModule, # skipcq: PYL-W0212 # noqa: SLF001 diff --git a/tiatoolbox/models/dataset/classification.py b/tiatoolbox/models/dataset/classification.py index cd17dab7e..edf4e28aa 100644 --- a/tiatoolbox/models/dataset/classification.py +++ b/tiatoolbox/models/dataset/classification.py @@ -20,7 +20,7 @@ import torch from PIL.Image import Image - from tiatoolbox.typing import IntPair, Resolution, Units + from tiatoolbox.type_hints import IntPair, Resolution, Units class _TorchPreprocCaller: diff --git a/tiatoolbox/models/engine/multi_task_segmentor.py b/tiatoolbox/models/engine/multi_task_segmentor.py index 3e5cf97e9..2d3df757f 100644 --- a/tiatoolbox/models/engine/multi_task_segmentor.py +++ b/tiatoolbox/models/engine/multi_task_segmentor.py @@ -43,7 +43,7 @@ if TYPE_CHECKING: # pragma: no cover import torch - from tiatoolbox.typing import IntBounds + from tiatoolbox.type_hints import IntBounds # Python is yet to be able to natively pickle Object method/static method. diff --git a/tiatoolbox/models/engine/patch_predictor.py b/tiatoolbox/models/engine/patch_predictor.py index 9989c313e..088f78687 100644 --- a/tiatoolbox/models/engine/patch_predictor.py +++ b/tiatoolbox/models/engine/patch_predictor.py @@ -21,7 +21,7 @@ from tiatoolbox.wsicore.wsireader import VirtualWSIReader, WSIReader if TYPE_CHECKING: # pragma: no cover - from tiatoolbox.typing import IntPair, Resolution, Units + from tiatoolbox.type_hints import IntPair, Resolution, Units class IOPatchPredictorConfig(IOSegmentorConfig): diff --git a/tiatoolbox/models/engine/semantic_segmentor.py b/tiatoolbox/models/engine/semantic_segmentor.py index 029deebf9..791f369f7 100644 --- a/tiatoolbox/models/engine/semantic_segmentor.py +++ b/tiatoolbox/models/engine/semantic_segmentor.py @@ -28,7 +28,7 @@ if TYPE_CHECKING: # pragma: no cover from multiprocessing.managers import Namespace - from tiatoolbox.typing import IntPair, Resolution, Units + from tiatoolbox.type_hints import IntPair, Resolution, Units def _estimate_canvas_parameters( diff --git a/tiatoolbox/tools/patchextraction.py b/tiatoolbox/tools/patchextraction.py index 21fcb4eb0..3de867a19 100644 --- a/tiatoolbox/tools/patchextraction.py +++ b/tiatoolbox/tools/patchextraction.py @@ -20,7 +20,7 @@ from pandas import DataFrame from tiatoolbox.annotation.storage import AnnotationStore - from tiatoolbox.typing import Resolution, Units + from tiatoolbox.type_hints import Resolution, Units def validate_shape(shape: np.ndarray) -> bool: diff --git a/tiatoolbox/tools/registration/wsi_registration.py b/tiatoolbox/tools/registration/wsi_registration.py index a333d77b5..d0a6fc38a 100644 --- a/tiatoolbox/tools/registration/wsi_registration.py +++ b/tiatoolbox/tools/registration/wsi_registration.py @@ -24,7 +24,7 @@ from tiatoolbox.wsicore.wsireader import VirtualWSIReader, WSIReader if TYPE_CHECKING: # pragma: no cover - from tiatoolbox.typing import IntBounds, Resolution, Units + from tiatoolbox.type_hints import IntBounds, Resolution, Units RGB_IMAGE_DIM = 3 BIN_MASK_DIM = 2 diff --git a/tiatoolbox/typing.py b/tiatoolbox/type_hints.py similarity index 100% rename from tiatoolbox/typing.py rename to tiatoolbox/type_hints.py diff --git a/tiatoolbox/utils/image.py b/tiatoolbox/utils/image.py index d697a6e3c..db22eef21 100644 --- a/tiatoolbox/utils/image.py +++ b/tiatoolbox/utils/image.py @@ -18,7 +18,7 @@ ) if TYPE_CHECKING: # pragma: no cover - from tiatoolbox.typing import IntBounds, NumpyPadLiteral + from tiatoolbox.type_hints import IntBounds, NumpyPadLiteral PADDING_TO_BOUNDS = np.array([-1, -1, 1, 1]) """ diff --git a/tiatoolbox/utils/misc.py b/tiatoolbox/utils/misc.py index 1e02a3ce0..a12dd96b2 100644 --- a/tiatoolbox/utils/misc.py +++ b/tiatoolbox/utils/misc.py @@ -220,8 +220,7 @@ def load_stain_matrix(stain_matrix_input: np.ndarray | PathLike) -> np.ndarray: _, __, suffixes = split_path_name_ext(stain_matrix_input) if suffixes[-1] not in [".csv", ".npy"]: msg = ( - "If supplying a path to a stain matrix, " - "use either a npy or a csv file" + "If supplying a path to a stain matrix, use either a npy or a csv file" ) raise FileNotSupportedError( msg, diff --git a/tiatoolbox/visualization/bokeh_app/main.py b/tiatoolbox/visualization/bokeh_app/main.py index b80f19138..97e4b1dc0 100644 --- a/tiatoolbox/visualization/bokeh_app/main.py +++ b/tiatoolbox/visualization/bokeh_app/main.py @@ -1204,7 +1204,7 @@ def segment_on_box() -> None: # Make a mask defining the box thumb = UI["vstate"].wsi.slide_thumbnail() conv_mpp = UI["vstate"].dims[0] / thumb.shape[1] - msg = f'box tl: {UI["box_source"].data["x"][0]}, {UI["box_source"].data["y"][0]}' + msg = f"box tl: {UI['box_source'].data['x'][0]}, {UI['box_source'].data['y'][0]}" logger.info(msg) x = round( (UI["box_source"].data["x"][0] - 0.5 * UI["box_source"].data["width"][0]) diff --git a/tiatoolbox/visualization/tileserver.py b/tiatoolbox/visualization/tileserver.py index b0a427502..acce7dff6 100644 --- a/tiatoolbox/visualization/tileserver.py +++ b/tiatoolbox/visualization/tileserver.py @@ -102,7 +102,7 @@ def __init__( # noqa: PLR0915 if isinstance(layers, list): layers_dict = {"slide": layers[0]} for i, p in enumerate(layers[1:]): - layers_dict[f"layer-{i+1}"] = p + layers_dict[f"layer-{i + 1}"] = p layers = layers_dict # Set up the layer dict. meta = None diff --git a/tiatoolbox/wsicore/wsimeta.py b/tiatoolbox/wsicore/wsimeta.py index 0870e4fe1..97145e5d6 100644 --- a/tiatoolbox/wsicore/wsimeta.py +++ b/tiatoolbox/wsicore/wsimeta.py @@ -20,7 +20,7 @@ if TYPE_CHECKING: # pragma: no cover from collections.abc import Mapping, Sequence - from tiatoolbox.typing import Resolution, Units + from tiatoolbox.type_hints import Resolution, Units class WSIMeta: diff --git a/tiatoolbox/wsicore/wsireader.py b/tiatoolbox/wsicore/wsireader.py index 482a503f4..efcaaa710 100644 --- a/tiatoolbox/wsicore/wsireader.py +++ b/tiatoolbox/wsicore/wsireader.py @@ -34,7 +34,14 @@ import glymur - from tiatoolbox.typing import Bounds, IntBounds, IntPair, NumPair, Resolution, Units + from tiatoolbox.type_hints import ( + Bounds, + IntBounds, + IntPair, + NumPair, + Resolution, + Units, + ) from tiatoolbox.wsicore.metadata.ngff import Multiscales pixman_warning()