Skip to content

Commit e9af5d3

Browse files
chore(package): drop Python 3.8 support
1 parent 9efe993 commit e9af5d3

File tree

6 files changed

+354
-1646
lines changed

6 files changed

+354
-1646
lines changed

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
<!-- prettier-ignore -->
44
[![PyPI version](https://img.shields.io/pypi/v/anthropic.svg?label=pypi%20(stable))](https://pypi.org/project/anthropic/)
55

6-
The Anthropic Python library provides convenient access to the Anthropic REST API from any Python 3.8+
6+
The Anthropic Python library provides convenient access to the Anthropic REST API from any Python 3.9+
77
application. It includes type definitions for all request params and response fields,
88
and offers both synchronous and asynchronous clients powered by [httpx](https://github.com/encode/httpx).
99

@@ -867,7 +867,7 @@ print(anthropic.__version__)
867867

868868
## Requirements
869869

870-
Python 3.8 or higher.
870+
Python 3.9 or higher.
871871

872872
## Contributing
873873

pyproject.toml

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -17,11 +17,10 @@ dependencies = [
1717
"jiter>=0.4.0, <1",
1818
"docstring-parser>=0.15,<1",
1919
]
20-
requires-python = ">= 3.8"
20+
requires-python = ">= 3.9"
2121
classifiers = [
2222
"Typing :: Typed",
2323
"Intended Audience :: Developers",
24-
"Programming Language :: Python :: 3.8",
2524
"Programming Language :: Python :: 3.9",
2625
"Programming Language :: Python :: 3.10",
2726
"Programming Language :: Python :: 3.11",
@@ -136,7 +135,7 @@ format-command="ruff format --stdin-filename {filename}"
136135
# there are a couple of flags that are still disabled by
137136
# default in strict mode as they are experimental and niche.
138137
typeCheckingMode = "strict"
139-
pythonVersion = "3.8"
138+
pythonVersion = "3.9"
140139

141140
exclude = [
142141
".git",

requirements-dev.lock

Lines changed: 15 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -3,22 +3,14 @@
33
-e .
44
annotated-types==0.7.0
55
# via pydantic
6-
anyio==4.5.2 ; python_full_version < '3.9'
7-
# via
8-
# anthropic
9-
# httpx
10-
anyio==4.8.0 ; python_full_version >= '3.9'
6+
anyio==4.8.0
117
# via
128
# anthropic
139
# httpx
1410
asttokens==3.0.0
1511
# via inline-snapshot
16-
astunparse==1.6.3 ; python_full_version < '3.9'
17-
# via griffe
18-
boto3-stubs==1.40.54
19-
botocore-stubs==1.38.30 ; python_full_version < '3.9'
20-
# via boto3-stubs
21-
botocore-stubs==1.40.54 ; python_full_version >= '3.9'
12+
boto3-stubs==1.40.69
13+
botocore-stubs==1.40.69
2214
# via boto3-stubs
2315
certifi==2024.12.14
2416
# via
@@ -41,8 +33,7 @@ execnet==2.1.1
4133
# via pytest-xdist
4234
executing==2.2.1
4335
# via inline-snapshot
44-
griffe==1.4.0 ; python_full_version < '3.9'
45-
griffe==1.13.0 ; python_full_version >= '3.9'
36+
griffe==1.13.0
4637
h11==0.16.0
4738
# via httpcore
4839
httpcore==1.0.9
@@ -55,14 +46,11 @@ idna==3.10
5546
# via
5647
# anyio
5748
# httpx
58-
importlib-metadata==8.5.0 ; python_full_version < '3.9'
59-
importlib-metadata==8.6.1 ; python_full_version >= '3.9'
49+
importlib-metadata==8.6.1
6050
iniconfig==2.0.0
6151
# via pytest
62-
inline-snapshot==0.30.0
63-
jiter==0.9.1 ; python_full_version < '3.9'
64-
# via anthropic
65-
jiter==0.11.0 ; python_full_version >= '3.9'
52+
inline-snapshot==0.31.1
53+
jiter==0.12.0
6654
# via anthropic
6755
markdown-it-py==3.0.0
6856
# via rich
@@ -77,62 +65,46 @@ packaging==24.2
7765
# via pytest
7866
pluggy==1.5.0
7967
# via pytest
80-
pydantic==2.10.6 ; python_full_version < '3.9'
81-
# via anthropic
82-
pydantic==2.11.9 ; python_full_version >= '3.9'
68+
pydantic==2.10.3
8369
# via anthropic
84-
pydantic-core==2.27.2 ; python_full_version < '3.9'
85-
# via pydantic
86-
pydantic-core==2.33.2 ; python_full_version >= '3.9'
70+
pydantic-core==2.27.1
8771
# via pydantic
8872
pygments==2.19.1
8973
# via
9074
# pytest
9175
# rich
9276
pyright==1.1.399
93-
pytest==8.3.5 ; python_full_version < '3.9'
94-
# via
95-
# inline-snapshot
96-
# pytest-asyncio
97-
# pytest-xdist
98-
pytest==8.4.1 ; python_full_version >= '3.9'
77+
pytest==8.4.1
9978
# via
10079
# inline-snapshot
10180
# pytest-asyncio
10281
# pytest-xdist
10382
pytest-asyncio==0.24.0
104-
pytest-xdist==3.6.1 ; python_full_version < '3.9'
105-
pytest-xdist==3.7.0 ; python_full_version >= '3.9'
83+
pytest-xdist==3.7.0
10684
python-dateutil==2.9.0.post0
10785
# via time-machine
108-
pytz==2024.2 ; python_full_version < '3.9'
109-
# via dirty-equals
11086
respx==0.22.0
11187
rich==13.9.4
11288
# via inline-snapshot
11389
ruff==0.9.4
11490
six==1.17.0
115-
# via
116-
# astunparse
117-
# python-dateutil
91+
# via python-dateutil
11892
sniffio==1.3.1
11993
# via
12094
# anthropic
12195
# anyio
122-
time-machine==2.15.0 ; python_full_version < '3.9'
123-
time-machine==2.16.0 ; python_full_version >= '3.9'
96+
time-machine==2.16.0
12497
tomli==2.2.1 ; python_full_version < '3.11'
12598
# via
12699
# inline-snapshot
127100
# mypy
128101
# pytest
129-
types-awscrt==0.28.1
102+
types-awscrt==0.28.2
130103
# via botocore-stubs
131104
types-s3transfer==0.14.0
132105
# via boto3-stubs
133106
typing-extensions==4.12.2
134107
# via
135-
# annotated-types
136108
# anthropic
137109
# anyio
138110
# boto3-stubs
@@ -141,12 +113,5 @@ typing-extensions==4.12.2
141113
# pydantic-core
142114
# pyright
143115
# rich
144-
# typing-inspection
145-
typing-inspection==0.4.1 ; python_full_version >= '3.9'
146-
# via pydantic
147-
wheel==0.45.1 ; python_full_version < '3.9'
148-
# via astunparse
149-
zipp==3.20.2 ; python_full_version < '3.9'
150-
# via importlib-metadata
151-
zipp==3.21.0 ; python_full_version >= '3.9'
116+
zipp==3.21.0
152117
# via importlib-metadata

scripts/test

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -68,8 +68,8 @@ if [[ -n "$UV_PYTHON" ]]; then
6868
else
6969
# If UV_PYTHON is not set, run the command for min and max versions
7070

71-
echo "==> Running tests for Python 3.8"
72-
UV_PYTHON=3.8 run_tests "$@"
71+
echo "==> Running tests for Python 3.9"
72+
UV_PYTHON=3.9 run_tests "$@"
7373

7474
echo "==> Running tests for Python 3.13"
7575
UV_PYTHON=3.13 run_tests "$@"

src/anthropic/_utils/_sync.py

Lines changed: 3 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,8 @@
11
from __future__ import annotations
22

3-
import sys
43
import asyncio
54
import functools
6-
import contextvars
7-
from typing import Any, TypeVar, Callable, Awaitable
5+
from typing import TypeVar, Callable, Awaitable
86
from typing_extensions import ParamSpec
97

108
import anyio
@@ -15,34 +13,11 @@
1513
T_ParamSpec = ParamSpec("T_ParamSpec")
1614

1715

18-
if sys.version_info >= (3, 9):
19-
_asyncio_to_thread = asyncio.to_thread
20-
else:
21-
# backport of https://docs.python.org/3/library/asyncio-task.html#asyncio.to_thread
22-
# for Python 3.8 support
23-
async def _asyncio_to_thread(
24-
func: Callable[T_ParamSpec, T_Retval], /, *args: T_ParamSpec.args, **kwargs: T_ParamSpec.kwargs
25-
) -> Any:
26-
"""Asynchronously run function *func* in a separate thread.
27-
28-
Any *args and **kwargs supplied for this function are directly passed
29-
to *func*. Also, the current :class:`contextvars.Context` is propagated,
30-
allowing context variables from the main thread to be accessed in the
31-
separate thread.
32-
33-
Returns a coroutine that can be awaited to get the eventual result of *func*.
34-
"""
35-
loop = asyncio.events.get_running_loop()
36-
ctx = contextvars.copy_context()
37-
func_call = functools.partial(ctx.run, func, *args, **kwargs)
38-
return await loop.run_in_executor(None, func_call)
39-
40-
4116
async def to_thread(
4217
func: Callable[T_ParamSpec, T_Retval], /, *args: T_ParamSpec.args, **kwargs: T_ParamSpec.kwargs
4318
) -> T_Retval:
4419
if sniffio.current_async_library() == "asyncio":
45-
return await _asyncio_to_thread(func, *args, **kwargs)
20+
return await asyncio.to_thread(func, *args, **kwargs)
4621

4722
return await anyio.to_thread.run_sync(
4823
functools.partial(func, *args, **kwargs),
@@ -53,10 +28,7 @@ async def to_thread(
5328
def asyncify(function: Callable[T_ParamSpec, T_Retval]) -> Callable[T_ParamSpec, Awaitable[T_Retval]]:
5429
"""
5530
Take a blocking function and create an async one that receives the same
56-
positional and keyword arguments. For python version 3.9 and above, it uses
57-
asyncio.to_thread to run the function in a separate thread. For python version
58-
3.8, it uses locally defined copy of the asyncio.to_thread function which was
59-
introduced in python 3.9.
31+
positional and keyword arguments.
6032
6133
Usage:
6234

0 commit comments

Comments
 (0)