mirascope 2.0.0a2__py3-none-any.whl → 2.0.0a4__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.
- mirascope/__init__.py +2 -2
- mirascope/api/__init__.py +6 -0
- mirascope/api/_generated/README.md +207 -0
- mirascope/api/_generated/__init__.py +141 -0
- mirascope/api/_generated/client.py +163 -0
- mirascope/api/_generated/core/__init__.py +52 -0
- mirascope/api/_generated/core/api_error.py +23 -0
- mirascope/api/_generated/core/client_wrapper.py +58 -0
- mirascope/api/_generated/core/datetime_utils.py +30 -0
- mirascope/api/_generated/core/file.py +70 -0
- mirascope/api/_generated/core/force_multipart.py +16 -0
- mirascope/api/_generated/core/http_client.py +619 -0
- mirascope/api/_generated/core/http_response.py +55 -0
- mirascope/api/_generated/core/jsonable_encoder.py +102 -0
- mirascope/api/_generated/core/pydantic_utilities.py +310 -0
- mirascope/api/_generated/core/query_encoder.py +60 -0
- mirascope/api/_generated/core/remove_none_from_dict.py +11 -0
- mirascope/api/_generated/core/request_options.py +35 -0
- mirascope/api/_generated/core/serialization.py +282 -0
- mirascope/api/_generated/docs/__init__.py +4 -0
- mirascope/api/_generated/docs/client.py +95 -0
- mirascope/api/_generated/docs/raw_client.py +132 -0
- mirascope/api/_generated/environment.py +9 -0
- mirascope/api/_generated/errors/__init__.py +17 -0
- mirascope/api/_generated/errors/bad_request_error.py +15 -0
- mirascope/api/_generated/errors/conflict_error.py +15 -0
- mirascope/api/_generated/errors/forbidden_error.py +15 -0
- mirascope/api/_generated/errors/internal_server_error.py +15 -0
- mirascope/api/_generated/errors/not_found_error.py +15 -0
- mirascope/api/_generated/health/__init__.py +7 -0
- mirascope/api/_generated/health/client.py +96 -0
- mirascope/api/_generated/health/raw_client.py +129 -0
- mirascope/api/_generated/health/types/__init__.py +8 -0
- mirascope/api/_generated/health/types/health_check_response.py +24 -0
- mirascope/api/_generated/health/types/health_check_response_status.py +5 -0
- mirascope/api/_generated/organizations/__init__.py +25 -0
- mirascope/api/_generated/organizations/client.py +380 -0
- mirascope/api/_generated/organizations/raw_client.py +876 -0
- mirascope/api/_generated/organizations/types/__init__.py +23 -0
- mirascope/api/_generated/organizations/types/organizations_create_response.py +24 -0
- mirascope/api/_generated/organizations/types/organizations_create_response_role.py +7 -0
- mirascope/api/_generated/organizations/types/organizations_get_response.py +24 -0
- mirascope/api/_generated/organizations/types/organizations_get_response_role.py +7 -0
- mirascope/api/_generated/organizations/types/organizations_list_response_item.py +24 -0
- mirascope/api/_generated/organizations/types/organizations_list_response_item_role.py +7 -0
- mirascope/api/_generated/organizations/types/organizations_update_response.py +24 -0
- mirascope/api/_generated/organizations/types/organizations_update_response_role.py +7 -0
- mirascope/api/_generated/projects/__init__.py +17 -0
- mirascope/api/_generated/projects/client.py +458 -0
- mirascope/api/_generated/projects/raw_client.py +1016 -0
- mirascope/api/_generated/projects/types/__init__.py +15 -0
- mirascope/api/_generated/projects/types/projects_create_response.py +30 -0
- mirascope/api/_generated/projects/types/projects_get_response.py +30 -0
- mirascope/api/_generated/projects/types/projects_list_response_item.py +30 -0
- mirascope/api/_generated/projects/types/projects_update_response.py +30 -0
- mirascope/api/_generated/reference.md +753 -0
- mirascope/api/_generated/traces/__init__.py +55 -0
- mirascope/api/_generated/traces/client.py +162 -0
- mirascope/api/_generated/traces/raw_client.py +168 -0
- mirascope/api/_generated/traces/types/__init__.py +95 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item.py +36 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_resource.py +31 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_resource_attributes_item.py +25 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_resource_attributes_item_value.py +54 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_resource_attributes_item_value_array_value.py +23 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_resource_attributes_item_value_kvlist_value.py +28 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_resource_attributes_item_value_kvlist_value_values_item.py +24 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item.py +35 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_scope.py +35 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_scope_attributes_item.py +27 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_scope_attributes_item_value.py +54 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_scope_attributes_item_value_array_value.py +23 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_scope_attributes_item_value_kvlist_value.py +28 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_scope_attributes_item_value_kvlist_value_values_item.py +24 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item.py +60 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item_attributes_item.py +29 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item_attributes_item_value.py +54 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item_attributes_item_value_array_value.py +23 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item_attributes_item_value_kvlist_value.py +28 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item_attributes_item_value_kvlist_value_values_item.py +24 -0
- mirascope/api/_generated/traces/types/traces_create_request_resource_spans_item_scope_spans_item_spans_item_status.py +24 -0
- mirascope/api/_generated/traces/types/traces_create_response.py +27 -0
- mirascope/api/_generated/traces/types/traces_create_response_partial_success.py +28 -0
- mirascope/api/_generated/types/__init__.py +37 -0
- mirascope/api/_generated/types/already_exists_error.py +24 -0
- mirascope/api/_generated/types/already_exists_error_tag.py +5 -0
- mirascope/api/_generated/types/database_error.py +24 -0
- mirascope/api/_generated/types/database_error_tag.py +5 -0
- mirascope/api/_generated/types/http_api_decode_error.py +29 -0
- mirascope/api/_generated/types/http_api_decode_error_tag.py +5 -0
- mirascope/api/_generated/types/issue.py +40 -0
- mirascope/api/_generated/types/issue_tag.py +17 -0
- mirascope/api/_generated/types/not_found_error_body.py +24 -0
- mirascope/api/_generated/types/not_found_error_tag.py +5 -0
- mirascope/api/_generated/types/permission_denied_error.py +24 -0
- mirascope/api/_generated/types/permission_denied_error_tag.py +7 -0
- mirascope/api/_generated/types/property_key.py +7 -0
- mirascope/api/_generated/types/property_key_key.py +27 -0
- mirascope/api/_generated/types/property_key_key_tag.py +5 -0
- mirascope/api/client.py +255 -0
- mirascope/api/settings.py +81 -0
- mirascope/llm/__init__.py +45 -11
- mirascope/llm/calls/calls.py +81 -57
- mirascope/llm/calls/decorator.py +121 -115
- mirascope/llm/content/__init__.py +3 -2
- mirascope/llm/context/_utils.py +19 -6
- mirascope/llm/exceptions.py +30 -16
- mirascope/llm/formatting/_utils.py +9 -5
- mirascope/llm/formatting/format.py +2 -2
- mirascope/llm/formatting/from_call_args.py +2 -2
- mirascope/llm/messages/message.py +13 -5
- mirascope/llm/models/__init__.py +2 -2
- mirascope/llm/models/models.py +189 -81
- mirascope/llm/prompts/__init__.py +13 -12
- mirascope/llm/prompts/_utils.py +27 -24
- mirascope/llm/prompts/decorator.py +133 -204
- mirascope/llm/prompts/prompts.py +424 -0
- mirascope/llm/prompts/protocols.py +25 -59
- mirascope/llm/providers/__init__.py +44 -0
- mirascope/llm/{clients → providers}/_missing_import_stubs.py +8 -6
- mirascope/llm/providers/anthropic/__init__.py +29 -0
- mirascope/llm/providers/anthropic/_utils/__init__.py +23 -0
- mirascope/llm/providers/anthropic/_utils/beta_decode.py +271 -0
- mirascope/llm/providers/anthropic/_utils/beta_encode.py +216 -0
- mirascope/llm/{clients → providers}/anthropic/_utils/decode.py +44 -11
- mirascope/llm/providers/anthropic/_utils/encode.py +356 -0
- mirascope/llm/providers/anthropic/beta_provider.py +322 -0
- mirascope/llm/providers/anthropic/model_id.py +23 -0
- mirascope/llm/providers/anthropic/model_info.py +87 -0
- mirascope/llm/providers/anthropic/provider.py +416 -0
- mirascope/llm/{clients → providers}/base/__init__.py +3 -3
- mirascope/llm/{clients → providers}/base/_utils.py +25 -8
- mirascope/llm/{clients/base/client.py → providers/base/base_provider.py} +255 -126
- mirascope/llm/providers/google/__init__.py +21 -0
- mirascope/llm/{clients → providers}/google/_utils/decode.py +61 -7
- mirascope/llm/{clients → providers}/google/_utils/encode.py +44 -30
- mirascope/llm/providers/google/model_id.py +22 -0
- mirascope/llm/providers/google/model_info.py +62 -0
- mirascope/llm/providers/google/provider.py +442 -0
- mirascope/llm/providers/load_provider.py +54 -0
- mirascope/llm/providers/mlx/__init__.py +24 -0
- mirascope/llm/providers/mlx/_utils.py +129 -0
- mirascope/llm/providers/mlx/encoding/__init__.py +8 -0
- mirascope/llm/providers/mlx/encoding/base.py +69 -0
- mirascope/llm/providers/mlx/encoding/transformers.py +147 -0
- mirascope/llm/providers/mlx/mlx.py +237 -0
- mirascope/llm/providers/mlx/model_id.py +17 -0
- mirascope/llm/providers/mlx/provider.py +415 -0
- mirascope/llm/providers/model_id.py +16 -0
- mirascope/llm/providers/ollama/__init__.py +19 -0
- mirascope/llm/providers/ollama/provider.py +71 -0
- mirascope/llm/providers/openai/__init__.py +6 -0
- mirascope/llm/providers/openai/completions/__init__.py +25 -0
- mirascope/llm/{clients → providers}/openai/completions/_utils/__init__.py +2 -0
- mirascope/llm/{clients → providers}/openai/completions/_utils/decode.py +60 -6
- mirascope/llm/{clients → providers}/openai/completions/_utils/encode.py +37 -26
- mirascope/llm/providers/openai/completions/base_provider.py +513 -0
- mirascope/llm/providers/openai/completions/provider.py +22 -0
- mirascope/llm/providers/openai/model_id.py +31 -0
- mirascope/llm/providers/openai/model_info.py +303 -0
- mirascope/llm/providers/openai/provider.py +398 -0
- mirascope/llm/providers/openai/responses/__init__.py +21 -0
- mirascope/llm/{clients → providers}/openai/responses/_utils/decode.py +59 -6
- mirascope/llm/{clients → providers}/openai/responses/_utils/encode.py +34 -23
- mirascope/llm/providers/openai/responses/provider.py +469 -0
- mirascope/llm/providers/provider_id.py +23 -0
- mirascope/llm/providers/provider_registry.py +169 -0
- mirascope/llm/providers/together/__init__.py +19 -0
- mirascope/llm/providers/together/provider.py +40 -0
- mirascope/llm/responses/__init__.py +3 -0
- mirascope/llm/responses/base_response.py +14 -5
- mirascope/llm/responses/base_stream_response.py +35 -6
- mirascope/llm/responses/finish_reason.py +1 -0
- mirascope/llm/responses/response.py +33 -13
- mirascope/llm/responses/root_response.py +12 -13
- mirascope/llm/responses/stream_response.py +35 -23
- mirascope/llm/responses/usage.py +95 -0
- mirascope/llm/tools/__init__.py +9 -2
- mirascope/llm/tools/_utils.py +12 -3
- mirascope/llm/tools/protocols.py +4 -4
- mirascope/llm/tools/tool_schema.py +44 -9
- mirascope/llm/tools/tools.py +10 -9
- mirascope/ops/__init__.py +156 -0
- mirascope/ops/_internal/__init__.py +5 -0
- mirascope/ops/_internal/closure.py +1118 -0
- mirascope/ops/_internal/configuration.py +126 -0
- mirascope/ops/_internal/context.py +76 -0
- mirascope/ops/_internal/exporters/__init__.py +26 -0
- mirascope/ops/_internal/exporters/exporters.py +342 -0
- mirascope/ops/_internal/exporters/processors.py +104 -0
- mirascope/ops/_internal/exporters/types.py +165 -0
- mirascope/ops/_internal/exporters/utils.py +29 -0
- mirascope/ops/_internal/instrumentation/__init__.py +8 -0
- mirascope/ops/_internal/instrumentation/llm/__init__.py +8 -0
- mirascope/ops/_internal/instrumentation/llm/encode.py +238 -0
- mirascope/ops/_internal/instrumentation/llm/gen_ai_types/__init__.py +38 -0
- mirascope/ops/_internal/instrumentation/llm/gen_ai_types/gen_ai_input_messages.py +31 -0
- mirascope/ops/_internal/instrumentation/llm/gen_ai_types/gen_ai_output_messages.py +38 -0
- mirascope/ops/_internal/instrumentation/llm/gen_ai_types/gen_ai_system_instructions.py +18 -0
- mirascope/ops/_internal/instrumentation/llm/gen_ai_types/shared.py +100 -0
- mirascope/ops/_internal/instrumentation/llm/llm.py +1288 -0
- mirascope/ops/_internal/propagation.py +198 -0
- mirascope/ops/_internal/protocols.py +51 -0
- mirascope/ops/_internal/session.py +139 -0
- mirascope/ops/_internal/spans.py +232 -0
- mirascope/ops/_internal/traced_calls.py +371 -0
- mirascope/ops/_internal/traced_functions.py +394 -0
- mirascope/ops/_internal/tracing.py +276 -0
- mirascope/ops/_internal/types.py +13 -0
- mirascope/ops/_internal/utils.py +75 -0
- mirascope/ops/_internal/versioned_calls.py +512 -0
- mirascope/ops/_internal/versioned_functions.py +346 -0
- mirascope/ops/_internal/versioning.py +303 -0
- mirascope/ops/exceptions.py +21 -0
- {mirascope-2.0.0a2.dist-info → mirascope-2.0.0a4.dist-info}/METADATA +78 -3
- mirascope-2.0.0a4.dist-info/RECORD +247 -0
- {mirascope-2.0.0a2.dist-info → mirascope-2.0.0a4.dist-info}/WHEEL +1 -1
- mirascope/graphs/__init__.py +0 -22
- mirascope/graphs/finite_state_machine.py +0 -625
- mirascope/llm/agents/__init__.py +0 -15
- mirascope/llm/agents/agent.py +0 -97
- mirascope/llm/agents/agent_template.py +0 -45
- mirascope/llm/agents/decorator.py +0 -176
- mirascope/llm/calls/base_call.py +0 -33
- mirascope/llm/clients/__init__.py +0 -34
- mirascope/llm/clients/anthropic/__init__.py +0 -25
- mirascope/llm/clients/anthropic/_utils/encode.py +0 -243
- mirascope/llm/clients/anthropic/clients.py +0 -819
- mirascope/llm/clients/anthropic/model_ids.py +0 -8
- mirascope/llm/clients/google/__init__.py +0 -20
- mirascope/llm/clients/google/clients.py +0 -853
- mirascope/llm/clients/google/model_ids.py +0 -15
- mirascope/llm/clients/openai/__init__.py +0 -25
- mirascope/llm/clients/openai/completions/__init__.py +0 -28
- mirascope/llm/clients/openai/completions/_utils/model_features.py +0 -81
- mirascope/llm/clients/openai/completions/clients.py +0 -833
- mirascope/llm/clients/openai/completions/model_ids.py +0 -8
- mirascope/llm/clients/openai/responses/__init__.py +0 -26
- mirascope/llm/clients/openai/responses/_utils/__init__.py +0 -13
- mirascope/llm/clients/openai/responses/_utils/model_features.py +0 -87
- mirascope/llm/clients/openai/responses/clients.py +0 -832
- mirascope/llm/clients/openai/responses/model_ids.py +0 -8
- mirascope/llm/clients/openai/shared/__init__.py +0 -7
- mirascope/llm/clients/openai/shared/_utils.py +0 -55
- mirascope/llm/clients/providers.py +0 -175
- mirascope-2.0.0a2.dist-info/RECORD +0 -102
- /mirascope/llm/{clients → providers}/base/kwargs.py +0 -0
- /mirascope/llm/{clients → providers}/base/params.py +0 -0
- /mirascope/llm/{clients/anthropic → providers/google}/_utils/__init__.py +0 -0
- /mirascope/llm/{clients → providers}/google/message.py +0 -0
- /mirascope/llm/{clients/google → providers/openai/responses}/_utils/__init__.py +0 -0
- {mirascope-2.0.0a2.dist-info → mirascope-2.0.0a4.dist-info}/licenses/LICENSE +0 -0
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
"""Provider-agnostic usage statistics for LLM API calls."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from dataclasses import dataclass
|
|
6
|
+
from typing import Any, Literal
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
@dataclass(kw_only=True)
|
|
10
|
+
class UsageDeltaChunk:
|
|
11
|
+
"""A chunk containing incremental token usage information from a streaming response.
|
|
12
|
+
|
|
13
|
+
This represents a delta/increment in usage statistics as they arrive during streaming.
|
|
14
|
+
Multiple UsageDeltaChunks are accumulated to produce the final Usage object.
|
|
15
|
+
"""
|
|
16
|
+
|
|
17
|
+
type: Literal["usage_delta_chunk"] = "usage_delta_chunk"
|
|
18
|
+
|
|
19
|
+
input_tokens: int = 0
|
|
20
|
+
"""Delta in input tokens."""
|
|
21
|
+
|
|
22
|
+
output_tokens: int = 0
|
|
23
|
+
"""Delta in output tokens."""
|
|
24
|
+
|
|
25
|
+
cache_read_tokens: int = 0
|
|
26
|
+
"""Delta in cache read tokens."""
|
|
27
|
+
|
|
28
|
+
cache_write_tokens: int = 0
|
|
29
|
+
"""Delta in cache write tokens."""
|
|
30
|
+
|
|
31
|
+
reasoning_tokens: int = 0
|
|
32
|
+
"""Delta in reasoning/thinking tokens."""
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
@dataclass(kw_only=True)
|
|
36
|
+
class Usage:
|
|
37
|
+
"""Token usage statistics from an LLM API call.
|
|
38
|
+
|
|
39
|
+
This abstraction captures common usage metrics across providers while preserving
|
|
40
|
+
access to the raw provider-specific usage data.
|
|
41
|
+
"""
|
|
42
|
+
|
|
43
|
+
input_tokens: int = 0
|
|
44
|
+
"""The number of input tokens used.
|
|
45
|
+
|
|
46
|
+
This includes ALL input tokens, including cache read and write tokens.
|
|
47
|
+
|
|
48
|
+
Will be 0 if not reported by the provider.
|
|
49
|
+
"""
|
|
50
|
+
|
|
51
|
+
output_tokens: int = 0
|
|
52
|
+
"""The number of output tokens used.
|
|
53
|
+
|
|
54
|
+
This includes ALL output tokens, including `reasoning_tokens` that may not be
|
|
55
|
+
in the user's visible output, or other "hidden" tokens.
|
|
56
|
+
|
|
57
|
+
Will be 0 if not reported by the provider.
|
|
58
|
+
"""
|
|
59
|
+
|
|
60
|
+
cache_read_tokens: int = 0
|
|
61
|
+
"""The number of tokens read from cache (prompt caching).
|
|
62
|
+
|
|
63
|
+
These are input tokens that were read from cache. Cache read tokens are generally
|
|
64
|
+
much less expensive than regular input tokens.
|
|
65
|
+
|
|
66
|
+
Will be 0 if not reported by the provider or if caching was not used.
|
|
67
|
+
"""
|
|
68
|
+
|
|
69
|
+
cache_write_tokens: int = 0
|
|
70
|
+
"""The number of tokens written to cache (cache creation).
|
|
71
|
+
|
|
72
|
+
These are input tokens that were written to cache, for future reuse and retrieval.
|
|
73
|
+
Cache write tokens are generally more expensive than uncached input tokens,
|
|
74
|
+
but may lead to cost savings down the line when they are re-read as cache_read_tokens.
|
|
75
|
+
|
|
76
|
+
Will be 0 if not reported by the provider or if caching was not used.
|
|
77
|
+
"""
|
|
78
|
+
|
|
79
|
+
reasoning_tokens: int = 0
|
|
80
|
+
"""The number of tokens used for reasoning/thinking.
|
|
81
|
+
|
|
82
|
+
Reasoning tokens are a subset of output_tokens that were generated as part of the model's
|
|
83
|
+
interior reasoning process. They are billed as output tokens, though they are generally
|
|
84
|
+
not shown to the user.
|
|
85
|
+
|
|
86
|
+
Will be 0 if not reported by the provider or if the model does not support reasoning.
|
|
87
|
+
"""
|
|
88
|
+
|
|
89
|
+
raw: Any = None
|
|
90
|
+
"""The raw usage object from the provider."""
|
|
91
|
+
|
|
92
|
+
@property
|
|
93
|
+
def total_tokens(self) -> int:
|
|
94
|
+
"""The total number of tokens used (input + output)."""
|
|
95
|
+
return self.input_tokens + self.output_tokens
|
mirascope/llm/tools/__init__.py
CHANGED
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
"""The Tools module for LLMs."""
|
|
2
2
|
|
|
3
|
-
from . import protocols
|
|
4
3
|
from .decorator import ToolDecorator, tool
|
|
4
|
+
from .protocols import AsyncContextToolFn, AsyncToolFn, ContextToolFn, ToolFn
|
|
5
5
|
from .tool_schema import (
|
|
6
6
|
FORMAT_TOOL_NAME,
|
|
7
|
+
AnyToolFn,
|
|
8
|
+
AnyToolSchema,
|
|
7
9
|
ToolParameterSchema,
|
|
8
10
|
ToolSchema,
|
|
9
11
|
ToolSchemaT,
|
|
@@ -20,21 +22,26 @@ from .tools import AsyncContextTool, AsyncTool, ContextTool, Tool, ToolT
|
|
|
20
22
|
|
|
21
23
|
__all__ = [
|
|
22
24
|
"FORMAT_TOOL_NAME",
|
|
25
|
+
"AnyToolFn",
|
|
26
|
+
"AnyToolSchema",
|
|
23
27
|
"AsyncContextTool",
|
|
28
|
+
"AsyncContextToolFn",
|
|
24
29
|
"AsyncContextToolkit",
|
|
25
30
|
"AsyncTool",
|
|
31
|
+
"AsyncToolFn",
|
|
26
32
|
"AsyncToolkit",
|
|
27
33
|
"BaseToolkit",
|
|
28
34
|
"ContextTool",
|
|
35
|
+
"ContextToolFn",
|
|
29
36
|
"ContextToolkit",
|
|
30
37
|
"Tool",
|
|
31
38
|
"ToolDecorator",
|
|
39
|
+
"ToolFn",
|
|
32
40
|
"ToolParameterSchema",
|
|
33
41
|
"ToolSchema",
|
|
34
42
|
"ToolSchemaT",
|
|
35
43
|
"ToolT",
|
|
36
44
|
"Toolkit",
|
|
37
45
|
"ToolkitT",
|
|
38
|
-
"protocols",
|
|
39
46
|
"tool",
|
|
40
47
|
]
|
mirascope/llm/tools/_utils.py
CHANGED
|
@@ -9,7 +9,10 @@ from .protocols import AsyncContextToolFn, AsyncToolFn, ContextToolFn, ToolFn
|
|
|
9
9
|
|
|
10
10
|
|
|
11
11
|
def is_context_tool_fn(
|
|
12
|
-
fn:
|
|
12
|
+
fn: ContextToolFn[DepsT, P, JsonableCovariantT]
|
|
13
|
+
| AsyncContextToolFn[DepsT, P, JsonableCovariantT]
|
|
14
|
+
| ToolFn[P, JsonableCovariantT]
|
|
15
|
+
| AsyncToolFn[P, JsonableCovariantT],
|
|
13
16
|
) -> TypeIs[
|
|
14
17
|
ContextToolFn[DepsT, P, JsonableCovariantT]
|
|
15
18
|
| AsyncContextToolFn[DepsT, P, JsonableCovariantT]
|
|
@@ -19,7 +22,13 @@ def is_context_tool_fn(
|
|
|
19
22
|
|
|
20
23
|
|
|
21
24
|
def is_async_tool_fn(
|
|
22
|
-
fn:
|
|
23
|
-
|
|
25
|
+
fn: ContextToolFn[DepsT, P, JsonableCovariantT]
|
|
26
|
+
| AsyncContextToolFn[DepsT, P, JsonableCovariantT]
|
|
27
|
+
| ToolFn[P, JsonableCovariantT]
|
|
28
|
+
| AsyncToolFn[P, JsonableCovariantT],
|
|
29
|
+
) -> TypeIs[
|
|
30
|
+
AsyncContextToolFn[DepsT, P, JsonableCovariantT]
|
|
31
|
+
| AsyncToolFn[P, JsonableCovariantT]
|
|
32
|
+
]:
|
|
24
33
|
"""Type guard to check if a function is an async tool function."""
|
|
25
34
|
return inspect.iscoroutinefunction(fn)
|
mirascope/llm/tools/protocols.py
CHANGED
|
@@ -52,7 +52,7 @@ class AsyncContextToolFn(Protocol[DepsT, P, JsonableCovariantT]):
|
|
|
52
52
|
raise NotImplementedError()
|
|
53
53
|
|
|
54
54
|
|
|
55
|
-
class
|
|
55
|
+
class KwargsCallable(Protocol[JsonableCovariantT]):
|
|
56
56
|
"""Protocol for functions that can be called with `Any`-typed kwargs.
|
|
57
57
|
|
|
58
58
|
Used internally to type-cast tool functions for compatibility with
|
|
@@ -62,7 +62,7 @@ class _KwargsCallable(Protocol[JsonableCovariantT]):
|
|
|
62
62
|
def __call__(self, **kwargs: dict[str, Any]) -> JsonableCovariantT: ...
|
|
63
63
|
|
|
64
64
|
|
|
65
|
-
class
|
|
65
|
+
class AsyncKwargsCallable(Protocol[JsonableCovariantT]):
|
|
66
66
|
"""Protocol for async functions that can be called with `Any`-typed kwargs.
|
|
67
67
|
|
|
68
68
|
Used internally to type-cast async tool functions for compatibility with
|
|
@@ -72,7 +72,7 @@ class _AsyncKwargsCallable(Protocol[JsonableCovariantT]):
|
|
|
72
72
|
async def __call__(self, **kwargs: dict[str, Any]) -> JsonableCovariantT: ...
|
|
73
73
|
|
|
74
74
|
|
|
75
|
-
class
|
|
75
|
+
class ContextKwargsCallable(Protocol[DepsT, JsonableCovariantT]):
|
|
76
76
|
"""Protocol for context functions that can be called with `Any`-typed kwargs.
|
|
77
77
|
|
|
78
78
|
Used internally to type-cast context tool functions for compatibility with
|
|
@@ -84,7 +84,7 @@ class _ContextKwargsCallable(Protocol[DepsT, JsonableCovariantT]):
|
|
|
84
84
|
) -> JsonableCovariantT: ...
|
|
85
85
|
|
|
86
86
|
|
|
87
|
-
class
|
|
87
|
+
class AsyncJsonKwargsCallable(Protocol[DepsT, JsonableCovariantT]):
|
|
88
88
|
"""Protocol for async context functions that can be called with `Any`-typed kwargs.
|
|
89
89
|
|
|
90
90
|
Used internally to type-cast async context tool functions for compatibility with
|
|
@@ -3,13 +3,16 @@
|
|
|
3
3
|
from __future__ import annotations
|
|
4
4
|
|
|
5
5
|
import inspect
|
|
6
|
-
from collections import namedtuple
|
|
7
6
|
from dataclasses import dataclass
|
|
8
7
|
from typing import (
|
|
9
8
|
Annotated,
|
|
10
9
|
Any,
|
|
11
10
|
Generic,
|
|
11
|
+
NamedTuple,
|
|
12
|
+
TypeAlias,
|
|
13
|
+
TypedDict,
|
|
12
14
|
TypeVar,
|
|
15
|
+
cast,
|
|
13
16
|
get_args,
|
|
14
17
|
get_origin,
|
|
15
18
|
get_type_hints,
|
|
@@ -20,16 +23,48 @@ from pydantic import BaseModel, Field, create_model
|
|
|
20
23
|
from pydantic.fields import FieldInfo
|
|
21
24
|
|
|
22
25
|
from ..content import ToolCall
|
|
26
|
+
from ..types import Jsonable
|
|
23
27
|
from .protocols import AsyncContextToolFn, AsyncToolFn, ContextToolFn, ToolFn
|
|
24
28
|
|
|
29
|
+
AnyToolFn: TypeAlias = (
|
|
30
|
+
ToolFn[..., Jsonable]
|
|
31
|
+
| AsyncToolFn[..., Jsonable]
|
|
32
|
+
| ContextToolFn[Any, ..., Jsonable]
|
|
33
|
+
| AsyncContextToolFn[Any, ..., Jsonable]
|
|
34
|
+
)
|
|
35
|
+
|
|
25
36
|
ToolFnT = TypeVar(
|
|
26
37
|
"ToolFnT",
|
|
27
|
-
bound=
|
|
38
|
+
bound=AnyToolFn,
|
|
28
39
|
covariant=True,
|
|
29
40
|
)
|
|
30
|
-
ToolSchemaT = TypeVar("ToolSchemaT", bound="ToolSchema")
|
|
31
41
|
|
|
32
|
-
|
|
42
|
+
AnyToolSchema: TypeAlias = "ToolSchema[AnyToolFn]"
|
|
43
|
+
ToolSchemaT = TypeVar("ToolSchemaT", bound=AnyToolSchema, covariant=True)
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
ModelJsonSchema = TypedDict(
|
|
47
|
+
"ModelJsonSchema",
|
|
48
|
+
{
|
|
49
|
+
"properties": dict[str, dict[str, Any]],
|
|
50
|
+
"required": list[str],
|
|
51
|
+
"$defs": dict[str, dict[str, Any]],
|
|
52
|
+
},
|
|
53
|
+
total=False,
|
|
54
|
+
)
|
|
55
|
+
"""Type for Pydantic's model_json_schema() output.
|
|
56
|
+
|
|
57
|
+
This TypedDict defines the structure of JSON schemas returned by Pydantic models,
|
|
58
|
+
allowing us to avoid type casts when extracting schema components.
|
|
59
|
+
"""
|
|
60
|
+
|
|
61
|
+
|
|
62
|
+
class DocstringArg(NamedTuple):
|
|
63
|
+
"""A parameter from a docstring."""
|
|
64
|
+
|
|
65
|
+
name: str
|
|
66
|
+
description: str
|
|
67
|
+
|
|
33
68
|
|
|
34
69
|
FORMAT_TOOL_NAME = "__mirascope_formatted_output_tool__"
|
|
35
70
|
"""Reserved name of the formatted output tool.
|
|
@@ -63,7 +98,7 @@ def _parse_docstring_params(docstring: str | None) -> ParsedDocstring:
|
|
|
63
98
|
return ParsedDocstring(args=[])
|
|
64
99
|
|
|
65
100
|
parsed = parse(docstring)
|
|
66
|
-
args = []
|
|
101
|
+
args: list[DocstringArg] = []
|
|
67
102
|
|
|
68
103
|
for param in parsed.params:
|
|
69
104
|
if param.description:
|
|
@@ -170,7 +205,7 @@ class ToolSchema(Generic[ToolFnT]):
|
|
|
170
205
|
|
|
171
206
|
param_descriptions = _parse_docstring_params(fn.__doc__)
|
|
172
207
|
|
|
173
|
-
field_definitions = {}
|
|
208
|
+
field_definitions: dict[str, tuple[Any, Any]] = {}
|
|
174
209
|
hints = get_type_hints(fn, include_extras=True)
|
|
175
210
|
|
|
176
211
|
context_param_skipped = False
|
|
@@ -203,7 +238,7 @@ class ToolSchema(Generic[ToolFnT]):
|
|
|
203
238
|
description=field_info.description,
|
|
204
239
|
)
|
|
205
240
|
else:
|
|
206
|
-
docstring_description = None
|
|
241
|
+
docstring_description: str | None = None
|
|
207
242
|
for arg in param_descriptions.args:
|
|
208
243
|
if arg.name == param.name:
|
|
209
244
|
docstring_description = arg.description
|
|
@@ -217,9 +252,9 @@ class ToolSchema(Generic[ToolFnT]):
|
|
|
217
252
|
|
|
218
253
|
field_definitions[param.name] = (param_type, field_value)
|
|
219
254
|
|
|
220
|
-
TempModel = create_model("TempModel", **field_definitions)
|
|
255
|
+
TempModel = create_model("TempModel", **cast(dict[str, Any], field_definitions))
|
|
221
256
|
|
|
222
|
-
schema = TempModel.model_json_schema()
|
|
257
|
+
schema = cast(ModelJsonSchema, TempModel.model_json_schema())
|
|
223
258
|
|
|
224
259
|
parameters = ToolParameterSchema(
|
|
225
260
|
properties=schema.get("properties", {}),
|
mirascope/llm/tools/tools.py
CHANGED
|
@@ -4,20 +4,21 @@ from __future__ import annotations
|
|
|
4
4
|
|
|
5
5
|
import json
|
|
6
6
|
from collections.abc import Awaitable
|
|
7
|
-
from typing import Any, Generic,
|
|
7
|
+
from typing import Any, Generic, cast
|
|
8
|
+
from typing_extensions import TypeVar
|
|
8
9
|
|
|
9
10
|
from ..content import ToolCall, ToolOutput
|
|
10
11
|
from ..context import Context, DepsT
|
|
11
12
|
from ..types import AnyP, JsonableCovariantT
|
|
12
13
|
from .protocols import (
|
|
13
14
|
AsyncContextToolFn,
|
|
15
|
+
AsyncJsonKwargsCallable,
|
|
16
|
+
AsyncKwargsCallable,
|
|
14
17
|
AsyncToolFn,
|
|
18
|
+
ContextKwargsCallable,
|
|
15
19
|
ContextToolFn,
|
|
20
|
+
KwargsCallable,
|
|
16
21
|
ToolFn,
|
|
17
|
-
_AsyncJsonKwargsCallable,
|
|
18
|
-
_AsyncKwargsCallable,
|
|
19
|
-
_ContextKwargsCallable,
|
|
20
|
-
_KwargsCallable,
|
|
21
22
|
)
|
|
22
23
|
from .tool_schema import ToolSchema
|
|
23
24
|
|
|
@@ -51,7 +52,7 @@ class Tool(
|
|
|
51
52
|
def execute(self, tool_call: ToolCall) -> ToolOutput[JsonableCovariantT]:
|
|
52
53
|
"""Execute the tool using an LLM-provided `ToolCall`."""
|
|
53
54
|
kwargs_from_json = json.loads(tool_call.args)
|
|
54
|
-
kwargs_callable = cast(
|
|
55
|
+
kwargs_callable = cast(KwargsCallable[JsonableCovariantT], self.fn)
|
|
55
56
|
result = kwargs_callable(**kwargs_from_json)
|
|
56
57
|
return ToolOutput(id=tool_call.id, value=result, name=self.name)
|
|
57
58
|
|
|
@@ -82,7 +83,7 @@ class AsyncTool(
|
|
|
82
83
|
async def execute(self, tool_call: ToolCall) -> ToolOutput[JsonableCovariantT]:
|
|
83
84
|
"""Execute the async tool using an LLM-provided `ToolCall`."""
|
|
84
85
|
kwargs_from_json = json.loads(tool_call.args)
|
|
85
|
-
kwargs_callable = cast(
|
|
86
|
+
kwargs_callable = cast(AsyncKwargsCallable[JsonableCovariantT], self.fn)
|
|
86
87
|
result = await kwargs_callable(**kwargs_from_json)
|
|
87
88
|
return ToolOutput(id=tool_call.id, value=result, name=self.name)
|
|
88
89
|
|
|
@@ -122,7 +123,7 @@ class ContextTool(
|
|
|
122
123
|
"""Execute the context tool using an LLM-provided `ToolCall`."""
|
|
123
124
|
kwargs_from_json = json.loads(tool_call.args)
|
|
124
125
|
kwargs_callable = cast(
|
|
125
|
-
|
|
126
|
+
ContextKwargsCallable[DepsT, JsonableCovariantT], self.fn
|
|
126
127
|
)
|
|
127
128
|
result = kwargs_callable(ctx, **kwargs_from_json)
|
|
128
129
|
return ToolOutput(id=tool_call.id, value=result, name=self.name)
|
|
@@ -163,7 +164,7 @@ class AsyncContextTool(
|
|
|
163
164
|
"""Execute the async context tool using an LLM-provided `ToolCall`."""
|
|
164
165
|
kwargs_from_json = json.loads(tool_call.args)
|
|
165
166
|
kwargs_callable = cast(
|
|
166
|
-
|
|
167
|
+
AsyncJsonKwargsCallable[DepsT, JsonableCovariantT], self.fn
|
|
167
168
|
)
|
|
168
169
|
result = await kwargs_callable(ctx, **kwargs_from_json)
|
|
169
170
|
return ToolOutput(id=tool_call.id, value=result, name=self.name)
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
"""Operational helpers (tracing, sessions, future ops.* utilities)."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
try:
|
|
6
|
+
from ._internal.configuration import configure, tracer_context
|
|
7
|
+
from ._internal.context import propagated_context
|
|
8
|
+
from ._internal.instrumentation.llm import (
|
|
9
|
+
instrument_llm,
|
|
10
|
+
uninstrument_llm,
|
|
11
|
+
)
|
|
12
|
+
from ._internal.propagation import (
|
|
13
|
+
ContextPropagator,
|
|
14
|
+
PropagatorFormat,
|
|
15
|
+
extract_context,
|
|
16
|
+
get_propagator,
|
|
17
|
+
inject_context,
|
|
18
|
+
reset_propagator,
|
|
19
|
+
)
|
|
20
|
+
from ._internal.session import (
|
|
21
|
+
SESSION_HEADER_NAME,
|
|
22
|
+
SessionContext,
|
|
23
|
+
current_session,
|
|
24
|
+
extract_session_id,
|
|
25
|
+
session,
|
|
26
|
+
)
|
|
27
|
+
from ._internal.spans import Span, span
|
|
28
|
+
from ._internal.traced_calls import (
|
|
29
|
+
TracedAsyncCall,
|
|
30
|
+
TracedAsyncContextCall,
|
|
31
|
+
TracedCall,
|
|
32
|
+
TracedContextCall,
|
|
33
|
+
)
|
|
34
|
+
from ._internal.traced_functions import (
|
|
35
|
+
AsyncTrace,
|
|
36
|
+
AsyncTracedFunction,
|
|
37
|
+
Trace,
|
|
38
|
+
TracedFunction,
|
|
39
|
+
)
|
|
40
|
+
from ._internal.tracing import (
|
|
41
|
+
TraceDecorator,
|
|
42
|
+
trace,
|
|
43
|
+
)
|
|
44
|
+
from ._internal.versioned_calls import (
|
|
45
|
+
VersionedAsyncCall,
|
|
46
|
+
VersionedAsyncContextCall,
|
|
47
|
+
VersionedCall,
|
|
48
|
+
VersionedContextCall,
|
|
49
|
+
)
|
|
50
|
+
from ._internal.versioned_functions import (
|
|
51
|
+
AsyncVersionedFunction,
|
|
52
|
+
VersionedFunction,
|
|
53
|
+
VersionInfo,
|
|
54
|
+
)
|
|
55
|
+
from ._internal.versioning import (
|
|
56
|
+
VersionDecorator,
|
|
57
|
+
version,
|
|
58
|
+
)
|
|
59
|
+
from .exceptions import ClosureComputationError
|
|
60
|
+
|
|
61
|
+
except ImportError: # pragma: no cover
|
|
62
|
+
# TODO: refactor alongside other import error handling improvements
|
|
63
|
+
from collections.abc import Callable
|
|
64
|
+
|
|
65
|
+
def _create_otel_import_error_stub(name: str) -> Callable[..., None]:
|
|
66
|
+
"""Create a stub that raises ImportError with helpful message."""
|
|
67
|
+
|
|
68
|
+
def _raise_not_installed() -> None:
|
|
69
|
+
raise ImportError(
|
|
70
|
+
f"The 'opentelemetry' packages are required to use {name}. "
|
|
71
|
+
"Install them with: `uv add 'mirascope[otel]'`."
|
|
72
|
+
)
|
|
73
|
+
|
|
74
|
+
return _raise_not_installed
|
|
75
|
+
|
|
76
|
+
propagated_context = _create_otel_import_error_stub("propagated_context")
|
|
77
|
+
instrument_llm = _create_otel_import_error_stub("instrument_llm")
|
|
78
|
+
uninstrument_llm = _create_otel_import_error_stub("uninstrument_llm")
|
|
79
|
+
ContextPropagator = _create_otel_import_error_stub("ContextPropagator")
|
|
80
|
+
PropagatorFormat = str
|
|
81
|
+
extract_context = _create_otel_import_error_stub("extract_context")
|
|
82
|
+
get_propagator = _create_otel_import_error_stub("get_propagator")
|
|
83
|
+
inject_context = _create_otel_import_error_stub("inject_context")
|
|
84
|
+
reset_propagator = _create_otel_import_error_stub("reset_propagator")
|
|
85
|
+
SESSION_HEADER_NAME = "X-Mirascope-Session-ID"
|
|
86
|
+
SessionContext = _create_otel_import_error_stub("SessionContext")
|
|
87
|
+
current_session = _create_otel_import_error_stub("current_session")
|
|
88
|
+
extract_session_id = _create_otel_import_error_stub("extract_session_id")
|
|
89
|
+
session = _create_otel_import_error_stub("session")
|
|
90
|
+
Span = _create_otel_import_error_stub("Span")
|
|
91
|
+
span = _create_otel_import_error_stub("span")
|
|
92
|
+
AsyncTrace = _create_otel_import_error_stub("AsyncTrace")
|
|
93
|
+
AsyncTracedFunction = _create_otel_import_error_stub("AsyncTracedFunction")
|
|
94
|
+
Trace = _create_otel_import_error_stub("Trace")
|
|
95
|
+
TraceDecorator = _create_otel_import_error_stub("TraceDecorator")
|
|
96
|
+
TracedAsyncCall = _create_otel_import_error_stub("TracedAsyncCall")
|
|
97
|
+
TracedAsyncContextCall = _create_otel_import_error_stub("TracedAsyncContextCall")
|
|
98
|
+
TracedCall = _create_otel_import_error_stub("TracedCall")
|
|
99
|
+
TracedContextCall = _create_otel_import_error_stub("TracedContextCall")
|
|
100
|
+
TracedFunction = _create_otel_import_error_stub("TracedFunction")
|
|
101
|
+
trace = _create_otel_import_error_stub("trace")
|
|
102
|
+
configure = _create_otel_import_error_stub("configure")
|
|
103
|
+
tracer_context = _create_otel_import_error_stub("tracer_context")
|
|
104
|
+
AsyncVersionedFunction = _create_otel_import_error_stub("AsyncVersionedFunction")
|
|
105
|
+
VersionDecorator = _create_otel_import_error_stub("VersionDecorator")
|
|
106
|
+
VersionedAsyncCall = _create_otel_import_error_stub("VersionedAsyncCall")
|
|
107
|
+
VersionedAsyncContextCall = _create_otel_import_error_stub(
|
|
108
|
+
"VersionedAsyncContextCall"
|
|
109
|
+
)
|
|
110
|
+
VersionedCall = _create_otel_import_error_stub("VersionedCall")
|
|
111
|
+
VersionedContextCall = _create_otel_import_error_stub("VersionedContextCall")
|
|
112
|
+
VersionedFunction = _create_otel_import_error_stub("VersionedFunction")
|
|
113
|
+
VersionInfo = _create_otel_import_error_stub("VersionInfo")
|
|
114
|
+
version = _create_otel_import_error_stub("version")
|
|
115
|
+
|
|
116
|
+
|
|
117
|
+
__all__ = [
|
|
118
|
+
"SESSION_HEADER_NAME",
|
|
119
|
+
"AsyncTrace",
|
|
120
|
+
"AsyncTracedFunction",
|
|
121
|
+
"AsyncVersionedFunction",
|
|
122
|
+
"ClosureComputationError",
|
|
123
|
+
"ContextPropagator",
|
|
124
|
+
"PropagatorFormat",
|
|
125
|
+
"SessionContext",
|
|
126
|
+
"Span",
|
|
127
|
+
"Trace",
|
|
128
|
+
"TraceDecorator",
|
|
129
|
+
"TracedAsyncCall",
|
|
130
|
+
"TracedAsyncContextCall",
|
|
131
|
+
"TracedCall",
|
|
132
|
+
"TracedContextCall",
|
|
133
|
+
"TracedFunction",
|
|
134
|
+
"VersionDecorator",
|
|
135
|
+
"VersionInfo",
|
|
136
|
+
"VersionedAsyncCall",
|
|
137
|
+
"VersionedAsyncContextCall",
|
|
138
|
+
"VersionedCall",
|
|
139
|
+
"VersionedContextCall",
|
|
140
|
+
"VersionedFunction",
|
|
141
|
+
"configure",
|
|
142
|
+
"current_session",
|
|
143
|
+
"extract_context",
|
|
144
|
+
"extract_session_id",
|
|
145
|
+
"get_propagator",
|
|
146
|
+
"inject_context",
|
|
147
|
+
"instrument_llm",
|
|
148
|
+
"propagated_context",
|
|
149
|
+
"reset_propagator",
|
|
150
|
+
"session",
|
|
151
|
+
"span",
|
|
152
|
+
"trace",
|
|
153
|
+
"tracer_context",
|
|
154
|
+
"uninstrument_llm",
|
|
155
|
+
"version",
|
|
156
|
+
]
|