anthropic 0.72.1__py3-none-any.whl → 0.74.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- anthropic/__init__.py +3 -0
- anthropic/_client.py +8 -0
- anthropic/_compat.py +6 -0
- anthropic/_models.py +13 -1
- anthropic/_utils/_transform.py +1 -1
- anthropic/_version.py +1 -1
- anthropic/lib/_files.py +2 -2
- anthropic/lib/_parse/_response.py +44 -0
- anthropic/lib/_parse/_transform.py +167 -0
- anthropic/lib/foundry.md +127 -0
- anthropic/lib/foundry.py +443 -0
- anthropic/lib/streaming/__init__.py +14 -4
- anthropic/lib/streaming/_beta_messages.py +82 -43
- anthropic/lib/streaming/_beta_types.py +21 -13
- anthropic/lib/tools/_beta_runner.py +102 -101
- anthropic/resources/beta/messages/batches.py +12 -12
- anthropic/resources/beta/messages/messages.py +365 -29
- anthropic/resources/messages/batches.py +12 -12
- anthropic/resources/messages/messages.py +14 -8
- anthropic/types/beta/__init__.py +1 -0
- anthropic/types/beta/beta_code_execution_tool_20250522_param.py +2 -0
- anthropic/types/beta/beta_code_execution_tool_20250825_param.py +2 -0
- anthropic/types/beta/beta_json_output_format_param.py +15 -0
- anthropic/types/beta/beta_memory_tool_20250818_param.py +2 -0
- anthropic/types/beta/beta_tool_bash_20241022_param.py +2 -0
- anthropic/types/beta/beta_tool_bash_20250124_param.py +2 -0
- anthropic/types/beta/beta_tool_computer_use_20241022_param.py +2 -0
- anthropic/types/beta/beta_tool_computer_use_20250124_param.py +2 -0
- anthropic/types/beta/beta_tool_param.py +2 -0
- anthropic/types/beta/beta_tool_text_editor_20241022_param.py +2 -0
- anthropic/types/beta/beta_tool_text_editor_20250124_param.py +2 -0
- anthropic/types/beta/beta_tool_text_editor_20250429_param.py +2 -0
- anthropic/types/beta/beta_tool_text_editor_20250728_param.py +2 -0
- anthropic/types/beta/beta_web_fetch_tool_20250910_param.py +2 -0
- anthropic/types/beta/beta_web_search_tool_20250305_param.py +2 -0
- anthropic/types/beta/message_count_tokens_params.py +4 -0
- anthropic/types/beta/message_create_params.py +24 -2
- anthropic/types/beta/messages/batch_create_params.py +8 -2
- anthropic/types/beta/parsed_beta_message.py +68 -0
- anthropic/types/messages/batch_create_params.py +0 -1
- {anthropic-0.72.1.dist-info → anthropic-0.74.0.dist-info}/METADATA +1 -1
- {anthropic-0.72.1.dist-info → anthropic-0.74.0.dist-info}/RECORD +44 -38
- {anthropic-0.72.1.dist-info → anthropic-0.74.0.dist-info}/WHEEL +0 -0
- {anthropic-0.72.1.dist-info → anthropic-0.74.0.dist-info}/licenses/LICENSE +0 -0
anthropic/__init__.py
CHANGED
|
@@ -44,6 +44,7 @@ from ._exceptions import (
|
|
|
44
44
|
)
|
|
45
45
|
from ._base_client import DefaultHttpxClient, DefaultAioHttpClient, DefaultAsyncHttpxClient
|
|
46
46
|
from ._utils._logs import setup_logging as _setup_logging
|
|
47
|
+
from .lib._parse._transform import transform_schema
|
|
47
48
|
|
|
48
49
|
__all__ = [
|
|
49
50
|
"types",
|
|
@@ -91,6 +92,7 @@ __all__ = [
|
|
|
91
92
|
"AI_PROMPT",
|
|
92
93
|
"beta_tool",
|
|
93
94
|
"beta_async_tool",
|
|
95
|
+
"transform_schema",
|
|
94
96
|
]
|
|
95
97
|
|
|
96
98
|
if not _t.TYPE_CHECKING:
|
|
@@ -99,6 +101,7 @@ if not _t.TYPE_CHECKING:
|
|
|
99
101
|
from .lib.tools import beta_tool, beta_async_tool
|
|
100
102
|
from .lib.vertex import *
|
|
101
103
|
from .lib.bedrock import *
|
|
104
|
+
from .lib.foundry import AnthropicFoundry as AnthropicFoundry, AsyncAnthropicFoundry as AsyncAnthropicFoundry
|
|
102
105
|
from .lib.streaming import *
|
|
103
106
|
|
|
104
107
|
_setup_logging()
|
anthropic/_client.py
CHANGED
|
@@ -183,6 +183,10 @@ class Anthropic(SyncAPIClient):
|
|
|
183
183
|
|
|
184
184
|
@override
|
|
185
185
|
def _validate_headers(self, headers: Headers, custom_headers: Headers) -> None:
|
|
186
|
+
if headers.get("Authorization") or headers.get("X-Api-Key"):
|
|
187
|
+
# valid
|
|
188
|
+
return
|
|
189
|
+
|
|
186
190
|
if self.api_key and headers.get("X-Api-Key"):
|
|
187
191
|
return
|
|
188
192
|
if isinstance(custom_headers.get("X-Api-Key"), Omit):
|
|
@@ -423,6 +427,10 @@ class AsyncAnthropic(AsyncAPIClient):
|
|
|
423
427
|
|
|
424
428
|
@override
|
|
425
429
|
def _validate_headers(self, headers: Headers, custom_headers: Headers) -> None:
|
|
430
|
+
if headers.get("Authorization") or headers.get("X-Api-Key"):
|
|
431
|
+
# valid
|
|
432
|
+
return
|
|
433
|
+
|
|
426
434
|
if self.api_key and headers.get("X-Api-Key"):
|
|
427
435
|
return
|
|
428
436
|
if isinstance(custom_headers.get("X-Api-Key"), Omit):
|
anthropic/_compat.py
CHANGED
|
@@ -131,6 +131,12 @@ def model_json(model: pydantic.BaseModel, *, indent: int | None = None) -> str:
|
|
|
131
131
|
return model.model_dump_json(indent=indent)
|
|
132
132
|
|
|
133
133
|
|
|
134
|
+
def model_parse_json(model: type[_ModelT], data: str | bytes) -> _ModelT:
|
|
135
|
+
if PYDANTIC_V1:
|
|
136
|
+
return model.parse_raw(data) # pyright: ignore[reportDeprecated]
|
|
137
|
+
return model.model_validate_json(data)
|
|
138
|
+
|
|
139
|
+
|
|
134
140
|
def model_dump(
|
|
135
141
|
model: pydantic.BaseModel,
|
|
136
142
|
*,
|
anthropic/_models.py
CHANGED
|
@@ -774,7 +774,7 @@ else:
|
|
|
774
774
|
|
|
775
775
|
|
|
776
776
|
if not PYDANTIC_V1:
|
|
777
|
-
from pydantic import TypeAdapter as _TypeAdapter
|
|
777
|
+
from pydantic import TypeAdapter as _TypeAdapter, computed_field as computed_field
|
|
778
778
|
|
|
779
779
|
_CachedTypeAdapter = cast("TypeAdapter[object]", lru_cache(maxsize=None)(_TypeAdapter))
|
|
780
780
|
|
|
@@ -811,6 +811,18 @@ elif not TYPE_CHECKING: # TODO: condition is weird
|
|
|
811
811
|
def TypeAdapter(*_args: Any, **_kwargs: Any) -> Any:
|
|
812
812
|
raise RuntimeError("attempted to use TypeAdapter in pydantic v1")
|
|
813
813
|
|
|
814
|
+
def computed_field(func: Any | None = None, /, **__: Any) -> Any:
|
|
815
|
+
def _exc_func(*_: Any, **__: Any) -> Any:
|
|
816
|
+
raise RuntimeError("attempted to use computed_field in pydantic v1")
|
|
817
|
+
|
|
818
|
+
def _dec(*_: Any, **__: Any) -> Any:
|
|
819
|
+
return _exc_func
|
|
820
|
+
|
|
821
|
+
if func is not None:
|
|
822
|
+
return _dec(func)
|
|
823
|
+
else:
|
|
824
|
+
return _dec
|
|
825
|
+
|
|
814
826
|
|
|
815
827
|
class FinalRequestOptionsInput(TypedDict, total=False):
|
|
816
828
|
method: Required[str]
|
anthropic/_utils/_transform.py
CHANGED
|
@@ -218,7 +218,7 @@ def _transform_recursive(
|
|
|
218
218
|
return data
|
|
219
219
|
|
|
220
220
|
if isinstance(data, pydantic.BaseModel):
|
|
221
|
-
return model_dump(data, exclude_unset=True, mode="json")
|
|
221
|
+
return model_dump(data, exclude_unset=True, mode="json", exclude=getattr(data, "__api_exclude__", None))
|
|
222
222
|
|
|
223
223
|
annotated_type = _get_annotated_type(annotation)
|
|
224
224
|
if annotated_type is None:
|
anthropic/_version.py
CHANGED
anthropic/lib/_files.py
CHANGED
|
@@ -22,7 +22,7 @@ def _collect_files(directory: Path, relative_to: Path, files: list[FileTypes]) -
|
|
|
22
22
|
_collect_files(path, relative_to, files)
|
|
23
23
|
continue
|
|
24
24
|
|
|
25
|
-
files.append((
|
|
25
|
+
files.append((path.relative_to(relative_to).as_posix(), path.read_bytes()))
|
|
26
26
|
|
|
27
27
|
|
|
28
28
|
async def async_files_from_dir(directory: str | os.PathLike[str]) -> list[FileTypes]:
|
|
@@ -39,4 +39,4 @@ async def _async_collect_files(directory: anyio.Path, relative_to: anyio.Path, f
|
|
|
39
39
|
await _async_collect_files(path, relative_to, files)
|
|
40
40
|
continue
|
|
41
41
|
|
|
42
|
-
files.append((
|
|
42
|
+
files.append((path.relative_to(relative_to).as_posix(), await path.read_bytes()))
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
from typing_extensions import TypeVar
|
|
4
|
+
|
|
5
|
+
from ..._types import NotGiven
|
|
6
|
+
from ..._models import TypeAdapter, construct_type_unchecked
|
|
7
|
+
from ..._utils._utils import is_given
|
|
8
|
+
from ...types.beta.beta_message import BetaMessage
|
|
9
|
+
from ...types.beta.parsed_beta_message import ParsedBetaMessage, ParsedBetaTextBlock, ParsedBetaContentBlock
|
|
10
|
+
|
|
11
|
+
ResponseFormatT = TypeVar("ResponseFormatT", default=None)
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
def parse_text(text: str, output_format: ResponseFormatT | NotGiven) -> ResponseFormatT | None:
|
|
15
|
+
if is_given(output_format):
|
|
16
|
+
adapted_type: TypeAdapter[ResponseFormatT] = TypeAdapter(output_format)
|
|
17
|
+
return adapted_type.validate_json(text)
|
|
18
|
+
return None
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
def parse_response(
|
|
22
|
+
*,
|
|
23
|
+
output_format: ResponseFormatT | NotGiven,
|
|
24
|
+
response: BetaMessage,
|
|
25
|
+
) -> ParsedBetaMessage[ResponseFormatT]:
|
|
26
|
+
content_list: list[ParsedBetaContentBlock[ResponseFormatT]] = []
|
|
27
|
+
for content in response.content:
|
|
28
|
+
if content.type == "text":
|
|
29
|
+
content_list.append(
|
|
30
|
+
construct_type_unchecked(
|
|
31
|
+
type_=ParsedBetaTextBlock[ResponseFormatT],
|
|
32
|
+
value={**content.to_dict(), "parsed_output": parse_text(content.text, output_format)},
|
|
33
|
+
)
|
|
34
|
+
)
|
|
35
|
+
else:
|
|
36
|
+
content_list.append(content) # type: ignore
|
|
37
|
+
|
|
38
|
+
return construct_type_unchecked(
|
|
39
|
+
type_=ParsedBetaMessage[ResponseFormatT],
|
|
40
|
+
value={
|
|
41
|
+
**response.to_dict(),
|
|
42
|
+
"content": content_list,
|
|
43
|
+
},
|
|
44
|
+
)
|
|
@@ -0,0 +1,167 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import inspect
|
|
4
|
+
from typing import Any, Literal, Optional, cast
|
|
5
|
+
from typing_extensions import assert_never
|
|
6
|
+
|
|
7
|
+
import pydantic
|
|
8
|
+
|
|
9
|
+
from ..._utils import is_list
|
|
10
|
+
|
|
11
|
+
SupportedTypes = Literal[
|
|
12
|
+
"object",
|
|
13
|
+
"array",
|
|
14
|
+
"string",
|
|
15
|
+
"integer",
|
|
16
|
+
"number",
|
|
17
|
+
"boolean",
|
|
18
|
+
"null",
|
|
19
|
+
]
|
|
20
|
+
|
|
21
|
+
SupportedStringFormats = {
|
|
22
|
+
"date-time",
|
|
23
|
+
"time",
|
|
24
|
+
"date",
|
|
25
|
+
"duration",
|
|
26
|
+
"email",
|
|
27
|
+
"hostname",
|
|
28
|
+
"uri",
|
|
29
|
+
"ipv4",
|
|
30
|
+
"ipv6",
|
|
31
|
+
"uuid",
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
def get_transformed_string(
|
|
36
|
+
schema: dict[str, Any],
|
|
37
|
+
) -> dict[str, Any]:
|
|
38
|
+
"""Transforms a JSON schema of type string to ensure it conforms to the API's expectations.
|
|
39
|
+
|
|
40
|
+
Specifically, it ensures that if the schema is of type "string" and does not already
|
|
41
|
+
specify a "format", it sets the format to "text".
|
|
42
|
+
|
|
43
|
+
Args:
|
|
44
|
+
schema: The original JSON schema.
|
|
45
|
+
|
|
46
|
+
Returns:
|
|
47
|
+
The transformed JSON schema.
|
|
48
|
+
"""
|
|
49
|
+
if schema.get("type") == "string" and "format" not in schema:
|
|
50
|
+
schema["format"] = "text"
|
|
51
|
+
return schema
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
def transform_schema(
|
|
55
|
+
json_schema: type[pydantic.BaseModel] | dict[str, Any],
|
|
56
|
+
) -> dict[str, Any]:
|
|
57
|
+
"""
|
|
58
|
+
Transforms a JSON schema to ensure it conforms to the API's expectations.
|
|
59
|
+
|
|
60
|
+
Args:
|
|
61
|
+
json_schema (Dict[str, Any]): The original JSON schema.
|
|
62
|
+
|
|
63
|
+
Returns:
|
|
64
|
+
The transformed JSON schema.
|
|
65
|
+
|
|
66
|
+
Examples:
|
|
67
|
+
>>> transform_schema(
|
|
68
|
+
... {
|
|
69
|
+
... "type": "integer",
|
|
70
|
+
... "minimum": 1,
|
|
71
|
+
... "maximum": 10,
|
|
72
|
+
... "description": "A number",
|
|
73
|
+
... }
|
|
74
|
+
... )
|
|
75
|
+
{'type': 'integer', 'description': 'A number\n\n{minimum: 1, maximum: 10}'}
|
|
76
|
+
"""
|
|
77
|
+
if inspect.isclass(json_schema) and issubclass(json_schema, pydantic.BaseModel): # pyright: ignore[reportUnnecessaryIsInstance]
|
|
78
|
+
json_schema = json_schema.model_json_schema()
|
|
79
|
+
|
|
80
|
+
strict_schema: dict[str, Any] = {}
|
|
81
|
+
json_schema = {**json_schema}
|
|
82
|
+
|
|
83
|
+
ref = json_schema.pop("$ref", None)
|
|
84
|
+
if ref is not None:
|
|
85
|
+
strict_schema["$ref"] = ref
|
|
86
|
+
return strict_schema
|
|
87
|
+
|
|
88
|
+
defs = json_schema.pop("$defs", None)
|
|
89
|
+
if defs is not None:
|
|
90
|
+
strict_defs: dict[str, Any] = {}
|
|
91
|
+
strict_schema["$defs"] = strict_defs
|
|
92
|
+
|
|
93
|
+
for name, schema in defs.items():
|
|
94
|
+
strict_defs[name] = transform_schema(schema)
|
|
95
|
+
|
|
96
|
+
type_: Optional[SupportedTypes] = json_schema.pop("type", None)
|
|
97
|
+
any_of = json_schema.pop("anyOf", None)
|
|
98
|
+
one_of = json_schema.pop("oneOf", None)
|
|
99
|
+
all_of = json_schema.pop("allOf", None)
|
|
100
|
+
|
|
101
|
+
if is_list(any_of):
|
|
102
|
+
strict_schema["anyOf"] = [transform_schema(cast("dict[str, Any]", variant)) for variant in any_of]
|
|
103
|
+
elif is_list(one_of):
|
|
104
|
+
strict_schema["anyOf"] = [transform_schema(cast("dict[str, Any]", variant)) for variant in one_of]
|
|
105
|
+
elif is_list(all_of):
|
|
106
|
+
strict_schema["allOf"] = [transform_schema(cast("dict[str, Any]", variant)) for variant in all_of]
|
|
107
|
+
else:
|
|
108
|
+
if type_ is None:
|
|
109
|
+
raise ValueError("Schema must have a 'type', 'anyOf', 'oneOf', or 'allOf' field.")
|
|
110
|
+
|
|
111
|
+
strict_schema["type"] = type_
|
|
112
|
+
|
|
113
|
+
description = json_schema.pop("description", None)
|
|
114
|
+
if description is not None:
|
|
115
|
+
strict_schema["description"] = description
|
|
116
|
+
|
|
117
|
+
title = json_schema.pop("title", None)
|
|
118
|
+
if title is not None:
|
|
119
|
+
strict_schema["title"] = title
|
|
120
|
+
|
|
121
|
+
if type_ == "object":
|
|
122
|
+
strict_schema["properties"] = {
|
|
123
|
+
key: transform_schema(prop_schema) for key, prop_schema in json_schema.pop("properties", {}).items()
|
|
124
|
+
}
|
|
125
|
+
json_schema.pop("additionalProperties", None)
|
|
126
|
+
strict_schema["additionalProperties"] = False
|
|
127
|
+
|
|
128
|
+
required = json_schema.pop("required", None)
|
|
129
|
+
if required is not None:
|
|
130
|
+
strict_schema["required"] = required
|
|
131
|
+
|
|
132
|
+
elif type_ == "string":
|
|
133
|
+
format = json_schema.pop("format", None)
|
|
134
|
+
if format and format in SupportedStringFormats:
|
|
135
|
+
strict_schema["format"] = format
|
|
136
|
+
elif format:
|
|
137
|
+
# add it back so its treated as an extra property and appended to the description
|
|
138
|
+
json_schema["format"] = format
|
|
139
|
+
elif type_ == "array":
|
|
140
|
+
items = json_schema.pop("items", None)
|
|
141
|
+
if items is not None:
|
|
142
|
+
strict_schema["items"] = transform_schema(items)
|
|
143
|
+
|
|
144
|
+
min_items = json_schema.pop("minItems", None)
|
|
145
|
+
if min_items is not None and min_items == 0 or min_items == 1:
|
|
146
|
+
strict_schema["minItems"] = min_items
|
|
147
|
+
elif min_items is not None:
|
|
148
|
+
# add it back so its treated as an extra property and appended to the description
|
|
149
|
+
json_schema["minItems"] = min_items
|
|
150
|
+
|
|
151
|
+
elif type_ == "boolean" or type_ == "integer" or type_ == "number" or type_ == "null" or type_ is None:
|
|
152
|
+
pass
|
|
153
|
+
else:
|
|
154
|
+
assert_never(type_)
|
|
155
|
+
|
|
156
|
+
# if there are any propes leftover then they aren't supported, so we add them to the description
|
|
157
|
+
# so that the model *might* follow them.
|
|
158
|
+
if json_schema:
|
|
159
|
+
description = strict_schema.get("description")
|
|
160
|
+
strict_schema["description"] = (
|
|
161
|
+
(description + "\n\n" if description is not None else "")
|
|
162
|
+
+ "{"
|
|
163
|
+
+ ", ".join(f"{key}: {value}" for key, value in json_schema.items())
|
|
164
|
+
+ "}"
|
|
165
|
+
)
|
|
166
|
+
|
|
167
|
+
return strict_schema
|
anthropic/lib/foundry.md
ADDED
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
# Anthropic Foundry
|
|
2
|
+
|
|
3
|
+
To use this library with Foundry, use the `AnthropicFoundry` class instead of the `Anthropic` class.
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
## Installation
|
|
7
|
+
|
|
8
|
+
```bash
|
|
9
|
+
pip install anthropic
|
|
10
|
+
```
|
|
11
|
+
|
|
12
|
+
## Usage
|
|
13
|
+
|
|
14
|
+
### Basic Usage with API Key
|
|
15
|
+
|
|
16
|
+
```python
|
|
17
|
+
from anthropic import AnthropicFoundry
|
|
18
|
+
|
|
19
|
+
client = AnthropicFoundry(
|
|
20
|
+
api_key="...", # defaults to ANTHROPIC_FOUNDRY_API_KEY environment variable
|
|
21
|
+
resource="my-resource", # your Foundry resource
|
|
22
|
+
)
|
|
23
|
+
|
|
24
|
+
message = client.messages.create(
|
|
25
|
+
model="claude-3-5-sonnet-20241022",
|
|
26
|
+
max_tokens=1024,
|
|
27
|
+
messages=[{"role": "user", "content": "Hello!"}],
|
|
28
|
+
)
|
|
29
|
+
|
|
30
|
+
print(message.content[0].text)
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
### Using Azure AD Token Provider
|
|
34
|
+
|
|
35
|
+
For enhanced security, you can use Azure AD (Microsoft Entra) authentication instead of an API key:
|
|
36
|
+
|
|
37
|
+
```python
|
|
38
|
+
from anthropic import AnthropicFoundry
|
|
39
|
+
from azure.identity import DefaultAzureCredential
|
|
40
|
+
from azure.identity import get_bearer_token_provider
|
|
41
|
+
|
|
42
|
+
credential = DefaultAzureCredential()
|
|
43
|
+
token_provider = get_bearer_token_provider(
|
|
44
|
+
credential,
|
|
45
|
+
"https://ai.azure.com/.default"
|
|
46
|
+
)
|
|
47
|
+
|
|
48
|
+
client = AnthropicFoundry(
|
|
49
|
+
azure_ad_token_provider=token_provider,
|
|
50
|
+
resource="my-resource",
|
|
51
|
+
)
|
|
52
|
+
|
|
53
|
+
message = client.messages.create(
|
|
54
|
+
model="claude-3-5-sonnet-20241022",
|
|
55
|
+
max_tokens=1024,
|
|
56
|
+
messages=[{"role": "user", "content": "Hello!"}],
|
|
57
|
+
)
|
|
58
|
+
|
|
59
|
+
print(message.content[0].text)
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
## Examples
|
|
63
|
+
|
|
64
|
+
### Streaming Messages
|
|
65
|
+
|
|
66
|
+
```python
|
|
67
|
+
from anthropic import AnthropicFoundry
|
|
68
|
+
|
|
69
|
+
client = AnthropicFoundry(
|
|
70
|
+
api_key="...",
|
|
71
|
+
resource="my-resource",
|
|
72
|
+
)
|
|
73
|
+
|
|
74
|
+
with client.messages.stream(
|
|
75
|
+
model="claude-3-5-sonnet-20241022",
|
|
76
|
+
max_tokens=1024,
|
|
77
|
+
messages=[{"role": "user", "content": "Write a haiku about programming"}],
|
|
78
|
+
) as stream:
|
|
79
|
+
for text in stream.text_stream:
|
|
80
|
+
print(text, end="", flush=True)
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
### Async Usage
|
|
84
|
+
|
|
85
|
+
```python
|
|
86
|
+
from anthropic import AsyncAnthropicFoundry
|
|
87
|
+
|
|
88
|
+
async def main():
|
|
89
|
+
client = AsyncAnthropicFoundry(
|
|
90
|
+
api_key="...",
|
|
91
|
+
resource="my-resource",
|
|
92
|
+
)
|
|
93
|
+
|
|
94
|
+
message = await client.messages.create(
|
|
95
|
+
model="claude-3-5-sonnet-20241022",
|
|
96
|
+
max_tokens=1024,
|
|
97
|
+
messages=[{"role": "user", "content": "Hello!"}],
|
|
98
|
+
)
|
|
99
|
+
|
|
100
|
+
print(message.content[0].text)
|
|
101
|
+
|
|
102
|
+
import asyncio
|
|
103
|
+
asyncio.run(main())
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
### Async Streaming
|
|
107
|
+
|
|
108
|
+
```python
|
|
109
|
+
from anthropic import AsyncAnthropicFoundry
|
|
110
|
+
|
|
111
|
+
async def main():
|
|
112
|
+
client = AsyncAnthropicFoundry(
|
|
113
|
+
api_key="...",
|
|
114
|
+
resource="my-resource",
|
|
115
|
+
)
|
|
116
|
+
|
|
117
|
+
async with client.messages.stream(
|
|
118
|
+
model="claude-3-5-sonnet-20241022",
|
|
119
|
+
max_tokens=1024,
|
|
120
|
+
messages=[{"role": "user", "content": "Write a haiku about programming"}],
|
|
121
|
+
) as stream:
|
|
122
|
+
async for text in stream.text_stream:
|
|
123
|
+
print(text, end="", flush=True)
|
|
124
|
+
|
|
125
|
+
import asyncio
|
|
126
|
+
asyncio.run(main())
|
|
127
|
+
```
|