agenthub-python 0.4.0__tar.gz → 0.4.1__tar.gz

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.
Files changed (38) hide show
  1. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/PKG-INFO +1 -1
  2. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/__init__.py +8 -1
  3. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/auto_client.py +16 -1
  4. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/claude4_6/client.py +4 -2
  5. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/claude5/client.py +7 -3
  6. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/deepseek_v4/client.py +10 -4
  7. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/errors.py +14 -0
  8. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/gemini3/client.py +4 -1
  9. agenthub_python-0.4.1/agenthub/gemini3_6/__init__.py +18 -0
  10. agenthub_python-0.4.1/agenthub/gemini3_6/client.py +458 -0
  11. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/glm5_1/client.py +7 -3
  12. agenthub_python-0.4.1/agenthub/glm5_2/__init__.py +18 -0
  13. agenthub_python-0.4.1/agenthub/glm5_2/client.py +410 -0
  14. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/gpt5_5/client.py +7 -3
  15. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/kimi_k2_6/client.py +10 -4
  16. agenthub_python-0.4.1/agenthub/kimi_k3/__init__.py +18 -0
  17. agenthub_python-0.4.1/agenthub/kimi_k3/client.py +436 -0
  18. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/openai/client.py +4 -2
  19. agenthub_python-0.4.1/agenthub/registry.py +564 -0
  20. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/pyproject.toml +1 -1
  21. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/README.md +0 -0
  22. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/abort_signal.py +0 -0
  23. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/base_client.py +0 -0
  24. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/claude4_6/__init__.py +0 -0
  25. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/claude5/__init__.py +0 -0
  26. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/deepseek_v4/__init__.py +0 -0
  27. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/gemini3/__init__.py +0 -0
  28. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/glm5_1/__init__.py +0 -0
  29. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/gpt5_5/__init__.py +0 -0
  30. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/integration/__init__.py +0 -0
  31. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/integration/playground.py +0 -0
  32. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/integration/tracer.py +0 -0
  33. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/kimi_k2_6/__init__.py +0 -0
  34. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/openai/__init__.py +0 -0
  35. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/openai_embedding/__init__.py +0 -0
  36. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/openai_embedding/client.py +0 -0
  37. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/types.py +0 -0
  38. {agenthub_python-0.4.0 → agenthub_python-0.4.1}/agenthub/utils.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: agenthub-python
3
- Version: 0.4.0
3
+ Version: 0.4.1
4
4
  Summary: AgentHub is the LLM API Hub for the Agent era, built for high-precision autonomous agents.
5
5
  Keywords: agent,llm,gemini,claude,gpt
6
6
  Author: PrismShadow
@@ -13,15 +13,22 @@
13
13
  # limitations under the License.
14
14
 
15
15
  from .auto_client import AutoLLMClient
16
- from .errors import AgentHubError, EmptyResponseError, ToolCallArgumentParseError
16
+ from .errors import AgentHubError, EmptyResponseError, ToolCallArgumentParseError, UnsupportedParameterError
17
+ from .registry import Currency, Modality, ModelPricing, SupportedModel, list_supported_models
17
18
  from .types import PromptCaching, ThinkingLevel
18
19
 
19
20
 
20
21
  __all__ = [
21
22
  "AgentHubError",
22
23
  "AutoLLMClient",
24
+ "Currency",
23
25
  "EmptyResponseError",
26
+ "Modality",
27
+ "ModelPricing",
24
28
  "PromptCaching",
29
+ "SupportedModel",
25
30
  "ThinkingLevel",
26
31
  "ToolCallArgumentParseError",
32
+ "UnsupportedParameterError",
33
+ "list_supported_models",
27
34
  ]
@@ -47,7 +47,14 @@ class AutoLLMClient(LLMClient):
47
47
  ) -> LLMClient:
48
48
  """Create the appropriate client for the given model."""
49
49
  client_type = (client_type or os.getenv("CLIENT_TYPE", model)).lower()
50
+ # gemini-3.6 must be matched before the broader gemini-3 prefix below
50
51
  if any(
52
+ prefix in client_type for prefix in ("gemini-3.6", "gemini-3.5-flash-lite")
53
+ ): # e.g., gemini-3.6-flash; gemini-3.5-flash-lite shares the sampling-parameter deprecation
54
+ from .gemini3_6 import Gemini3_6Client
55
+
56
+ return Gemini3_6Client(model=model, api_key=api_key, base_url=base_url)
57
+ elif any(
51
58
  prefix in client_type for prefix in ("gemini-3", "gemini-embedding")
52
59
  ): # e.g., gemini-3-flash-preview, gemini-embedding-2
53
60
  from .gemini3 import Gemini3Client
@@ -67,10 +74,18 @@ class AutoLLMClient(LLMClient):
67
74
  from .gpt5_5 import GPT5_5Client
68
75
 
69
76
  return GPT5_5Client(model=model, api_key=api_key, base_url=base_url)
77
+ elif "glm-5.2" in client_type:
78
+ from .glm5_2 import GLM5_2Client
79
+
80
+ return GLM5_2Client(model=model, api_key=api_key, base_url=base_url)
70
81
  elif "glm-5" in client_type or "glm-5.1" in client_type:
71
82
  from .glm5_1 import GLM5_1Client
72
83
 
73
84
  return GLM5_1Client(model=model, api_key=api_key, base_url=base_url)
85
+ elif "kimi-k3" in client_type:
86
+ from .kimi_k3 import KimiK3Client
87
+
88
+ return KimiK3Client(model=model, api_key=api_key, base_url=base_url)
74
89
  elif "kimi-k2.5" in client_type or "kimi-k2.6" in client_type:
75
90
  from .kimi_k2_6 import KimiK2_6Client
76
91
 
@@ -90,7 +105,7 @@ class AutoLLMClient(LLMClient):
90
105
  else:
91
106
  raise ValueError(
92
107
  f"{client_type} is not supported. "
93
- "Supported client types: gemini-3, claude-5, claude-4-8, claude-4-7, claude-4-6, gpt-5.5, gpt-5.4, glm-5.1, kimi-k2.6, kimi-k2.5, deepseek-v4, openai-embedding, openai."
108
+ "Supported client types: gemini-3.6, gemini-3, claude-5, claude-4-8, claude-4-7, claude-4-6, gpt-5.5, gpt-5.4, glm-5.2, glm-5.1, kimi-k3, kimi-k2.6, kimi-k2.5, deepseek-v4, openai-embedding, openai."
94
109
  )
95
110
 
96
111
  def transform_uni_config_to_model_config(self, config: UniConfig) -> Any:
@@ -23,7 +23,7 @@ from anthropic import AsyncAnthropic, AsyncAnthropicBedrock
23
23
  from anthropic.types.beta import BetaMessageParam, BetaRawMessageStreamEvent
24
24
 
25
25
  from ..base_client import LLMClient
26
- from ..errors import parse_tool_call_arguments
26
+ from ..errors import UnsupportedParameterError, parse_tool_call_arguments
27
27
  from ..types import (
28
28
  EventType,
29
29
  FinishReason,
@@ -118,7 +118,9 @@ class Claude4_6Client(LLMClient):
118
118
  """Convert ToolChoice to Claude's tool_choice format."""
119
119
  if isinstance(tool_choice, list):
120
120
  if len(tool_choice) > 1:
121
- raise ValueError("Claude supports only one tool choice.")
121
+ raise UnsupportedParameterError(
122
+ self.__class__.__name__, "tool_choice", "Claude supports only one tool choice."
123
+ )
122
124
 
123
125
  return {"type": "any", "name": tool_choice[0]}
124
126
  elif tool_choice == "none":
@@ -23,7 +23,7 @@ from anthropic import AsyncAnthropic, AsyncAnthropicBedrock
23
23
  from anthropic.types.beta import BetaMessageParam, BetaRawMessageStreamEvent
24
24
 
25
25
  from ..base_client import LLMClient
26
- from ..errors import parse_tool_call_arguments
26
+ from ..errors import UnsupportedParameterError, parse_tool_call_arguments
27
27
  from ..types import (
28
28
  EventType,
29
29
  FinishReason,
@@ -118,7 +118,9 @@ class Claude5Client(LLMClient):
118
118
  """Convert ToolChoice to Claude's tool_choice format."""
119
119
  if isinstance(tool_choice, list):
120
120
  if len(tool_choice) > 1:
121
- raise ValueError("Claude supports only one tool choice.")
121
+ raise UnsupportedParameterError(
122
+ self.__class__.__name__, "tool_choice", "Claude supports only one tool choice."
123
+ )
122
124
 
123
125
  return {"type": "any", "name": tool_choice[0]}
124
126
  elif tool_choice == "none":
@@ -149,7 +151,9 @@ class Claude5Client(LLMClient):
149
151
  claude_config["max_tokens"] = 64000 # Claude requires max_tokens to be specified
150
152
 
151
153
  if config.get("temperature") is not None and config["temperature"] != 1.0:
152
- raise ValueError("Claude 4.8 does not support setting temperature.")
154
+ raise UnsupportedParameterError(
155
+ self.__class__.__name__, "temperature", "Claude 4.8 does not support setting temperature."
156
+ )
153
157
 
154
158
  if config.get("thinking_level") is not None:
155
159
  claude_config.update(self._convert_thinking_level_to_thinking_config(config["thinking_level"]))
@@ -20,7 +20,7 @@ from openai import AsyncOpenAI
20
20
  from openai.types.chat import ChatCompletionChunk, ChatCompletionMessageParam
21
21
 
22
22
  from ..base_client import LLMClient
23
- from ..errors import parse_tool_call_arguments
23
+ from ..errors import UnsupportedParameterError, parse_tool_call_arguments
24
24
  from ..types import (
25
25
  EventType,
26
26
  FinishReason,
@@ -72,7 +72,9 @@ class DeepSeekV4Client(LLMClient):
72
72
  """Convert ToolChoice to DeepSeek's OpenAI-compatible tool_choice format."""
73
73
  if tool_choice in ["auto", "none"]:
74
74
  return tool_choice
75
- raise ValueError("DeepSeek V4 only supports 'auto' and 'none' for tool_choice.")
75
+ raise UnsupportedParameterError(
76
+ self.__class__.__name__, "tool_choice", "DeepSeek V4 only supports 'auto' and 'none' for tool_choice."
77
+ )
76
78
 
77
79
  def transform_uni_config_to_model_config(self, config: UniConfig) -> dict[str, Any]:
78
80
  """
@@ -90,7 +92,9 @@ class DeepSeekV4Client(LLMClient):
90
92
  deepseek_config["max_tokens"] = config["max_tokens"]
91
93
 
92
94
  if config.get("temperature") is not None and config["temperature"] != 1.0:
93
- raise ValueError("DeepSeek V4 does not support setting temperature.")
95
+ raise UnsupportedParameterError(
96
+ self.__class__.__name__, "temperature", "DeepSeek V4 does not support setting temperature."
97
+ )
94
98
 
95
99
  thinking_level = config.get("thinking_level")
96
100
  if thinking_level is not None:
@@ -106,7 +110,9 @@ class DeepSeekV4Client(LLMClient):
106
110
  deepseek_config["tool_choice"] = self._convert_tool_choice(config["tool_choice"])
107
111
 
108
112
  if config.get("prompt_caching") is not None and config["prompt_caching"] != PromptCaching.ENABLE:
109
- raise ValueError("prompt_caching must be ENABLE for DeepSeek.")
113
+ raise UnsupportedParameterError(
114
+ self.__class__.__name__, "prompt_caching", "prompt_caching must be ENABLE for DeepSeek."
115
+ )
110
116
 
111
117
  return deepseek_config
112
118
 
@@ -29,6 +29,20 @@ class AgentHubError(ValueError):
29
29
  """Base class for errors raised by AgentHub clients."""
30
30
 
31
31
 
32
+ class UnsupportedParameterError(AgentHubError):
33
+ """Raised when a UniConfig parameter value is not supported by the target model client.
34
+
35
+ Thinking levels never raise this by design: every client maps each ThinkingLevel
36
+ onto the closest level the model supports. Parameters such as temperature and
37
+ tool_choice may reject unsupported values with this error.
38
+ """
39
+
40
+ def __init__(self, client: str, parameter: str, message: str) -> None:
41
+ self.client = client
42
+ self.parameter = parameter
43
+ super().__init__(message)
44
+
45
+
32
46
  class EmptyResponseError(AgentHubError):
33
47
  """Raised when a completed response carries no non-thinking content and no tool calls.
34
48
 
@@ -25,6 +25,7 @@ from google.genai import types
25
25
  from google.oauth2 import service_account
26
26
 
27
27
  from ..base_client import LLMClient
28
+ from ..errors import UnsupportedParameterError
28
29
  from ..types import (
29
30
  ContentItem,
30
31
  EventType,
@@ -148,7 +149,9 @@ class Gemini3Client(LLMClient):
148
149
  config_params["tool_config"] = types.ToolConfig(function_calling_config=tool_config)
149
150
 
150
151
  if config.get("prompt_caching") is not None and config["prompt_caching"] != PromptCaching.ENABLE:
151
- raise ValueError("prompt_caching must be ENABLE for Gemini 3.")
152
+ raise UnsupportedParameterError(
153
+ self.__class__.__name__, "prompt_caching", "prompt_caching must be ENABLE for Gemini 3."
154
+ )
152
155
 
153
156
  if config.get("image_config") is not None:
154
157
  config_params["image_config"] = types.ImageConfig(**config["image_config"])
@@ -0,0 +1,18 @@
1
+ # Copyright 2025 Prism Shadow. and/or its affiliates
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ from .client import Gemini3_6Client
16
+
17
+
18
+ __all__ = ["Gemini3_6Client"]