From b0307fab3c25917af11e6e141c93ebc4cc8005be Mon Sep 17 00:00:00 2001 From: Henrik Andersson Date: Wed, 24 Jun 2026 19:34:32 +0200 Subject: [PATCH 1/4] Fix mypy union-attr error in vertical comparison colorbar ax.figure is typed Figure | SubFigure | None, so accessing .colorbar directly raised a union-attr error. Narrow to non-None before use. --- src/modelskill/comparison/_vertical_comparison.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/modelskill/comparison/_vertical_comparison.py b/src/modelskill/comparison/_vertical_comparison.py index c6f2a6918..a272d2dfe 100644 --- a/src/modelskill/comparison/_vertical_comparison.py +++ b/src/modelskill/comparison/_vertical_comparison.py @@ -169,7 +169,9 @@ def hovmoller( V = v.reshape(len(T), n_layers) T_grid, _ = np.meshgrid(T, np.arange(n_layers), indexing="ij") cf = ax.contourf(T_grid, Z, V, **kwargs) - cbar = ax.figure.colorbar(cf, ax=ax) + fig = ax.figure + assert fig is not None + cbar = fig.colorbar(cf, ax=ax) cbar.set_label(cmp._unit_text) if self._pos_z(): ax.invert_yaxis() From acf900831dbb3257840bb57ce00182a86a0b80a0 Mon Sep 17 00:00:00 2001 From: Henrik Andersson Date: Thu, 25 Jun 2026 08:17:06 +0200 Subject: [PATCH 2/4] Fix overload-overlap mypy error in ComparerCollection.__getitem__ The slice/Iterable overload overlaps with the int/Hashable overload because str and tuple are both Hashable and Iterable[Hashable]. The overlap is structurally unavoidable, so suppress it in place. --- src/modelskill/comparison/_collection.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/modelskill/comparison/_collection.py b/src/modelskill/comparison/_collection.py index fd4023509..3d1cad9bd 100644 --- a/src/modelskill/comparison/_collection.py +++ b/src/modelskill/comparison/_collection.py @@ -214,7 +214,7 @@ def rename(self, mapping: Dict[str, str]) -> "ComparerCollection": return ComparerCollection(cmps) @overload - def __getitem__(self, x: slice | Iterable[Hashable]) -> ComparerCollection: ... + def __getitem__(self, x: slice | Iterable[Hashable]) -> ComparerCollection: ... # type: ignore[overload-overlap] @overload def __getitem__(self, x: int | Hashable) -> Comparer: ... From d411fceadf5a38daab4c963cd79298d02b49eb52 Mon Sep 17 00:00:00 2001 From: Henrik Andersson Date: Thu, 25 Jun 2026 08:28:26 +0200 Subject: [PATCH 3/4] Drop Python 3.11 support to fix typecheck CI numpy's current type stubs use the 3.12+ `type` statement, which mypy rejects when targeting 3.11, breaking the typecheck on every matrix job. Bump requires-python and mypy's target to 3.12 and drop 3.11 from the CI matrices. --- .github/workflows/full_test.yml | 4 ++-- .github/workflows/python-publish.yml | 2 +- .github/workflows/scheduled_test.yml | 2 +- pyproject.toml | 5 ++--- 4 files changed, 6 insertions(+), 7 deletions(-) diff --git a/.github/workflows/full_test.yml b/.github/workflows/full_test.yml index 26157917a..7881909ca 100644 --- a/.github/workflows/full_test.yml +++ b/.github/workflows/full_test.yml @@ -20,7 +20,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python-version: ["3.11", "3.14"] + python-version: ["3.12", "3.14"] pandas-version: ["pandas2", "pandas3"] # TODO: drop pandas2 once 3.x is well-established steps: @@ -65,7 +65,7 @@ jobs: - name: Set up uv uses: astral-sh/setup-uv@v6 with: - python-version: "3.11" + python-version: "3.12" enable-cache: true - name: Install dependencies (without networks) diff --git a/.github/workflows/python-publish.yml b/.github/workflows/python-publish.yml index 928a0270f..fbb4cc526 100644 --- a/.github/workflows/python-publish.yml +++ b/.github/workflows/python-publish.yml @@ -15,7 +15,7 @@ jobs: strategy: matrix: os: [ubuntu-latest, windows-latest] - python-version: ["3.11", "3.14"] + python-version: ["3.12", "3.14"] steps: - uses: actions/checkout@v4 diff --git a/.github/workflows/scheduled_test.yml b/.github/workflows/scheduled_test.yml index c96cf40fa..9af4045e9 100644 --- a/.github/workflows/scheduled_test.yml +++ b/.github/workflows/scheduled_test.yml @@ -14,7 +14,7 @@ jobs: strategy: matrix: os: [ubuntu-latest, windows-latest] - python-version: ["3.11", "3.14"] + python-version: ["3.12", "3.14"] steps: - uses: actions/checkout@v4 diff --git a/pyproject.toml b/pyproject.toml index 2957549ad..992a2aa97 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -29,14 +29,13 @@ authors = [ description = "Compare results from simulations with observations." license = "MIT" readme = "README.md" -requires-python = ">=3.11" +requires-python = ">=3.12" classifiers = [ "License :: OSI Approved :: MIT License", "Development Status :: 5 - Production/Stable", "Intended Audience :: Science/Research", "Programming Language :: Python", "Programming Language :: Python :: 3", - "Programming Language :: Python :: 3.11", "Programming Language :: Python :: 3.12", "Programming Language :: Python :: 3.13", "Topic :: Scientific/Engineering", @@ -77,7 +76,7 @@ ignore = ["E501"] select = ["E4", "E7", "E9", "F", "D200", "D205"] [tool.mypy] -python_version = "3.11" +python_version = "3.12" ignore_missing_imports = true warn_unreachable = false no_implicit_optional = true From 761d71af7867163b4f92f801f4a5b83f542ec646 Mon Sep 17 00:00:00 2001 From: Henrik Andersson Date: Thu, 25 Jun 2026 08:32:52 +0200 Subject: [PATCH 4/4] Add Python 3.14 trove classifier 3.14 is exercised in CI and allowed by requires-python, but was missing from the classifiers. --- pyproject.toml | 1 + 1 file changed, 1 insertion(+) diff --git a/pyproject.toml b/pyproject.toml index 992a2aa97..890fc7574 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -38,6 +38,7 @@ classifiers = [ "Programming Language :: Python :: 3", "Programming Language :: Python :: 3.12", "Programming Language :: Python :: 3.13", + "Programming Language :: Python :: 3.14", "Topic :: Scientific/Engineering", ]