diff --git a/.appveyor.yml b/.appveyor.yml index 360760ac8d..391cf1071c 100644 --- a/.appveyor.yml +++ b/.appveyor.yml @@ -9,7 +9,7 @@ platform: - x86 environment: matrix: - - PYTHON: 36 + - PYTHON: 38 CONFIG: Debug install: - ps: | diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index ca1ed75646..6b05bc7f06 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -33,7 +33,7 @@ jobs: matrix: runs-on: [ubuntu-20.04, windows-2022, macos-13] python: - - '3.6' + - '3.8' - '3.9' - '3.12' - '3.13' @@ -49,16 +49,17 @@ jobs: include: # Just add a key - runs-on: ubuntu-20.04 - python: '3.6' + python: '3.8' args: > -DPYBIND11_FINDPYTHON=ON -DCMAKE_CXX_FLAGS="-D_=1" + exercise_D_: 1 - runs-on: ubuntu-20.04 python: 'pypy-3.8' args: > -DPYBIND11_FINDPYTHON=ON - runs-on: windows-2019 - python: '3.6' + python: '3.8' args: > -DPYBIND11_FINDPYTHON=ON # Inject a couple Windows 2019 runs @@ -83,7 +84,7 @@ jobs: - name: Setup Boost (Linux) # Can't use boost + define _ - if: runner.os == 'Linux' && matrix.python != '3.6' + if: runner.os == 'Linux' && matrix.exercise_D_ != 1 run: sudo apt-get install libboost-dev - name: Setup Boost (macOS) @@ -134,9 +135,7 @@ jobs: run: cmake --build . --target pytest -j 2 - name: C++11 tests - # TODO: Figure out how to load the DLL on Python 3.8+ - if: "!(runner.os == 'Windows' && (matrix.python == 3.8 || matrix.python == 3.9 || matrix.python == '3.10' || matrix.python == '3.11' || matrix.python == 'pypy-3.8'))" - run: cmake --build . --target cpptest -j 2 + run: cmake --build . --target cpptest -j 2 - name: Interface test C++11 run: cmake --build . --target test_cmake_build @@ -165,8 +164,6 @@ jobs: run: cmake --build build2 --target pytest - name: C++ tests - # TODO: Figure out how to load the DLL on Python 3.8+ - if: "!(runner.os == 'Windows' && (matrix.python == 3.8 || matrix.python == 3.9 || matrix.python == '3.10' || matrix.python == '3.11' || matrix.python == 'pypy-3.8'))" run: cmake --build build2 --target cpptest # Third build - C++17 mode with unstable ABI @@ -660,15 +657,13 @@ jobs: cmake --build build-17 --target test_cmake_build - # Testing on CentOS (manylinux uses a centos base, and this is an easy way - # to get GCC 4.8, which is the manylinux1 compiler). + # Testing on CentOS (manylinux uses a centos base). centos: runs-on: ubuntu-latest strategy: fail-fast: false matrix: container: - - "centos:7" # GCC 4.8 - "almalinux:8" - "almalinux:9" @@ -678,18 +673,13 @@ jobs: steps: - name: Latest actions/checkout uses: actions/checkout@v4 - if: matrix.container != 'centos:7' - - name: Pin actions/checkout as required for centos:7 - uses: actions/checkout@v3 - if: matrix.container == 'centos:7' + - name: Add Python 3.8 + if: matrix.container == 'almalinux:8' + run: dnf update -y && dnf install -y python38-devel gcc-c++ make git - - name: Add Python 3 (RHEL 7) - if: matrix.container == 'centos:7' - run: yum update -y && yum install -y python3-devel gcc-c++ make git - - - name: Add Python 3 (RHEL 8+) - if: matrix.container != 'centos:7' + - name: Add Python 3 (default) + if: matrix.container != 'almalinux:8' run: dnf update -y && dnf install -y python3-devel gcc-c++ make git - name: Update pip @@ -812,17 +802,25 @@ jobs: fail-fast: false matrix: python: - - 3.6 - - 3.7 - - 3.8 - - 3.9 + - '3.7' + - '3.8' + - '3.9' + - '3.10' + - '3.11' + - '3.12' include: - - python: 3.9 + - python: '3.12' args: -DCMAKE_CXX_STANDARD=20 - - python: 3.8 + - python: '3.11' + args: -DCMAKE_CXX_STANDARD=20 + - python: '3.10' + args: -DCMAKE_CXX_STANDARD=20 + - python: '3.9' + args: -DCMAKE_CXX_STANDARD=20 + - python: '3.8' args: -DCMAKE_CXX_STANDARD=17 - - python: 3.7 + - python: '3.7' args: -DCMAKE_CXX_STANDARD=14 diff --git a/.github/workflows/ci_sh_def.yml b/.github/workflows/ci_sh_def.yml index 11d24fcf7c..92b43b6634 100644 --- a/.github/workflows/ci_sh_def.yml +++ b/.github/workflows/ci_sh_def.yml @@ -45,7 +45,7 @@ jobs: matrix: runs-on: [ubuntu-20.04, windows-2022, macos-13] python: - - '3.6' + - '3.8' - '3.9' - '3.12' - '3.13' @@ -61,16 +61,17 @@ jobs: include: # Just add a key - runs-on: ubuntu-20.04 - python: '3.6' + python: '3.8' args: > -DPYBIND11_FINDPYTHON=ON -DCMAKE_CXX_FLAGS="-D_=1" + exercise_D_: 1 - runs-on: ubuntu-20.04 python: 'pypy-3.8' args: > -DPYBIND11_FINDPYTHON=ON - runs-on: windows-2019 - python: '3.6' + python: '3.8' args: > -DPYBIND11_FINDPYTHON=ON # Inject a couple Windows 2019 runs @@ -95,7 +96,7 @@ jobs: - name: Setup Boost (Linux) # Can't use boost + define _ - if: runner.os == 'Linux' && matrix.python != '3.6' + if: runner.os == 'Linux' && matrix.exercise_D_ != 1 run: sudo apt-get install libboost-dev - name: Setup Boost (macOS) @@ -147,9 +148,7 @@ jobs: run: cmake --build . --target pytest -j 2 - name: C++11 tests - # TODO: Figure out how to load the DLL on Python 3.8+ - if: "!(runner.os == 'Windows' && (matrix.python == 3.8 || matrix.python == 3.9 || matrix.python == '3.10' || matrix.python == '3.11' || matrix.python == 'pypy-3.8'))" - run: cmake --build . --target cpptest -j 2 + run: cmake --build . --target cpptest -j 2 - name: Interface test C++11 run: cmake --build . --target test_cmake_build @@ -179,8 +178,6 @@ jobs: run: cmake --build build2 --target pytest - name: C++ tests - # TODO: Figure out how to load the DLL on Python 3.8+ - if: "!(runner.os == 'Windows' && (matrix.python == 3.8 || matrix.python == 3.9 || matrix.python == '3.10' || matrix.python == '3.11' || matrix.python == 'pypy-3.8'))" run: cmake --build build2 --target cpptest # Third build - C++17 mode with unstable ABI @@ -682,15 +679,13 @@ jobs: cmake --build build-17 --target test_cmake_build - # Testing on CentOS (manylinux uses a centos base, and this is an easy way - # to get GCC 4.8, which is the manylinux1 compiler). + # Testing on CentOS (manylinux uses a centos base). centos: runs-on: ubuntu-latest strategy: fail-fast: false matrix: container: - - "centos:7" # GCC 4.8 - "almalinux:8" - "almalinux:9" @@ -700,18 +695,13 @@ jobs: steps: - name: Latest actions/checkout uses: actions/checkout@v4 - if: matrix.container != 'centos:7' - - name: Pin actions/checkout as required for centos:7 - uses: actions/checkout@v3 - if: matrix.container == 'centos:7' + - name: Add Python 3.8 + if: matrix.container == 'almalinux:8' + run: dnf update -y && dnf install -y python38-devel gcc-c++ make git - - name: Add Python 3 (RHEL 7) - if: matrix.container == 'centos:7' - run: yum update -y && yum install -y python3-devel gcc-c++ make git - - - name: Add Python 3 (RHEL 8+) - if: matrix.container != 'centos:7' + - name: Add Python 3 (default) + if: matrix.container != 'almalinux:8' run: dnf update -y && dnf install -y python3-devel gcc-c++ make git - name: Update pip @@ -836,17 +826,25 @@ jobs: fail-fast: false matrix: python: - - 3.6 - - 3.7 - - 3.8 - - 3.9 + - '3.7' + - '3.8' + - '3.9' + - '3.10' + - '3.11' + - '3.12' include: - - python: 3.9 + - python: '3.12' args: -DCMAKE_CXX_STANDARD=20 - - python: 3.8 + - python: '3.11' + args: -DCMAKE_CXX_STANDARD=20 + - python: '3.10' + args: -DCMAKE_CXX_STANDARD=20 + - python: '3.9' + args: -DCMAKE_CXX_STANDARD=20 + - python: '3.8' args: -DCMAKE_CXX_STANDARD=17 - - python: 3.7 + - python: '3.7' args: -DCMAKE_CXX_STANDARD=14 diff --git a/.github/workflows/ci_sh_def.yml.patch b/.github/workflows/ci_sh_def.yml.patch index 262e4f75fe..439763ece7 100644 --- a/.github/workflows/ci_sh_def.yml.patch +++ b/.github/workflows/ci_sh_def.yml.patch @@ -1,5 +1,5 @@ ---- ci.yml 2024-06-19 10:06:18.454361731 -0700 -+++ ci_sh_def.yml 2024-06-19 10:07:59.514269934 -0700 +--- ci.yml 2024-06-21 22:56:01.205982412 -0700 ++++ ci_sh_def.yml 2024-06-21 22:57:45.189902320 -0700 @@ -1,4 +1,16 @@ -name: CI +# PLEASE KEEP THIS GROUP OF FILES IN SYNC AT ALL TIMES: @@ -27,7 +27,7 @@ cancel-in-progress: true env: -@@ -125,6 +137,7 @@ +@@ -126,6 +138,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=11 @@ -35,7 +35,7 @@ ${{ matrix.args }} - name: Build C++11 -@@ -156,6 +169,7 @@ +@@ -155,6 +168,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=17 @@ -43,7 +43,7 @@ ${{ matrix.args }} - name: Build -@@ -177,6 +191,7 @@ +@@ -174,6 +188,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=17 @@ -51,7 +51,7 @@ -DPYBIND11_INTERNALS_VERSION=10000000 ${{ matrix.args }} -@@ -220,6 +235,7 @@ +@@ -217,6 +232,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DPython_ROOT_DIR=.venv @@ -59,7 +59,7 @@ - name: Build C++11 run: cmake --build build -j2 -@@ -293,6 +309,7 @@ +@@ -290,6 +306,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=17 @@ -67,7 +67,7 @@ - name: Build run: cmake --build build -j 2 -@@ -361,6 +378,7 @@ +@@ -358,6 +375,7 @@ -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DCMAKE_CXX_STANDARD=${{ matrix.std }} @@ -75,7 +75,7 @@ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") - name: Build -@@ -390,7 +408,7 @@ +@@ -387,7 +405,7 @@ run: apt-get update && DEBIAN_FRONTEND="noninteractive" apt-get install -y cmake git python3-dev python3-pytest python3-numpy - name: Configure @@ -84,7 +84,7 @@ - name: Build run: cmake --build build -j2 --verbose -@@ -478,7 +496,7 @@ +@@ -475,7 +493,7 @@ cmake -S . -B build -DDOWNLOAD_CATCH=ON \ -DCMAKE_CXX_STANDARD=17 \ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") \ @@ -93,7 +93,7 @@ -DPYBIND11_TEST_FILTER="test_smart_ptr.cpp" - name: Build -@@ -532,6 +550,7 @@ +@@ -529,6 +547,7 @@ -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DCMAKE_CXX_STANDARD=${{ matrix.std }} @@ -101,7 +101,7 @@ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") - name: Build -@@ -554,6 +573,7 @@ +@@ -551,6 +570,7 @@ -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DCMAKE_CXX_STANDARD=${{ matrix.std }} @@ -109,7 +109,7 @@ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") "-DPYBIND11_TEST_OVERRIDE=test_call_policies.cpp;test_gil_scoped.cpp;test_thread.cpp" -@@ -603,6 +623,7 @@ +@@ -600,6 +620,7 @@ -DDOWNLOAD_CATCH=ON \ -DDOWNLOAD_EIGEN=OFF \ -DCMAKE_CXX_STANDARD=11 \ @@ -117,7 +117,7 @@ -DCMAKE_CXX_COMPILER=$(which icpc) \ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") -@@ -635,6 +656,7 @@ +@@ -632,6 +653,7 @@ -DDOWNLOAD_CATCH=ON \ -DDOWNLOAD_EIGEN=OFF \ -DCMAKE_CXX_STANDARD=17 \ @@ -125,7 +125,7 @@ -DCMAKE_CXX_COMPILER=$(which icpc) \ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") -@@ -713,6 +735,7 @@ +@@ -703,6 +725,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=11 @@ -133,7 +133,7 @@ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") - name: Build -@@ -763,6 +786,7 @@ +@@ -753,6 +776,7 @@ cmake ../pybind11-tests -DDOWNLOAD_CATCH=ON -DPYBIND11_WERROR=ON @@ -141,7 +141,7 @@ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") working-directory: /build-tests -@@ -858,6 +882,7 @@ +@@ -856,6 +880,7 @@ -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON @@ -149,7 +149,7 @@ ${{ matrix.args }} - name: Build C++11 run: cmake --build build -j 2 -@@ -912,6 +937,7 @@ +@@ -910,6 +935,7 @@ -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON @@ -157,7 +157,7 @@ ${{ matrix.args }} - name: Build C++11 run: cmake --build build --config Debug -j 2 -@@ -954,6 +980,7 @@ +@@ -952,6 +978,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=20 @@ -165,7 +165,7 @@ - name: Build C++20 run: cmake --build build -j 2 -@@ -974,6 +1001,7 @@ +@@ -972,6 +999,7 @@ -DDOWNLOAD_CATCH=ON -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_STANDARD=20 @@ -173,7 +173,7 @@ "-DPYBIND11_TEST_OVERRIDE=test_call_policies.cpp;test_gil_scoped.cpp;test_thread.cpp" - name: Build C++20 - Exercise cmake -DPYBIND11_TEST_OVERRIDE -@@ -1026,6 +1054,7 @@ +@@ -1024,6 +1052,7 @@ run: >- cmake -G "MinGW Makefiles" -DCMAKE_CXX_STANDARD=11 -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DPYTHON_EXECUTABLE=$(python -c "import sys; print(sys.executable)") @@ -181,7 +181,7 @@ -S . -B build - name: Build C++11 -@@ -1047,6 +1076,7 @@ +@@ -1045,6 +1074,7 @@ run: >- cmake -G "MinGW Makefiles" -DCMAKE_CXX_STANDARD=14 -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DPYTHON_EXECUTABLE=$(python -c "import sys; print(sys.executable)") @@ -189,7 +189,7 @@ -S . -B build2 - name: Build C++14 -@@ -1068,6 +1098,7 @@ +@@ -1066,6 +1096,7 @@ run: >- cmake -G "MinGW Makefiles" -DCMAKE_CXX_STANDARD=17 -DPYBIND11_WERROR=ON -DDOWNLOAD_CATCH=ON -DPYTHON_EXECUTABLE=$(python -c "import sys; print(sys.executable)") @@ -197,7 +197,7 @@ -S . -B build3 - name: Build C++17 -@@ -1135,6 +1166,7 @@ +@@ -1133,6 +1164,7 @@ -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_CXX_STANDARD=17 @@ -205,7 +205,7 @@ - name: Build run: cmake --build . -j 2 -@@ -1200,6 +1232,7 @@ +@@ -1198,6 +1230,7 @@ -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_CXX_STANDARD=17 @@ -213,7 +213,7 @@ -DPYTHON_EXECUTABLE=$(python3 -c "import sys; print(sys.executable)") - name: Build -@@ -1223,6 +1256,7 @@ +@@ -1221,6 +1254,7 @@ -DDOWNLOAD_EIGEN=ON -DCMAKE_CXX_COMPILER=clang++ -DCMAKE_CXX_STANDARD=17 diff --git a/.github/workflows/pip.yml b/.github/workflows/pip.yml index ad30cbcbd5..4d22727cb4 100644 --- a/.github/workflows/pip.yml +++ b/.github/workflows/pip.yml @@ -22,19 +22,18 @@ env: jobs: # This builds the sdists and wheels and makes sure the files are exactly as - # expected. Using Windows and Python 3.6, since that is often the most - # challenging matrix element. + # expected. test-packaging: - name: 🐍 3.6 • 📦 tests • windows-latest + name: 🐍 3.8 • 📦 tests • windows-latest runs-on: windows-latest steps: - uses: actions/checkout@v4 - - name: Setup 🐍 3.6 + - name: Setup 🐍 3.8 uses: actions/setup-python@v5 with: - python-version: 3.6 + python-version: 3.8 - name: Prepare env run: | diff --git a/README.rst b/README.rst index 895fc60d0b..a4f9d1e69d 100644 --- a/README.rst +++ b/README.rst @@ -38,7 +38,7 @@ dependency. Think of this library as a tiny self-contained version of Boost.Python with everything stripped away that isn't relevant for binding generation. Without comments, the core header files only require ~4K -lines of code and depend on Python (3.6+, or PyPy) and the C++ +lines of code and depend on Python (3.7+, or PyPy) and the C++ standard library. This compact implementation was possible thanks to some C++11 language features (specifically: tuples, lambda functions and variadic templates). Since its creation, this library has grown beyond @@ -83,7 +83,7 @@ Goodies In addition to the core functionality, pybind11 provides some extra goodies: -- Python 3.6+, and PyPy3 7.3 are supported with an implementation-agnostic +- Python 3.7+, and PyPy3 7.3 are supported with an implementation-agnostic interface (pybind11 2.9 was the last version to support Python 2 and 3.5). - It is possible to bind C++11 lambda functions with captured diff --git a/docs/benchmark.py b/docs/benchmark.py index fb49fd0488..a273674f45 100644 --- a/docs/benchmark.py +++ b/docs/benchmark.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import datetime as dt import os import random diff --git a/docs/compiling.rst b/docs/compiling.rst index 970bd5df82..0b7c178b01 100644 --- a/docs/compiling.rst +++ b/docs/compiling.rst @@ -426,7 +426,7 @@ with ``PYTHON_EXECUTABLE``. For example: .. code-block:: bash - cmake -DPYBIND11_PYTHON_VERSION=3.6 .. + cmake -DPYBIND11_PYTHON_VERSION=3.7 .. # Another method: cmake -DPYTHON_EXECUTABLE=/path/to/python .. @@ -493,7 +493,7 @@ existing targets instead: cmake_minimum_required(VERSION 3.15...3.22) project(example LANGUAGES CXX) - find_package(Python 3.6 COMPONENTS Interpreter Development REQUIRED) + find_package(Python 3.7 COMPONENTS Interpreter Development REQUIRED) find_package(pybind11 CONFIG REQUIRED) # or add_subdirectory(pybind11) diff --git a/docs/conf.py b/docs/conf.py index 9ba106d51b..e5cba03826 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -11,6 +11,7 @@ # # All configuration values have a default; values that are commented out # serve to show the default. +from __future__ import annotations import os import re diff --git a/include/pybind11/detail/class.h b/include/pybind11/detail/class.h index 2b06fd5fe4..33a1e8a124 100644 --- a/include/pybind11/detail/class.h +++ b/include/pybind11/detail/class.h @@ -569,17 +569,9 @@ inline void enable_dynamic_attributes(PyHeapTypeObject *heap_type) { type->tp_traverse = pybind11_traverse; type->tp_clear = pybind11_clear; - static PyGetSetDef getset[] = {{ -#if PY_VERSION_HEX < 0x03070000 - const_cast("__dict__"), -#else - "__dict__", -#endif - PyObject_GenericGetDict, - PyObject_GenericSetDict, - nullptr, - nullptr}, - {nullptr, nullptr, nullptr, nullptr, nullptr}}; + static PyGetSetDef getset[] + = {{"__dict__", PyObject_GenericGetDict, PyObject_GenericSetDict, nullptr, nullptr}, + {nullptr, nullptr, nullptr, nullptr, nullptr}}; type->tp_getset = getset; } diff --git a/include/pybind11/detail/common.h b/include/pybind11/detail/common.h index f0f3c50d3d..698421d840 100644 --- a/include/pybind11/detail/common.h +++ b/include/pybind11/detail/common.h @@ -272,9 +272,8 @@ PYBIND11_WARNING_DISABLE_MSVC(4505) #endif #include -// Reminder: WITH_THREAD is always defined if PY_VERSION_HEX >= 0x03070000 -#if PY_VERSION_HEX < 0x03060000 -# error "PYTHON < 3.6 IS UNSUPPORTED. pybind11 v2.9 was the last to support Python 2 and 3.5." +#if PY_VERSION_HEX < 0x03070000 +# error "PYTHON < 3.7 IS UNSUPPORTED. pybind11 v2.12 was the last to support Python 3.6." #endif #include #include diff --git a/include/pybind11/detail/internals.h b/include/pybind11/detail/internals.h index c7580728fd..5da383269f 100644 --- a/include/pybind11/detail/internals.h +++ b/include/pybind11/detail/internals.h @@ -11,7 +11,7 @@ #include "common.h" -#if defined(WITH_THREAD) && defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) +#if defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) # include "../gil.h" #endif @@ -65,65 +65,41 @@ inline PyObject *make_object_base_type(PyTypeObject *metaclass); // The old Python Thread Local Storage (TLS) API is deprecated in Python 3.7 in favor of the new // Thread Specific Storage (TSS) API. -#if PY_VERSION_HEX >= 0x03070000 // Avoid unnecessary allocation of `Py_tss_t`, since we cannot use // `Py_LIMITED_API` anyway. -# if PYBIND11_INTERNALS_VERSION > 4 -# define PYBIND11_TLS_KEY_REF Py_tss_t & -# if defined(__clang__) -# define PYBIND11_TLS_KEY_INIT(var) \ - _Pragma("clang diagnostic push") /**/ \ - _Pragma("clang diagnostic ignored \"-Wmissing-field-initializers\"") /**/ \ - Py_tss_t var \ - = Py_tss_NEEDS_INIT; \ - _Pragma("clang diagnostic pop") -# elif defined(__GNUC__) && !defined(__INTEL_COMPILER) -# define PYBIND11_TLS_KEY_INIT(var) \ - _Pragma("GCC diagnostic push") /**/ \ - _Pragma("GCC diagnostic ignored \"-Wmissing-field-initializers\"") /**/ \ - Py_tss_t var \ - = Py_tss_NEEDS_INIT; \ - _Pragma("GCC diagnostic pop") -# else -# define PYBIND11_TLS_KEY_INIT(var) Py_tss_t var = Py_tss_NEEDS_INIT; -# endif -# define PYBIND11_TLS_KEY_CREATE(var) (PyThread_tss_create(&(var)) == 0) -# define PYBIND11_TLS_GET_VALUE(key) PyThread_tss_get(&(key)) -# define PYBIND11_TLS_REPLACE_VALUE(key, value) PyThread_tss_set(&(key), (value)) -# define PYBIND11_TLS_DELETE_VALUE(key) PyThread_tss_set(&(key), nullptr) -# define PYBIND11_TLS_FREE(key) PyThread_tss_delete(&(key)) +#if PYBIND11_INTERNALS_VERSION > 4 +# define PYBIND11_TLS_KEY_REF Py_tss_t & +# if defined(__clang__) +# define PYBIND11_TLS_KEY_INIT(var) \ + _Pragma("clang diagnostic push") /**/ \ + _Pragma("clang diagnostic ignored \"-Wmissing-field-initializers\"") /**/ \ + Py_tss_t var \ + = Py_tss_NEEDS_INIT; \ + _Pragma("clang diagnostic pop") +# elif defined(__GNUC__) && !defined(__INTEL_COMPILER) +# define PYBIND11_TLS_KEY_INIT(var) \ + _Pragma("GCC diagnostic push") /**/ \ + _Pragma("GCC diagnostic ignored \"-Wmissing-field-initializers\"") /**/ \ + Py_tss_t var \ + = Py_tss_NEEDS_INIT; \ + _Pragma("GCC diagnostic pop") # else -# define PYBIND11_TLS_KEY_REF Py_tss_t * -# define PYBIND11_TLS_KEY_INIT(var) Py_tss_t *var = nullptr; -# define PYBIND11_TLS_KEY_CREATE(var) \ - (((var) = PyThread_tss_alloc()) != nullptr && (PyThread_tss_create((var)) == 0)) -# define PYBIND11_TLS_GET_VALUE(key) PyThread_tss_get((key)) -# define PYBIND11_TLS_REPLACE_VALUE(key, value) PyThread_tss_set((key), (value)) -# define PYBIND11_TLS_DELETE_VALUE(key) PyThread_tss_set((key), nullptr) -# define PYBIND11_TLS_FREE(key) PyThread_tss_free(key) +# define PYBIND11_TLS_KEY_INIT(var) Py_tss_t var = Py_tss_NEEDS_INIT; # endif +# define PYBIND11_TLS_KEY_CREATE(var) (PyThread_tss_create(&(var)) == 0) +# define PYBIND11_TLS_GET_VALUE(key) PyThread_tss_get(&(key)) +# define PYBIND11_TLS_REPLACE_VALUE(key, value) PyThread_tss_set(&(key), (value)) +# define PYBIND11_TLS_DELETE_VALUE(key) PyThread_tss_set(&(key), nullptr) +# define PYBIND11_TLS_FREE(key) PyThread_tss_delete(&(key)) #else -// Usually an int but a long on Cygwin64 with Python 3.x -# define PYBIND11_TLS_KEY_REF decltype(PyThread_create_key()) -# define PYBIND11_TLS_KEY_INIT(var) PYBIND11_TLS_KEY_REF var = 0; -# define PYBIND11_TLS_KEY_CREATE(var) (((var) = PyThread_create_key()) != -1) -# define PYBIND11_TLS_GET_VALUE(key) PyThread_get_key_value((key)) -# if defined(PYPY_VERSION) -// On CPython < 3.4 and on PyPy, `PyThread_set_key_value` strangely does not set -// the value if it has already been set. Instead, it must first be deleted and -// then set again. -inline void tls_replace_value(PYBIND11_TLS_KEY_REF key, void *value) { - PyThread_delete_key_value(key); - PyThread_set_key_value(key, value); -} -# define PYBIND11_TLS_DELETE_VALUE(key) PyThread_delete_key_value(key) -# define PYBIND11_TLS_REPLACE_VALUE(key, value) \ - ::pybind11::detail::tls_replace_value((key), (value)) -# else -# define PYBIND11_TLS_DELETE_VALUE(key) PyThread_set_key_value((key), nullptr) -# define PYBIND11_TLS_REPLACE_VALUE(key, value) PyThread_set_key_value((key), (value)) -# endif -# define PYBIND11_TLS_FREE(key) (void) key +# define PYBIND11_TLS_KEY_REF Py_tss_t * +# define PYBIND11_TLS_KEY_INIT(var) Py_tss_t *var = nullptr; +# define PYBIND11_TLS_KEY_CREATE(var) \ + (((var) = PyThread_tss_alloc()) != nullptr && (PyThread_tss_create((var)) == 0)) +# define PYBIND11_TLS_GET_VALUE(key) PyThread_tss_get((key)) +# define PYBIND11_TLS_REPLACE_VALUE(key, value) PyThread_tss_set((key), (value)) +# define PYBIND11_TLS_DELETE_VALUE(key) PyThread_tss_set((key), nullptr) +# define PYBIND11_TLS_FREE(key) PyThread_tss_free(key) #endif // Python loads modules by default with dlopen with the RTLD_LOCAL flag; under libc++ and possibly @@ -217,28 +193,27 @@ struct internals { PyTypeObject *static_property_type; PyTypeObject *default_metaclass; PyObject *instance_base; -#if defined(WITH_THREAD) // Unused if PYBIND11_SIMPLE_GIL_MANAGEMENT is defined: PYBIND11_TLS_KEY_INIT(tstate) -# if PYBIND11_INTERNALS_VERSION > 4 +#if PYBIND11_INTERNALS_VERSION > 4 PYBIND11_TLS_KEY_INIT(loader_life_support_tls_key) -# endif // PYBIND11_INTERNALS_VERSION > 4 +#endif // PYBIND11_INTERNALS_VERSION > 4 // Unused if PYBIND11_SIMPLE_GIL_MANAGEMENT is defined: PyInterpreterState *istate = nullptr; -# if PYBIND11_INTERNALS_VERSION > 4 +#if PYBIND11_INTERNALS_VERSION > 4 // Note that we have to use a std::string to allocate memory to ensure a unique address // We want unique addresses since we use pointer equality to compare function records std::string function_record_capsule_name = internals_function_record_capsule_name; -# endif +#endif internals() = default; internals(const internals &other) = delete; internals &operator=(const internals &other) = delete; ~internals() { -# if PYBIND11_INTERNALS_VERSION > 4 +#if PYBIND11_INTERNALS_VERSION > 4 PYBIND11_TLS_FREE(loader_life_support_tls_key); -# endif // PYBIND11_INTERNALS_VERSION > 4 +#endif // PYBIND11_INTERNALS_VERSION > 4 // This destructor is called *after* Py_Finalize() in finalize_interpreter(). // That *SHOULD BE* fine. The following details what happens when PyThread_tss_free is @@ -249,7 +224,6 @@ struct internals { // that the `tstate` be allocated with the CPython allocator. PYBIND11_TLS_FREE(tstate); } -#endif }; /// Additional type information which does not fit into the PyTypeObject. @@ -334,11 +308,7 @@ struct type_info { #endif #ifndef PYBIND11_INTERNALS_KIND -# if defined(WITH_THREAD) -# define PYBIND11_INTERNALS_KIND "" -# else -# define PYBIND11_INTERNALS_KIND "_without_thread" -# endif +# define PYBIND11_INTERNALS_KIND "" #endif /// See README_smart_holder.rst: @@ -531,10 +501,9 @@ PYBIND11_NOINLINE internals &get_internals() { return **internals_pp; } -#if defined(WITH_THREAD) -# if defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) +#if defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) gil_scoped_acquire gil; -# else +#else // Ensure that the GIL is held since we will need to make Python calls. // Cannot use py::gil_scoped_acquire here since that constructor calls get_internals. struct gil_scoped_acquire_local { @@ -544,7 +513,6 @@ PYBIND11_NOINLINE internals &get_internals() { ~gil_scoped_acquire_local() { PyGILState_Release(state); } const PyGILState_STATE state; } gil; -# endif #endif error_scope err_scope; @@ -569,7 +537,6 @@ PYBIND11_NOINLINE internals &get_internals() { } auto *&internals_ptr = *internals_pp; internals_ptr = new internals(); -#if defined(WITH_THREAD) PyThreadState *tstate = PyThreadState_Get(); // NOLINTNEXTLINE(bugprone-assignment-in-if-condition) @@ -578,15 +545,14 @@ PYBIND11_NOINLINE internals &get_internals() { } PYBIND11_TLS_REPLACE_VALUE(internals_ptr->tstate, tstate); -# if PYBIND11_INTERNALS_VERSION > 4 +#if PYBIND11_INTERNALS_VERSION > 4 // NOLINTNEXTLINE(bugprone-assignment-in-if-condition) if (!PYBIND11_TLS_KEY_CREATE(internals_ptr->loader_life_support_tls_key)) { pybind11_fail("get_internals: could not successfully initialize the " "loader_life_support TSS key!"); } -# endif - internals_ptr->istate = tstate->interp; #endif + internals_ptr->istate = tstate->interp; state_dict[PYBIND11_INTERNALS_ID] = capsule(internals_pp); internals_ptr->registered_exception_translators.push_front(&translate_exception); internals_ptr->static_property_type = make_static_property_type(); @@ -615,7 +581,7 @@ PYBIND11_NOINLINE internals &get_internals() { struct local_internals { type_map registered_types_cpp; std::forward_list registered_exception_translators; -#if defined(WITH_THREAD) && PYBIND11_INTERNALS_VERSION == 4 +#if PYBIND11_INTERNALS_VERSION == 4 // For ABI compatibility, we can't store the loader_life_support TLS key in // the `internals` struct directly. Instead, we store it in `shared_data` and @@ -648,7 +614,7 @@ struct local_internals { loader_life_support_tls_key = static_cast(ptr)->loader_life_support_tls_key; } -#endif // defined(WITH_THREAD) && PYBIND11_INTERNALS_VERSION == 4 +#endif // PYBIND11_INTERNALS_VERSION == 4 }; /// Works like `get_internals`, but for things which are locally registered. diff --git a/include/pybind11/detail/type_caster_base.h b/include/pybind11/detail/type_caster_base.h index 832d849bf1..f6234c3d23 100644 --- a/include/pybind11/detail/type_caster_base.h +++ b/include/pybind11/detail/type_caster_base.h @@ -36,14 +36,13 @@ class loader_life_support { loader_life_support *parent = nullptr; std::unordered_set keep_alive; -#if defined(WITH_THREAD) // Store stack pointer in thread-local storage. static PYBIND11_TLS_KEY_REF get_stack_tls_key() { -# if PYBIND11_INTERNALS_VERSION == 4 +#if PYBIND11_INTERNALS_VERSION == 4 return get_local_internals().loader_life_support_tls_key; -# else +#else return get_internals().loader_life_support_tls_key; -# endif +#endif } static loader_life_support *get_stack_top() { return static_cast(PYBIND11_TLS_GET_VALUE(get_stack_tls_key())); @@ -51,15 +50,6 @@ class loader_life_support { static void set_stack_top(loader_life_support *value) { PYBIND11_TLS_REPLACE_VALUE(get_stack_tls_key(), value); } -#else - // Use single global variable for stack. - static loader_life_support **get_stack_pp() { - static loader_life_support *global_stack = nullptr; - return global_stack; - } - static loader_life_support *get_stack_top() { return *get_stack_pp(); } - static void set_stack_top(loader_life_support *value) { *get_stack_pp() = value; } -#endif public: /// A new patient frame is created when a function is entered diff --git a/include/pybind11/embed.h b/include/pybind11/embed.h index caa14f4a05..9d29eb8249 100644 --- a/include/pybind11/embed.h +++ b/include/pybind11/embed.h @@ -103,9 +103,6 @@ inline void initialize_interpreter_pre_pyconfig(bool init_signal_handlers, bool add_program_dir_to_path) { detail::precheck_interpreter(); Py_InitializeEx(init_signal_handlers ? 1 : 0); -# if defined(WITH_THREAD) && PY_VERSION_HEX < 0x03070000 - PyEval_InitThreads(); -# endif // Before it was special-cased in python 3.8, passing an empty or null argv // caused a segfault, so we have to reimplement the special case ourselves. diff --git a/include/pybind11/gil.h b/include/pybind11/gil.h index da22f48d7e..6b0edaee4e 100644 --- a/include/pybind11/gil.h +++ b/include/pybind11/gil.h @@ -13,7 +13,7 @@ #include -#if defined(WITH_THREAD) && !defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) +#if !defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) # include "detail/internals.h" #endif @@ -26,9 +26,7 @@ PyThreadState *get_thread_state_unchecked(); PYBIND11_NAMESPACE_END(detail) -#if defined(WITH_THREAD) - -# if !defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) +#if !defined(PYBIND11_SIMPLE_GIL_MANAGEMENT) /* The functions below essentially reproduce the PyGILState_* API using a RAII * pattern, but there are a few important differences: @@ -69,11 +67,11 @@ class gil_scoped_acquire { if (!tstate) { tstate = PyThreadState_New(internals.istate); -# if defined(PYBIND11_DETAILED_ERROR_MESSAGES) +# if defined(PYBIND11_DETAILED_ERROR_MESSAGES) if (!tstate) { pybind11_fail("scoped_acquire: could not create thread state!"); } -# endif +# endif tstate->gilstate_counter = 0; PYBIND11_TLS_REPLACE_VALUE(internals.tstate, tstate); } else { @@ -94,20 +92,20 @@ class gil_scoped_acquire { PYBIND11_NOINLINE void dec_ref() { --tstate->gilstate_counter; -# if defined(PYBIND11_DETAILED_ERROR_MESSAGES) +# if defined(PYBIND11_DETAILED_ERROR_MESSAGES) if (detail::get_thread_state_unchecked() != tstate) { pybind11_fail("scoped_acquire::dec_ref(): thread state must be current!"); } if (tstate->gilstate_counter < 0) { pybind11_fail("scoped_acquire::dec_ref(): reference count underflow!"); } -# endif +# endif if (tstate->gilstate_counter == 0) { -# if defined(PYBIND11_DETAILED_ERROR_MESSAGES) +# if defined(PYBIND11_DETAILED_ERROR_MESSAGES) if (!release) { pybind11_fail("scoped_acquire::dec_ref(): internal error!"); } -# endif +# endif PyThreadState_Clear(tstate); if (active) { PyThreadState_DeleteCurrent(); @@ -188,7 +186,7 @@ class gil_scoped_release { bool active = true; }; -# else // PYBIND11_SIMPLE_GIL_MANAGEMENT +#else // PYBIND11_SIMPLE_GIL_MANAGEMENT class gil_scoped_acquire { PyGILState_STATE state; @@ -216,32 +214,6 @@ class gil_scoped_release { void disarm() {} }; -# endif // PYBIND11_SIMPLE_GIL_MANAGEMENT - -#else // WITH_THREAD - -class gil_scoped_acquire { -public: - gil_scoped_acquire() { - // Trick to suppress `unused variable` error messages (at call sites). - (void) (this != (this + 1)); - } - gil_scoped_acquire(const gil_scoped_acquire &) = delete; - gil_scoped_acquire &operator=(const gil_scoped_acquire &) = delete; - void disarm() {} -}; - -class gil_scoped_release { -public: - gil_scoped_release() { - // Trick to suppress `unused variable` error messages (at call sites). - (void) (this != (this + 1)); - } - gil_scoped_release(const gil_scoped_release &) = delete; - gil_scoped_release &operator=(const gil_scoped_release &) = delete; - void disarm() {} -}; - -#endif // WITH_THREAD +#endif // PYBIND11_SIMPLE_GIL_MANAGEMENT PYBIND11_NAMESPACE_END(PYBIND11_NAMESPACE) diff --git a/include/pybind11/stl/filesystem.h b/include/pybind11/stl/filesystem.h index e26f421776..85c131efe4 100644 --- a/include/pybind11/stl/filesystem.h +++ b/include/pybind11/stl/filesystem.h @@ -14,8 +14,7 @@ #ifdef __has_include # if defined(PYBIND11_CPP17) -# if __has_include() && \ - PY_VERSION_HEX >= 0x03060000 +# if __has_include() # include # define PYBIND11_HAS_FILESYSTEM 1 # elif __has_include() diff --git a/noxfile.py b/noxfile.py index 5fbf096858..be75def5d4 100644 --- a/noxfile.py +++ b/noxfile.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import argparse import nox diff --git a/pybind11/__init__.py b/pybind11/__init__.py index 7c10b30578..b14660caeb 100644 --- a/pybind11/__init__.py +++ b/pybind11/__init__.py @@ -1,7 +1,9 @@ +from __future__ import annotations + import sys -if sys.version_info < (3, 6): # noqa: UP036 - msg = "pybind11 does not support Python < 3.6. 2.9 was the last release supporting Python 2.7 and 3.5." +if sys.version_info < (3, 7): # noqa: UP036 + msg = "pybind11 does not support Python < 3.7. v2.12 was the last release supporting Python 3.6." raise ImportError(msg) diff --git a/pybind11/__main__.py b/pybind11/__main__.py index 180665c23c..b656ce6fee 100644 --- a/pybind11/__main__.py +++ b/pybind11/__main__.py @@ -1,4 +1,5 @@ # pylint: disable=missing-function-docstring +from __future__ import annotations import argparse import sys diff --git a/pybind11/_version.py b/pybind11/_version.py index 917edd74d1..f71abbcdb8 100644 --- a/pybind11/_version.py +++ b/pybind11/_version.py @@ -1,7 +1,7 @@ -from typing import Union +from __future__ import annotations -def _to_int(s: str) -> Union[int, str]: +def _to_int(s: str) -> int | str: try: return int(s) except ValueError: diff --git a/pybind11/commands.py b/pybind11/commands.py index b11690f46b..d535b6cca4 100644 --- a/pybind11/commands.py +++ b/pybind11/commands.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import os DIR = os.path.abspath(os.path.dirname(__file__)) diff --git a/pybind11/setup_helpers.py b/pybind11/setup_helpers.py index 16ab76b28a..ced506f8c2 100644 --- a/pybind11/setup_helpers.py +++ b/pybind11/setup_helpers.py @@ -36,6 +36,7 @@ # # If you copy this file in, you don't # need the .pyi file; it's just an interface file for static type checkers. +from __future__ import annotations import contextlib import os @@ -52,7 +53,6 @@ from typing import ( Any, Callable, - Dict, Iterable, Iterator, List, @@ -113,10 +113,10 @@ class Pybind11Extension(_Extension): # flags are prepended, so that they can be further overridden, e.g. by # ``extra_compile_args=["-g"]``. - def _add_cflags(self, flags: List[str]) -> None: + def _add_cflags(self, flags: list[str]) -> None: self.extra_compile_args[:0] = flags - def _add_ldflags(self, flags: List[str]) -> None: + def _add_ldflags(self, flags: list[str]) -> None: self.extra_link_args[:0] = flags def __init__(self, *args: Any, **kwargs: Any) -> None: @@ -250,7 +250,7 @@ def has_flag(compiler: Any, flag: str) -> bool: @lru_cache() -def auto_cpp_level(compiler: Any) -> Union[str, int]: +def auto_cpp_level(compiler: Any) -> str | int: """ Return the max supported C++ std level (17, 14, or 11). Returns latest on Windows. """ @@ -288,8 +288,8 @@ def build_extensions(self) -> None: def intree_extensions( - paths: Iterable[str], package_dir: Optional[Dict[str, str]] = None -) -> List[Pybind11Extension]: + paths: Iterable[str], package_dir: dict[str, str] | None = None +) -> list[Pybind11Extension]: """ Generate Pybind11Extensions from source files directly located in a Python source tree. @@ -409,7 +409,7 @@ class ParallelCompile: def __init__( self, - envvar: Optional[str] = None, + envvar: str | None = None, default: int = 0, max: int = 0, # pylint: disable=redefined-builtin needs_recompile: Callable[[str, str], bool] = no_recompile, @@ -418,7 +418,7 @@ def __init__( self.default = default self.max = max self.needs_recompile = needs_recompile - self._old: List[CCompilerMethod] = [] + self._old: list[CCompilerMethod] = [] def function(self) -> CCompilerMethod: """ @@ -427,14 +427,14 @@ def function(self) -> CCompilerMethod: def compile_function( compiler: distutils.ccompiler.CCompiler, - sources: List[str], - output_dir: Optional[str] = None, - macros: Optional[List[Union[Tuple[str], Tuple[str, Optional[str]]]]] = None, - include_dirs: Optional[List[str]] = None, + sources: list[str], + output_dir: str | None = None, + macros: list[tuple[str] | tuple[str, str | None]] | None = None, + include_dirs: list[str] | None = None, debug: bool = False, - extra_preargs: Optional[List[str]] = None, - extra_postargs: Optional[List[str]] = None, - depends: Optional[List[str]] = None, + extra_preargs: list[str] | None = None, + extra_postargs: list[str] | None = None, + depends: list[str] | None = None, ) -> Any: # These lines are directly from distutils.ccompiler.CCompiler macros, objects, extra_postargs, pp_opts, build = compiler._setup_compile( # type: ignore[attr-defined] diff --git a/pyproject.toml b/pyproject.toml index 1f011c2f48..71e7f56178 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -30,7 +30,7 @@ ignore_missing_imports = true [tool.pylint] -master.py-version = "3.6" +master.py-version = "3.7" reports.output-format = "colorized" messages_control.disable = [ "design", @@ -76,6 +76,8 @@ ignore = [ ] unfixable = ["T20"] isort.known-first-party = ["env", "pybind11_cross_module_tests", "pybind11_tests"] +isort.required-imports = ["from __future__ import annotations"] + [tool.ruff.lint.per-file-ignores] "tests/**" = ["EM", "N", "E721"] diff --git a/setup.cfg b/setup.cfg index 92e6c953a9..79d75d0cdb 100644 --- a/setup.cfg +++ b/setup.cfg @@ -14,7 +14,6 @@ classifiers = Topic :: Utilities Programming Language :: C++ Programming Language :: Python :: 3 :: Only - Programming Language :: Python :: 3.6 Programming Language :: Python :: 3.7 Programming Language :: Python :: 3.8 Programming Language :: Python :: 3.9 @@ -39,5 +38,5 @@ project_urls = Chat = https://gitter.im/pybind/Lobby [options] -python_requires = >=3.6 +python_requires = >=3.7 zip_safe = False diff --git a/setup.py b/setup.py index 9fea7d35c7..96563c1a59 100644 --- a/setup.py +++ b/setup.py @@ -1,6 +1,7 @@ #!/usr/bin/env python3 # Setup script for PyPI; use CMakeFile.txt to build extension modules +from __future__ import annotations import contextlib import os @@ -9,9 +10,9 @@ import string import subprocess import sys +from collections.abc import Generator from pathlib import Path from tempfile import TemporaryDirectory -from typing import Dict, Iterator, List, Union import setuptools.command.sdist @@ -23,7 +24,7 @@ COMMON_FILE = Path("include/pybind11/detail/common.h") -def build_expected_version_hex(matches: Dict[str, str]) -> str: +def build_expected_version_hex(matches: dict[str, str]) -> str: patch_level_serial = matches["PATCH"] serial = None major = int(matches["MAJOR"]) @@ -64,7 +65,7 @@ def build_expected_version_hex(matches: Dict[str, str]) -> str: # Read the listed version -loc: Dict[str, str] = {} +loc: dict[str, str] = {} code = compile(VERSION_FILE.read_text(encoding="utf-8"), "pybind11/_version.py", "exec") exec(code, loc) version = loc["__version__"] @@ -84,9 +85,7 @@ def build_expected_version_hex(matches: Dict[str, str]) -> str: # TODO: use literals & overload (typing extensions or Python 3.8) -def get_and_replace( - filename: Path, binary: bool = False, **opts: str -) -> Union[bytes, str]: +def get_and_replace(filename: Path, binary: bool = False, **opts: str) -> bytes | str: if binary: contents = filename.read_bytes() return string.Template(contents.decode()).substitute(opts).encode() @@ -97,7 +96,7 @@ def get_and_replace( # Use our input files instead when making the SDist (and anything that depends # on it, like a wheel) class SDist(setuptools.command.sdist.sdist): - def make_release_tree(self, base_dir: str, files: List[str]) -> None: + def make_release_tree(self, base_dir: str, files: list[str]) -> None: super().make_release_tree(base_dir, files) for to, src in to_src: @@ -112,7 +111,7 @@ def make_release_tree(self, base_dir: str, files: List[str]) -> None: # Remove the CMake install directory when done @contextlib.contextmanager -def remove_output(*sources: str) -> Iterator[None]: +def remove_output(*sources: str) -> Generator[None, None, None]: try: yield finally: diff --git a/tests/conftest.py b/tests/conftest.py index 8ebc702224..7de6c2acee 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -4,6 +4,8 @@ Adds docstring and exceptions message sanitizers. """ +from __future__ import annotations + import contextlib import difflib import gc diff --git a/tests/env.py b/tests/env.py index 4c60f4bbeb..9f5347f2e5 100644 --- a/tests/env.py +++ b/tests/env.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import platform import sys import sysconfig diff --git a/tests/extra_python_package/test_files.py b/tests/extra_python_package/test_files.py index 95b3e967db..58f8bd88e4 100644 --- a/tests/extra_python_package/test_files.py +++ b/tests/extra_python_package/test_files.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import contextlib import os import string diff --git a/tests/extra_setuptools/test_setuphelper.py b/tests/extra_setuptools/test_setuphelper.py index d5d3093bf0..2c069adffb 100644 --- a/tests/extra_setuptools/test_setuphelper.py +++ b/tests/extra_setuptools/test_setuphelper.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import os import subprocess import sys diff --git a/tests/requirements.txt b/tests/requirements.txt index e056c6fa8a..337897bd24 100644 --- a/tests/requirements.txt +++ b/tests/requirements.txt @@ -1,15 +1,13 @@ --only-binary=:all: -build~=0.9; python_version=="3.6" build~=1.0; python_version>="3.7" numpy~=1.20.0; python_version=="3.7" and platform_python_implementation=="PyPy" numpy~=1.23.0; python_version=="3.8" and platform_python_implementation=="PyPy" numpy~=1.25.0; python_version=="3.9" and platform_python_implementation=='PyPy' -numpy~=1.19.3; platform_python_implementation!="PyPy" and python_version=="3.6" numpy~=1.21.5; platform_python_implementation!="PyPy" and python_version>="3.7" and python_version<"3.10" numpy~=1.22.2; platform_python_implementation!="PyPy" and python_version=="3.10" numpy~=1.26.0; platform_python_implementation!="PyPy" and python_version>="3.11" and python_version<"3.13" pytest~=7.0 pytest-timeout scipy~=1.5.4; platform_python_implementation!="PyPy" and python_version<"3.10" -scipy~=1.8.0; platform_python_implementation!="PyPy" and python_version=="3.10" -scipy~=1.11.1; platform_python_implementation!="PyPy" and python_version>="3.11" and python_version<"3.13" +scipy~=1.8.0; platform_python_implementation!="PyPy" and python_version=="3.10" and sys_platform!='win32' +scipy~=1.11.1; platform_python_implementation!="PyPy" and python_version>="3.11" and python_version<"3.13" and sys_platform!='win32' diff --git a/tests/test_async.py b/tests/test_async.py index 83a4c5036a..4d33ba65f6 100644 --- a/tests/test_async.py +++ b/tests/test_async.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest asyncio = pytest.importorskip("asyncio") diff --git a/tests/test_buffers.py b/tests/test_buffers.py index 5d33625ba4..84a301e250 100644 --- a/tests/test_buffers.py +++ b/tests/test_buffers.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import ctypes import io import struct diff --git a/tests/test_builtin_casters.py b/tests/test_builtin_casters.py index dbac1cbc27..9aa5926e9c 100644 --- a/tests/test_builtin_casters.py +++ b/tests/test_builtin_casters.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys import pytest diff --git a/tests/test_call_policies.cpp b/tests/test_call_policies.cpp index 279012d45c..92924cb452 100644 --- a/tests/test_call_policies.cpp +++ b/tests/test_call_policies.cpp @@ -95,7 +95,7 @@ TEST_SUBMODULE(call_policies, m) { }, py::call_guard()); -#if defined(WITH_THREAD) && !defined(PYPY_VERSION) +#if !defined(PYPY_VERSION) // `py::call_guard()` should work in PyPy as well, // but it's unclear how to test it without `PyGILState_GetThisThreadState`. auto report_gil_status = []() { diff --git a/tests/test_call_policies.py b/tests/test_call_policies.py index 6160564123..91670deb37 100644 --- a/tests/test_call_policies.py +++ b/tests/test_call_policies.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import env # noqa: F401 diff --git a/tests/test_callbacks.py b/tests/test_callbacks.py index 86c7674555..ce2a6d2549 100644 --- a/tests/test_callbacks.py +++ b/tests/test_callbacks.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import time from threading import Thread diff --git a/tests/test_chrono.py b/tests/test_chrono.py index a29316c38d..ed889fbd6b 100644 --- a/tests/test_chrono.py +++ b/tests/test_chrono.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import datetime import pytest diff --git a/tests/test_class.py b/tests/test_class.py index edaa5b3ca4..9b2b1d8346 100644 --- a/tests/test_class.py +++ b/tests/test_class.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from unittest import mock import pytest diff --git a/tests/test_class_sh_basic.py b/tests/test_class_sh_basic.py index c7ff82c818..b82e53fc4d 100644 --- a/tests/test_class_sh_basic.py +++ b/tests/test_class_sh_basic.py @@ -1,4 +1,6 @@ # Importing re before pytest after observing a PyPy CI flake when importing pytest first. +from __future__ import annotations + import re import pytest diff --git a/tests/test_class_sh_disowning.py b/tests/test_class_sh_disowning.py index f4d2471815..63cdd4edb6 100644 --- a/tests/test_class_sh_disowning.py +++ b/tests/test_class_sh_disowning.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_disowning as m diff --git a/tests/test_class_sh_disowning_mi.py b/tests/test_class_sh_disowning_mi.py index 6fbc1f8e39..4a4beecce1 100644 --- a/tests/test_class_sh_disowning_mi.py +++ b/tests/test_class_sh_disowning_mi.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import env # noqa: F401 diff --git a/tests/test_class_sh_factory_constructors.py b/tests/test_class_sh_factory_constructors.py index 9ebff96ed0..5d45db6fd5 100644 --- a/tests/test_class_sh_factory_constructors.py +++ b/tests/test_class_sh_factory_constructors.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_factory_constructors as m diff --git a/tests/test_class_sh_inheritance.py b/tests/test_class_sh_inheritance.py index eaf53a5c6f..cd9d6f47e2 100644 --- a/tests/test_class_sh_inheritance.py +++ b/tests/test_class_sh_inheritance.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import class_sh_inheritance as m diff --git a/tests/test_class_sh_mi_thunks.py b/tests/test_class_sh_mi_thunks.py index de2a9196b2..c1c8a30431 100644 --- a/tests/test_class_sh_mi_thunks.py +++ b/tests/test_class_sh_mi_thunks.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_mi_thunks as m diff --git a/tests/test_class_sh_module_local.py b/tests/test_class_sh_module_local.py index a88e3fc1c9..e504152a16 100644 --- a/tests/test_class_sh_module_local.py +++ b/tests/test_class_sh_module_local.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import class_sh_module_local_0 as m0 import class_sh_module_local_1 as m1 import class_sh_module_local_2 as m2 diff --git a/tests/test_class_sh_property.py b/tests/test_class_sh_property.py index 9dc2a19771..9aeef44e03 100644 --- a/tests/test_class_sh_property.py +++ b/tests/test_class_sh_property.py @@ -1,5 +1,6 @@ # The compact 4-character naming scheme (e.g. mptr, cptr, shcp) is explained at the top of # test_class_sh_property.cpp. +from __future__ import annotations import pytest diff --git a/tests/test_class_sh_property_non_owning.py b/tests/test_class_sh_property_non_owning.py index 8b6f5f4bd3..33a9d4503b 100644 --- a/tests/test_class_sh_property_non_owning.py +++ b/tests/test_class_sh_property_non_owning.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_property_non_owning as m diff --git a/tests/test_class_sh_shared_ptr_copy_move.py b/tests/test_class_sh_shared_ptr_copy_move.py index bc7198f2e4..067bb47d2a 100644 --- a/tests/test_class_sh_shared_ptr_copy_move.py +++ b/tests/test_class_sh_shared_ptr_copy_move.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import class_sh_shared_ptr_copy_move as m diff --git a/tests/test_class_sh_trampoline_basic.py b/tests/test_class_sh_trampoline_basic.py index dfd7ac10e8..eab82121fb 100644 --- a/tests/test_class_sh_trampoline_basic.py +++ b/tests/test_class_sh_trampoline_basic.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_trampoline_basic as m diff --git a/tests/test_class_sh_trampoline_self_life_support.py b/tests/test_class_sh_trampoline_self_life_support.py index 3bd12bc4f9..d4af2ab99a 100644 --- a/tests/test_class_sh_trampoline_self_life_support.py +++ b/tests/test_class_sh_trampoline_self_life_support.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import pybind11_tests.class_sh_trampoline_self_life_support as m diff --git a/tests/test_class_sh_trampoline_shared_from_this.py b/tests/test_class_sh_trampoline_shared_from_this.py index eeb7bb8ac5..85fe7858f5 100644 --- a/tests/test_class_sh_trampoline_shared_from_this.py +++ b/tests/test_class_sh_trampoline_shared_from_this.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys import weakref diff --git a/tests/test_class_sh_trampoline_shared_ptr_cpp_arg.py b/tests/test_class_sh_trampoline_shared_ptr_cpp_arg.py index b9cde4f2cb..431edb7191 100644 --- a/tests/test_class_sh_trampoline_shared_ptr_cpp_arg.py +++ b/tests/test_class_sh_trampoline_shared_ptr_cpp_arg.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import pybind11_tests.class_sh_trampoline_shared_ptr_cpp_arg as m diff --git a/tests/test_class_sh_trampoline_unique_ptr.py b/tests/test_class_sh_trampoline_unique_ptr.py index c598079e42..7799df6d61 100644 --- a/tests/test_class_sh_trampoline_unique_ptr.py +++ b/tests/test_class_sh_trampoline_unique_ptr.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pybind11_tests.class_sh_trampoline_unique_ptr as m diff --git a/tests/test_class_sh_unique_ptr_custom_deleter.py b/tests/test_class_sh_unique_ptr_custom_deleter.py index d9cf1d4508..34aa520682 100644 --- a/tests/test_class_sh_unique_ptr_custom_deleter.py +++ b/tests/test_class_sh_unique_ptr_custom_deleter.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import class_sh_unique_ptr_custom_deleter as m diff --git a/tests/test_class_sh_unique_ptr_member.py b/tests/test_class_sh_unique_ptr_member.py index 1a50a57b7b..a5d2ccd234 100644 --- a/tests/test_class_sh_unique_ptr_member.py +++ b/tests/test_class_sh_unique_ptr_member.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_unique_ptr_member as m diff --git a/tests/test_class_sh_virtual_py_cpp_mix.py b/tests/test_class_sh_virtual_py_cpp_mix.py index 552162d8ed..33133eb889 100644 --- a/tests/test_class_sh_virtual_py_cpp_mix.py +++ b/tests/test_class_sh_virtual_py_cpp_mix.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import class_sh_virtual_py_cpp_mix as m diff --git a/tests/test_classh_mock.py b/tests/test_classh_mock.py index 7d0ffbe8b2..b05cd0c57c 100644 --- a/tests/test_classh_mock.py +++ b/tests/test_classh_mock.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import classh_mock as m diff --git a/tests/test_cmake_build/test.py b/tests/test_cmake_build/test.py index 807fd43b4a..bb4c20e0cb 100644 --- a/tests/test_cmake_build/test.py +++ b/tests/test_cmake_build/test.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys import test_cmake_build diff --git a/tests/test_const_name.py b/tests/test_const_name.py index a145f0bbb5..f520249456 100644 --- a/tests/test_const_name.py +++ b/tests/test_const_name.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import const_name as m diff --git a/tests/test_constants_and_functions.py b/tests/test_constants_and_functions.py index a1142461c0..63004e1b6c 100644 --- a/tests/test_constants_and_functions.py +++ b/tests/test_constants_and_functions.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest m = pytest.importorskip("pybind11_tests.constants_and_functions") diff --git a/tests/test_copy_move.py b/tests/test_copy_move.py index 9fef089339..405e00132c 100644 --- a/tests/test_copy_move.py +++ b/tests/test_copy_move.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import copy_move_policies as m diff --git a/tests/test_custom_type_casters.py b/tests/test_custom_type_casters.py index 3a00ea964b..689b1e9cb6 100644 --- a/tests/test_custom_type_casters.py +++ b/tests/test_custom_type_casters.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import custom_type_casters as m diff --git a/tests/test_custom_type_setup.py b/tests/test_custom_type_setup.py index e63ff5758e..56922c6dd1 100644 --- a/tests/test_custom_type_setup.py +++ b/tests/test_custom_type_setup.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import gc import weakref diff --git a/tests/test_descr_src_loc.py b/tests/test_descr_src_loc.py index b13c4ad53f..cf16f7141c 100644 --- a/tests/test_descr_src_loc.py +++ b/tests/test_descr_src_loc.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import descr_src_loc as m diff --git a/tests/test_docstring_options.py b/tests/test_docstring_options.py index e6f5a9d987..09fc8ac254 100644 --- a/tests/test_docstring_options.py +++ b/tests/test_docstring_options.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import docstring_options as m diff --git a/tests/test_eigen_matrix.py b/tests/test_eigen_matrix.py index 9a2cafc0a6..e1d7433f15 100644 --- a/tests/test_eigen_matrix.py +++ b/tests/test_eigen_matrix.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import ConstructorStats diff --git a/tests/test_eigen_tensor.py b/tests/test_eigen_tensor.py index 3e7ee6b7f2..a2b99d9d7d 100644 --- a/tests/test_eigen_tensor.py +++ b/tests/test_eigen_tensor.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys import pytest diff --git a/tests/test_embed/test_interpreter.py b/tests/test_embed/test_interpreter.py index f279449722..424d36dea2 100644 --- a/tests/test_embed/test_interpreter.py +++ b/tests/test_embed/test_interpreter.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys from widget_module import Widget diff --git a/tests/test_embed/test_trampoline.py b/tests/test_embed/test_trampoline.py index 8e14e8ef0b..b8ff3eba28 100644 --- a/tests/test_embed/test_trampoline.py +++ b/tests/test_embed/test_trampoline.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import trampoline_module diff --git a/tests/test_enum.py b/tests/test_enum.py index 6b75b7ae54..9914b90013 100644 --- a/tests/test_enum.py +++ b/tests/test_enum.py @@ -1,4 +1,5 @@ # ruff: noqa: SIM201 SIM300 SIM202 +from __future__ import annotations import pytest diff --git a/tests/test_eval.py b/tests/test_eval.py index 51b6b796b4..45b68ece72 100644 --- a/tests/test_eval.py +++ b/tests/test_eval.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import os import pytest diff --git a/tests/test_eval_call.py b/tests/test_eval_call.py index fd1da2a5cc..a677249d4b 100644 --- a/tests/test_eval_call.py +++ b/tests/test_eval_call.py @@ -1,4 +1,5 @@ # This file is called from 'test_eval.py' +from __future__ import annotations if "call_test2" in locals(): call_test2(y) # noqa: F821 undefined name diff --git a/tests/test_exc_namespace_visibility.py b/tests/test_exc_namespace_visibility.py index 0f1cab9d5b..e94271a58c 100644 --- a/tests/test_exc_namespace_visibility.py +++ b/tests/test_exc_namespace_visibility.py @@ -10,6 +10,7 @@ # test_cross_module_exception_translator (test_exceptions.py) failure. This # test has to be imported (by pytest) before test_exceptions.py; pytest sorts # lexically. See https://github.com/pybind/pybind11/pull/4054 for more information. +from __future__ import annotations import itertools diff --git a/tests/test_exceptions.py b/tests/test_exceptions.py index 01fcb918ec..b33997eeea 100644 --- a/tests/test_exceptions.py +++ b/tests/test_exceptions.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys import pytest diff --git a/tests/test_factory_constructors.py b/tests/test_factory_constructors.py index 4e2d6e4222..8a8ae66d91 100644 --- a/tests/test_factory_constructors.py +++ b/tests/test_factory_constructors.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import re import pytest diff --git a/tests/test_gil_scoped.py b/tests/test_gil_scoped.py index fc8af9b77c..a183876845 100644 --- a/tests/test_gil_scoped.py +++ b/tests/test_gil_scoped.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import multiprocessing import sys import threading diff --git a/tests/test_iostream.py b/tests/test_iostream.py index 871269a92e..f7eeff502b 100644 --- a/tests/test_iostream.py +++ b/tests/test_iostream.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from contextlib import redirect_stderr, redirect_stdout from io import StringIO diff --git a/tests/test_kwargs_and_defaults.py b/tests/test_kwargs_and_defaults.py index d7bc7379b1..b9b1a7ea87 100644 --- a/tests/test_kwargs_and_defaults.py +++ b/tests/test_kwargs_and_defaults.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import kwargs_and_defaults as m diff --git a/tests/test_local_bindings.py b/tests/test_local_bindings.py index d641877396..1e83164c77 100644 --- a/tests/test_local_bindings.py +++ b/tests/test_local_bindings.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import env # noqa: F401 diff --git a/tests/test_methods_and_attributes.py b/tests/test_methods_and_attributes.py index 8af4afb5c0..ec794457c8 100644 --- a/tests/test_methods_and_attributes.py +++ b/tests/test_methods_and_attributes.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import sys import pytest diff --git a/tests/test_modules.py b/tests/test_modules.py index 2f6d825b79..95835e14ea 100644 --- a/tests/test_modules.py +++ b/tests/test_modules.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import builtins import pytest diff --git a/tests/test_multiple_inheritance.py b/tests/test_multiple_inheritance.py index 3a1d88d711..d445824b54 100644 --- a/tests/test_multiple_inheritance.py +++ b/tests/test_multiple_inheritance.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import env # noqa: F401 diff --git a/tests/test_numpy_array.py b/tests/test_numpy_array.py index 25ad09ec3c..4726a8e73c 100644 --- a/tests/test_numpy_array.py +++ b/tests/test_numpy_array.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import env # noqa: F401 @@ -198,11 +200,7 @@ def assert_references(a, b, base=None): assert a.flags.f_contiguous == b.flags.f_contiguous assert a.flags.writeable == b.flags.writeable assert a.flags.aligned == b.flags.aligned - # 1.13 supported Python 3.6 - if tuple(int(x) for x in np.__version__.split(".")[:2]) >= (1, 14): - assert a.flags.writebackifcopy == b.flags.writebackifcopy - else: - assert a.flags.updateifcopy == b.flags.updateifcopy + assert a.flags.writebackifcopy == b.flags.writebackifcopy assert np.all(a == b) assert not b.flags.owndata assert b.base is base diff --git a/tests/test_numpy_dtypes.py b/tests/test_numpy_dtypes.py index 790f63641c..8ae239ed86 100644 --- a/tests/test_numpy_dtypes.py +++ b/tests/test_numpy_dtypes.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import re import pytest diff --git a/tests/test_numpy_vectorize.py b/tests/test_numpy_vectorize.py index f1e8b62540..ce38d72d96 100644 --- a/tests/test_numpy_vectorize.py +++ b/tests/test_numpy_vectorize.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import numpy_vectorize as m diff --git a/tests/test_opaque_types.py b/tests/test_opaque_types.py index 5d4f2a1bf4..3420864367 100644 --- a/tests/test_opaque_types.py +++ b/tests/test_opaque_types.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import ConstructorStats, UserType diff --git a/tests/test_operator_overloading.py b/tests/test_operator_overloading.py index 9fde305a03..b6760902dc 100644 --- a/tests/test_operator_overloading.py +++ b/tests/test_operator_overloading.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import ConstructorStats diff --git a/tests/test_pickling.py b/tests/test_pickling.py index 12361a661e..ad67a1df98 100644 --- a/tests/test_pickling.py +++ b/tests/test_pickling.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pickle import re diff --git a/tests/test_python_multiple_inheritance.py b/tests/test_python_multiple_inheritance.py index 3bddd67dfb..12216283ab 100644 --- a/tests/test_python_multiple_inheritance.py +++ b/tests/test_python_multiple_inheritance.py @@ -1,5 +1,6 @@ # Adapted from: # https://github.com/google/clif/blob/5718e4d0807fd3b6a8187dde140069120b81ecef/clif/testing/python/python_multiple_inheritance_test.py +from __future__ import annotations from pybind11_tests import python_multiple_inheritance as m diff --git a/tests/test_pytypes.py b/tests/test_pytypes.py index 72dac13b81..8e35c70733 100644 --- a/tests/test_pytypes.py +++ b/tests/test_pytypes.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import contextlib import sys import types diff --git a/tests/test_sequences_and_iterators.py b/tests/test_sequences_and_iterators.py index c13f03dd8f..f609f553de 100644 --- a/tests/test_sequences_and_iterators.py +++ b/tests/test_sequences_and_iterators.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pytest import approx # noqa: PT013 diff --git a/tests/test_smart_ptr.py b/tests/test_smart_ptr.py index bbcccdbf5f..893d609f51 100644 --- a/tests/test_smart_ptr.py +++ b/tests/test_smart_ptr.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest m = pytest.importorskip("pybind11_tests.smart_ptr") diff --git a/tests/test_stl.py b/tests/test_stl.py index b08bd4680f..65fda54cc3 100644 --- a/tests/test_stl.py +++ b/tests/test_stl.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import ConstructorStats, UserType diff --git a/tests/test_stl_binders.py b/tests/test_stl_binders.py index d1bf64aa02..09e784e2eb 100644 --- a/tests/test_stl_binders.py +++ b/tests/test_stl_binders.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import stl_binders as m diff --git a/tests/test_tagbased_polymorphic.py b/tests/test_tagbased_polymorphic.py index 84f0ea7178..dabf307cf1 100644 --- a/tests/test_tagbased_polymorphic.py +++ b/tests/test_tagbased_polymorphic.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import tagbased_polymorphic as m diff --git a/tests/test_thread.py b/tests/test_thread.py index e89991f9d6..4541a305ec 100644 --- a/tests/test_thread.py +++ b/tests/test_thread.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import threading from pybind11_tests import thread as m diff --git a/tests/test_type_caster_odr_guard_1.py b/tests/test_type_caster_odr_guard_1.py index 8b62490433..88a89bd0b6 100644 --- a/tests/test_type_caster_odr_guard_1.py +++ b/tests/test_type_caster_odr_guard_1.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import pybind11_tests diff --git a/tests/test_type_caster_odr_guard_2.py b/tests/test_type_caster_odr_guard_2.py index b4f5ef6c41..29aeb832ec 100644 --- a/tests/test_type_caster_odr_guard_2.py +++ b/tests/test_type_caster_odr_guard_2.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import pybind11_tests.type_caster_odr_guard_2 as m diff --git a/tests/test_type_caster_pyobject_ptr.py b/tests/test_type_caster_pyobject_ptr.py index f6358d0118..ebc24e3182 100644 --- a/tests/test_type_caster_pyobject_ptr.py +++ b/tests/test_type_caster_pyobject_ptr.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import type_caster_pyobject_ptr as m diff --git a/tests/test_union.py b/tests/test_union.py index e1866e701d..a9de6baf18 100644 --- a/tests/test_union.py +++ b/tests/test_union.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import union_ as m diff --git a/tests/test_unnamed_namespace_a.py b/tests/test_unnamed_namespace_a.py index 9d9856c5a4..0fa1fa323f 100644 --- a/tests/test_unnamed_namespace_a.py +++ b/tests/test_unnamed_namespace_a.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import unnamed_namespace_a as m diff --git a/tests/test_unnamed_namespace_b.py b/tests/test_unnamed_namespace_b.py index 4bcaa7a6c5..9e57328227 100644 --- a/tests/test_unnamed_namespace_b.py +++ b/tests/test_unnamed_namespace_b.py @@ -1,3 +1,5 @@ +from __future__ import annotations + from pybind11_tests import unnamed_namespace_b as m diff --git a/tests/test_vector_unique_ptr_member.py b/tests/test_vector_unique_ptr_member.py index 2da3d97c37..969c1a5d6e 100644 --- a/tests/test_vector_unique_ptr_member.py +++ b/tests/test_vector_unique_ptr_member.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest from pybind11_tests import vector_unique_ptr_member as m diff --git a/tests/test_virtual_functions.py b/tests/test_virtual_functions.py index c17af7df58..08acaa1908 100644 --- a/tests/test_virtual_functions.py +++ b/tests/test_virtual_functions.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import pytest import env # noqa: F401 diff --git a/tools/FindPythonLibsNew.cmake b/tools/FindPythonLibsNew.cmake index 0640a1915f..283b4e2980 100644 --- a/tools/FindPythonLibsNew.cmake +++ b/tools/FindPythonLibsNew.cmake @@ -92,7 +92,7 @@ endif() # Use the Python interpreter to find the libs. if(NOT PythonLibsNew_FIND_VERSION) - set(PythonLibsNew_FIND_VERSION "3.6") + set(PythonLibsNew_FIND_VERSION "3.7") endif() if(NOT CMAKE_VERSION VERSION_LESS "3.27") diff --git a/tools/codespell_ignore_lines_from_errors.py b/tools/codespell_ignore_lines_from_errors.py index 4ec9add12d..08ced3d4ef 100644 --- a/tools/codespell_ignore_lines_from_errors.py +++ b/tools/codespell_ignore_lines_from_errors.py @@ -9,11 +9,12 @@ git diff to review changes, then commit, push. """ +from __future__ import annotations + import sys -from typing import List -def run(args: List[str]) -> None: +def run(args: list[str]) -> None: assert len(args) == 1, "codespell_errors.txt" cache = {} done = set() diff --git a/tools/libsize.py b/tools/libsize.py index 1ac9afbe81..ef5fb13c25 100644 --- a/tools/libsize.py +++ b/tools/libsize.py @@ -1,3 +1,5 @@ +from __future__ import annotations + import os import sys diff --git a/tools/pybind11NewTools.cmake b/tools/pybind11NewTools.cmake index f2ec347561..a8b0800bb8 100644 --- a/tools/pybind11NewTools.cmake +++ b/tools/pybind11NewTools.cmake @@ -56,7 +56,7 @@ if(NOT Python_FOUND AND NOT Python3_FOUND) endif() find_package( - Python 3.6 REQUIRED COMPONENTS ${_pybind11_interp_component} ${_pybind11_dev_component} + Python 3.7 REQUIRED COMPONENTS ${_pybind11_interp_component} ${_pybind11_dev_component} ${_pybind11_quiet} ${_pybind11_global_keyword}) # If we are in submodule mode, export the Python targets to global targets. diff --git a/tools/pybind11Tools.cmake b/tools/pybind11Tools.cmake index 045e5f1e7a..bed5e08039 100644 --- a/tools/pybind11Tools.cmake +++ b/tools/pybind11Tools.cmake @@ -43,7 +43,7 @@ endif() # A user can set versions manually too set(Python_ADDITIONAL_VERSIONS - "3.12;3.11;3.10;3.9;3.8;3.7;3.6" + "3.12;3.11;3.10;3.9;3.8;3.7" CACHE INTERNAL "") list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}")