diff --git a/.binder/environment.yml b/.binder/environment.yml index a60eb372831..2c57bd1121c 100644 --- a/.binder/environment.yml +++ b/.binder/environment.yml @@ -2,7 +2,7 @@ name: xarray-examples channels: - conda-forge dependencies: - - python=3.10 + - python=3.11 - boto3 - bottleneck - cartopy diff --git a/.github/workflows/ci-additional.yaml b/.github/workflows/ci-additional.yaml index 95181ae3761..345c7a8e234 100644 --- a/.github/workflows/ci-additional.yaml +++ b/.github/workflows/ci-additional.yaml @@ -132,7 +132,7 @@ jobs: fail_ci_if_error: false mypy-min: - name: Mypy 3.10 + name: Mypy 3.11 runs-on: "ubuntu-latest" needs: detect-ci-trigger defaults: @@ -140,7 +140,7 @@ jobs: shell: bash -l {0} env: CONDA_ENV_FILE: ci/requirements/environment.yml - PYTHON_VERSION: "3.10" + PYTHON_VERSION: "3.11" steps: - uses: actions/checkout@v4 @@ -239,7 +239,7 @@ jobs: fail_ci_if_error: false pyright39: - name: Pyright 3.10 + name: Pyright 3.11 runs-on: "ubuntu-latest" needs: detect-ci-trigger if: | @@ -252,7 +252,7 @@ jobs: shell: bash -l {0} env: CONDA_ENV_FILE: ci/requirements/environment.yml - PYTHON_VERSION: "3.10" + PYTHON_VERSION: "3.11" steps: - uses: actions/checkout@v4 diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index 76f4f0d5e7e..b115d605ee3 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -47,18 +47,18 @@ jobs: matrix: os: ["ubuntu-latest", "macos-latest", "windows-latest"] # Bookend python versions - python-version: ["3.10", "3.13"] + python-version: ["3.11", "3.13"] env: [""] include: # Minimum python version: - env: "bare-minimum" - python-version: "3.10" + python-version: "3.11" os: ubuntu-latest - env: "bare-min-and-scipy" - python-version: "3.10" + python-version: "3.11" os: ubuntu-latest - env: "min-all-deps" - python-version: "3.10" + python-version: "3.11" os: ubuntu-latest # Latest python version: - env: "all-but-numba" @@ -73,7 +73,7 @@ jobs: # The mypy tests must be executed using only 1 process in order to guarantee # predictable mypy output messages for comparison to expectations. - env: "mypy" - python-version: "3.10" + python-version: "3.11" numprocesses: 1 os: ubuntu-latest - env: "mypy" diff --git a/ci/requirements/all-but-numba.yml b/ci/requirements/all-but-numba.yml index 7c492aec704..712055a0ec2 100644 --- a/ci/requirements/all-but-numba.yml +++ b/ci/requirements/all-but-numba.yml @@ -4,7 +4,7 @@ channels: - nodefaults dependencies: # Pin a "very new numpy" (updated Sept 24, 2024) - - numpy>=2.1.1 + - numpy>=2.2 - aiobotocore - array-api-strict<2.4 - boto3 diff --git a/ci/requirements/bare-min-and-scipy.yml b/ci/requirements/bare-min-and-scipy.yml index 5e5522faaea..bb25af67651 100644 --- a/ci/requirements/bare-min-and-scipy.yml +++ b/ci/requirements/bare-min-and-scipy.yml @@ -3,7 +3,7 @@ channels: - conda-forge - nodefaults dependencies: - - python=3.10 + - python=3.11 - coveralls - pip - pytest @@ -12,7 +12,7 @@ dependencies: - pytest-mypy-plugins - pytest-timeout - pytest-xdist - - numpy=1.24 - - packaging=23.1 - - pandas=2.1 - - scipy=1.11 + - numpy=1.26 + - packaging=24.1 + - pandas=2.2 + - scipy=1.13 diff --git a/ci/requirements/bare-minimum.yml b/ci/requirements/bare-minimum.yml index 02e99d34af2..fafc1aa034a 100644 --- a/ci/requirements/bare-minimum.yml +++ b/ci/requirements/bare-minimum.yml @@ -3,7 +3,7 @@ channels: - conda-forge - nodefaults dependencies: - - python=3.10 + - python=3.11 - coveralls - pip - pytest @@ -12,6 +12,6 @@ dependencies: - pytest-mypy-plugins - pytest-timeout - pytest-xdist - - numpy=1.24 - - packaging=23.1 - - pandas=2.1 + - numpy=1.26 + - packaging=24.1 + - pandas=2.2 diff --git a/ci/requirements/doc.yml b/ci/requirements/doc.yml index 0559f393bd0..64ea08b73ff 100644 --- a/ci/requirements/doc.yml +++ b/ci/requirements/doc.yml @@ -23,7 +23,7 @@ dependencies: - ncdata - netcdf4 - numba - - numpy>=2 + - numpy>=2.2 - packaging - pandas - pooch diff --git a/ci/requirements/environment.yml b/ci/requirements/environment.yml index fc54b6600fe..cc33d8b4681 100644 --- a/ci/requirements/environment.yml +++ b/ci/requirements/environment.yml @@ -26,7 +26,7 @@ dependencies: - numba - numbagg - numexpr - - numpy>=2 + - numpy>=2.2 - opt_einsum - packaging - pandas diff --git a/ci/requirements/min-all-deps.yml b/ci/requirements/min-all-deps.yml index 03e14773d53..b7698c0abd3 100644 --- a/ci/requirements/min-all-deps.yml +++ b/ci/requirements/min-all-deps.yml @@ -7,40 +7,36 @@ dependencies: # Run ci/min_deps_check.py to verify that this file respects the policy. # When upgrading python, numpy, or pandas, must also change # doc/user-guide/installing.rst, doc/user-guide/plotting.rst and setup.py. - - python=3.10 - - array-api-strict=1.0 # dependency for testing the array api compat - - boto3=1.29 - - bottleneck=1.3 - - cartopy=0.22 + - python=3.11 + - array-api-strict=1.1 # dependency for testing the array api compat + - boto3=1.34 + - bottleneck=1.4 + - cartopy=0.23 - cftime=1.6 - coveralls - - dask-core=2023.11 - - distributed=2023.11 - # Flox > 0.8 has a bug with numbagg versions - # It will require numbagg > 0.6 - # so we should just skip that series eventually - # or keep flox pinned for longer than necessary - - flox=0.7 + - dask-core=2024.6 + - distributed=2024.6 + - flox=0.9 - h5netcdf=1.3 # h5py and hdf5 tend to cause conflicts # for e.g. hdf5 1.12 conflicts with h5py=3.1 # prioritize bumping other packages instead - - h5py=3.8 - - hdf5=1.12 + - h5py=3.11 + - hdf5=1.14 - hypothesis - - iris=3.7 - - lxml=4.9 # Optional dep of pydap + - iris=3.9 + - lxml=5.1 # Optional dep of pydap - matplotlib-base=3.8 - nc-time-axis=1.4 # netcdf follows a 1.major.minor[.patch] convention # (see https://github.com/Unidata/netcdf4-python/issues/1090) - - netcdf4=1.6.0 - - numba=0.57 - - numbagg=0.6 - - numpy=1.24 - - packaging=23.2 - - pandas=2.1 - - pint=0.22 + - netcdf4=1.6 + - numba=0.60 + - numbagg=0.8 + - numpy=1.26 + - packaging=24.1 + - pandas=2.2 + - pint=0.24 - pip - pydap=3.5 - pytest @@ -50,9 +46,8 @@ dependencies: - pytest-timeout - pytest-xdist - rasterio=1.3 - - scipy=1.11 + - scipy=1.13 - seaborn=0.13 - - sparse=0.14 + - sparse=0.15 - toolz=0.12 - - typing_extensions=4.8 - - zarr=2.16 + - zarr=2.18 diff --git a/doc/contribute/contributing.rst b/doc/contribute/contributing.rst index e0ece730cd1..339050a7f8a 100644 --- a/doc/contribute/contributing.rst +++ b/doc/contribute/contributing.rst @@ -290,7 +290,7 @@ We'll now kick off a two-step process: .. code-block:: sh # Create and activate the build environment - conda create -c conda-forge -n xarray-tests python=3.10 + conda create -c conda-forge -n xarray-tests python=3.11 # This is for Linux and MacOS conda env update -f ci/requirements/environment.yml diff --git a/doc/getting-started-guide/installing.rst b/doc/getting-started-guide/installing.rst index 4910047014e..cca54585c5f 100644 --- a/doc/getting-started-guide/installing.rst +++ b/doc/getting-started-guide/installing.rst @@ -6,10 +6,10 @@ Installation Required dependencies --------------------- -- Python (3.10 or later) -- `numpy `__ (1.23 or later) -- `packaging `__ (23.1 or later) -- `pandas `__ (2.0 or later) +- Python (3.11 or later) +- `numpy `__ (1.26 or later) +- `packaging `__ (24.1 or later) +- `pandas `__ (2.2 or later) .. _optional-dependencies: diff --git a/doc/whats-new.rst b/doc/whats-new.rst index 607661ed30b..140487185ee 100644 --- a/doc/whats-new.rst +++ b/doc/whats-new.rst @@ -13,10 +13,91 @@ v2025.07.0 (unreleased) New Features ~~~~~~~~~~~~ - Breaking changes ~~~~~~~~~~~~~~~~ +The minimum versions of some dependencies were changed (:issue:`10417`, :pull:`10438`): +By `Dhruva Kumar Kaushal `_. + +.. list-table:: + :header-rows: 1 + :widths: 30 20 20 + + * - Dependency + - Old Version + - New Version + * - Python + - 3.10 + - 3.11 + * - array-api-strict + - 1.0 + - 1.1 + * - boto3 + - 1.29 + - 1.34 + * - bottleneck + - 1.3 + - 1.4 + * - cartopy + - 0.22 + - 0.23 + * - dask-core + - 2023.11 + - 2024.6 + * - distributed + - 2023.11 + - 2024.6 + * - flox + - 0.7 + - 0.9 + * - h5py + - 3.8 + - 3.11 + * - hdf5 + - 1.12 + - 1.14 + * - iris + - 3.7 + - 3.9 + * - lxml + - 4.9 + - 5.1 + * - matplotlib-base + - 3.7 + - 3.8 + * - numba + - 0.57 + - 0.60 + * - numbagg + - 0.6 + - 0.8 + * - numpy + - 1.24 + - 1.26 + * - packaging + - 23.2 + - 24.1 + * - pandas + - 2.1 + - 2.2 + * - pint + - 0.22 + - 0.24 + * - pydap + - N/A + - 3.5 + * - scipy + - 1.11 + - 1.13 + * - sparse + - 0.14 + - 0.15 + * - typing_extensions + - 4.8 + - Removed + * - zarr + - 2.16 + - 2.18 Deprecations ~~~~~~~~~~~~ diff --git a/pyproject.toml b/pyproject.toml index c980c204b5f..0c1e9fb25f4 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -6,7 +6,6 @@ classifiers = [ "Intended Audience :: Science/Research", "Programming Language :: Python", "Programming Language :: Python :: 3", - "Programming Language :: Python :: 3.10", "Programming Language :: Python :: 3.11", "Programming Language :: Python :: 3.12", "Programming Language :: Python :: 3.13", @@ -17,9 +16,9 @@ dynamic = ["version"] license = "Apache-2.0" name = "xarray" readme = "README.md" -requires-python = ">=3.10" +requires-python = ">=3.11" -dependencies = ["numpy>=1.24", "packaging>=23.2", "pandas>=2.1"] +dependencies = ["numpy>=1.26", "packaging>=24.1", "pandas>=2.2"] # We don't encode minimum requirements here (though if we can write a script to # generate the text from `min_deps_check.py`, that's welcome...). We do add @@ -27,21 +26,28 @@ dependencies = ["numpy>=1.24", "packaging>=23.2", "pandas>=2.1"] # note that it's not a direct dependency of xarray. [project.optional-dependencies] -accel = ["scipy", "bottleneck", "numbagg", "numba>=0.54", "flox", "opt_einsum"] +accel = [ + "scipy>=1.13", + "bottleneck", + "numbagg>=0.8", + "numba>=0.59", + "flox>=0.9", + "opt_einsum", +] complete = ["xarray[accel,etc,io,parallel,viz]"] io = [ - "netCDF4", + "netCDF4>=1.6.0", "h5netcdf", - "scipy", - 'pydap; python_version<"3.10"', - "zarr", + "pydap", + "scipy>=1.13", + "zarr>=2.18", "fsspec", "cftime", "pooch", ] -etc = ["sparse"] +etc = ["sparse>=0.15"] parallel = ["dask[complete]"] -viz = ["cartopy", "matplotlib", "nc-time-axis", "seaborn"] +viz = ["cartopy>=0.23", "matplotlib", "nc-time-axis", "seaborn"] types = [ "pandas-stubs", "scipy-stubs", diff --git a/xarray/core/accessor_dt.py b/xarray/core/accessor_dt.py index c78b38caf63..86e875cab5c 100644 --- a/xarray/core/accessor_dt.py +++ b/xarray/core/accessor_dt.py @@ -20,7 +20,7 @@ from xarray.namedarray.utils import is_duck_dask_array if TYPE_CHECKING: - import sys + from typing import Self from numpy.typing import DTypeLike @@ -28,11 +28,6 @@ from xarray.core.dataset import Dataset from xarray.core.types import CFCalendar - if sys.version_info >= (3, 11): - from typing import Self - else: - from typing_extensions import Self - def _season_from_months(months): """Compute season (DJF, MAM, JJA, SON) from month ordinal""" diff --git a/xarray/core/datatree_mapping.py b/xarray/core/datatree_mapping.py index 6262c7f19cd..00e575ef448 100644 --- a/xarray/core/datatree_mapping.py +++ b/xarray/core/datatree_mapping.py @@ -1,6 +1,5 @@ from __future__ import annotations -import sys from collections.abc import Callable, Mapping from typing import TYPE_CHECKING, Any, cast, overload @@ -162,11 +161,7 @@ def wrapper(*args, **kwargs): def add_note(err: BaseException, msg: str) -> None: - # TODO: remove once python 3.10 can be dropped - if sys.version_info < (3, 11): - err.__notes__ = getattr(err, "__notes__", []) + [msg] # type: ignore[attr-defined] - else: - err.add_note(msg) + err.add_note(msg) def _check_single_set_return_values(path_to_node: str, obj: Any) -> int | None: diff --git a/xarray/core/types.py b/xarray/core/types.py index 2124aee0ad4..d3fd0180104 100644 --- a/xarray/core/types.py +++ b/xarray/core/types.py @@ -1,7 +1,6 @@ from __future__ import annotations import datetime -import sys from collections.abc import Callable, Collection, Hashable, Iterator, Mapping, Sequence from types import EllipsisType from typing import ( @@ -9,7 +8,9 @@ Any, Literal, Protocol, + Self, SupportsIndex, + TypeAlias, TypeVar, Union, overload, @@ -18,21 +19,6 @@ import numpy as np import pandas as pd - -try: - if sys.version_info >= (3, 11): - from typing import Self, TypeAlias - else: - from typing import TypeAlias - - from typing_extensions import Self -except ImportError: - if TYPE_CHECKING: - raise - else: - Self: Any = None - - from numpy._typing import _SupportsDType from numpy.typing import ArrayLike diff --git a/xarray/namedarray/_typing.py b/xarray/namedarray/_typing.py index 2dba06a5d44..635adc89f08 100644 --- a/xarray/namedarray/_typing.py +++ b/xarray/namedarray/_typing.py @@ -1,6 +1,5 @@ from __future__ import annotations -import sys from collections.abc import Callable, Hashable, Iterable, Mapping, Sequence from enum import Enum from types import EllipsisType, ModuleType @@ -20,10 +19,7 @@ import numpy as np try: - if sys.version_info >= (3, 11): - from typing import TypeAlias - else: - from typing import TypeAlias + from typing import TypeAlias except ImportError: if TYPE_CHECKING: raise diff --git a/xarray/namedarray/core.py b/xarray/namedarray/core.py index 9d5b058439e..dac8162ca45 100644 --- a/xarray/namedarray/core.py +++ b/xarray/namedarray/core.py @@ -2,7 +2,6 @@ import copy import math -import sys import warnings from collections.abc import Callable, Hashable, Iterable, Mapping, Sequence from itertools import starmap @@ -86,10 +85,7 @@ PostComputeCallable: Any # type: ignore[no-redef] PostPersistCallable: Any # type: ignore[no-redef] - if sys.version_info >= (3, 11): - from typing import Self - else: - from typing_extensions import Self + from typing import Self T_NamedArray = TypeVar("T_NamedArray", bound="_NamedArray[Any]") T_NamedArrayInteger = TypeVar( diff --git a/xarray/util/generate_ops.py b/xarray/util/generate_ops.py index 3300bbf594a..0c5ac2f2eb8 100644 --- a/xarray/util/generate_ops.py +++ b/xarray/util/generate_ops.py @@ -133,7 +133,7 @@ def {{ method }}(self, *args: Any, **kwargs: Any) -> Self: # We require a "hack" to tell type checkers that e.g. Variable + DataArray = DataArray # In reality this returns NotImplemented, but this is not a valid type in python 3.9. # Therefore, we return DataArray. In reality this would call DataArray.__add__(Variable) -# TODO: change once python 3.10 is the minimum. +# TODO: change once python 3.11 is the minimum. # # Mypy seems to require that __iadd__ and __add__ have the same signature. # This requires some extra type: ignores[misc] in the inplace methods :/