sofias-sdk-lite 0.2.0__tar.gz → 0.2.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.
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/PKG-INFO +1 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/pyproject.toml +1 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/pyproject.toml.orig +1 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/agent.py +3 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/agent_builder.py +6 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/agent_config.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/middleware.py +3 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/response_workflow.py +7 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/agent_settings.py +3 -2
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/runtime_config.py +4 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/sdk_config.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/source.py +6 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/agent_contracts.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/base_contracts.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/errors/error_handler.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/messaging/models.py +6 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/aggregator_config.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/aggregator_node.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/base_node.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/delegation_config.py +6 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/function_node.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/llm_node.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/llm_node_config.py +4 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/planner_node.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/prompt_assembler.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/events.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/tracing.py +4 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/consumer.py +3 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/delegation_transport.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/rpc_client.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/routing/router.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/routing/strategies.py +14 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/runner/runner.py +3 -1
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/state/conversation_state.py +4 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/state/history.py +2 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/LICENSE +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/README.md +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/execution_context.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/streaming.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/defaults.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/node_contracts.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/strict_contract.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/errors/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/errors/circuit_breaker.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/errors/exceptions.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/factory.py +8 -8
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/gateway.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/openai_compatible.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/protocol.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/tokens.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/tools.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/messaging/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/delegation_node.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/delegation_transport.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/plan_executor.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/planning_models.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/_log.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/trace_context.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/py.typed +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/client.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/config.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/publisher.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/types.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/routing/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/runner/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/runner/config.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/state/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/state/memory.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/tools.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/workflows/__init__.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/workflows/chat.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/workflows/null.py +0 -0
- {sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/workflows/streaming_chat.py +0 -0
|
@@ -67,12 +67,13 @@ class Agent:
|
|
|
67
67
|
to Node instances which handle their own execution.
|
|
68
68
|
|
|
69
69
|
Example:
|
|
70
|
+
```python
|
|
70
71
|
# Agent is typically built via AgentBuilder
|
|
71
72
|
agent = (
|
|
72
73
|
AgentBuilder("my_agent", version="1.0.0")
|
|
73
74
|
.with_settings_class(MySettings)
|
|
74
75
|
.with_contract(input_schema=MyInput, output_schema=MyOutput)
|
|
75
|
-
.
|
|
76
|
+
.add_llm_node("start", node_config, contract)
|
|
76
77
|
.set_entry_node("start")
|
|
77
78
|
.set_terminal("start")
|
|
78
79
|
.build()
|
|
@@ -86,6 +87,7 @@ class Agent:
|
|
|
86
87
|
)
|
|
87
88
|
)
|
|
88
89
|
assert response.status == ResponseStatus.SUCCESS
|
|
90
|
+
```
|
|
89
91
|
"""
|
|
90
92
|
|
|
91
93
|
def __init__(
|
|
@@ -64,6 +64,7 @@ class AgentBuilder:
|
|
|
64
64
|
time, catching configuration errors before runtime.
|
|
65
65
|
|
|
66
66
|
Example:
|
|
67
|
+
```python
|
|
67
68
|
agent = (
|
|
68
69
|
AgentBuilder("inbox_assist", version="1.0.0")
|
|
69
70
|
.with_description("Agent that processes incoming emails")
|
|
@@ -84,6 +85,7 @@ class AgentBuilder:
|
|
|
84
85
|
.with_circuit_breaker(CircuitBreakerConfig(failure_threshold=5))
|
|
85
86
|
.build()
|
|
86
87
|
)
|
|
88
|
+
```
|
|
87
89
|
"""
|
|
88
90
|
|
|
89
91
|
def __init__(self, name: str, *, version: str = "1.0.0") -> None:
|
|
@@ -408,6 +410,7 @@ class AgentBuilder:
|
|
|
408
410
|
Self for method chaining.
|
|
409
411
|
|
|
410
412
|
Example:
|
|
413
|
+
```python
|
|
411
414
|
builder.with_delegation_transport(my_transport).add_delegation_node(
|
|
412
415
|
name="delegate_analysis",
|
|
413
416
|
config=DelegationNodeConfig(
|
|
@@ -424,6 +427,7 @@ class AgentBuilder:
|
|
|
424
427
|
"transform_for_analyzer": lambda d: {"text": d["content"]},
|
|
425
428
|
},
|
|
426
429
|
)
|
|
430
|
+
```
|
|
427
431
|
"""
|
|
428
432
|
self._delegation_node_configs[name] = config
|
|
429
433
|
self._delegation_node_contracts[name] = contract
|
|
@@ -709,6 +713,7 @@ class AgentBuilder:
|
|
|
709
713
|
Self for method chaining.
|
|
710
714
|
|
|
711
715
|
Example:
|
|
716
|
+
```python
|
|
712
717
|
from sofias_sdk_lite.state import (
|
|
713
718
|
ConversationState,
|
|
714
719
|
InMemoryStateProvider,
|
|
@@ -717,6 +722,7 @@ class AgentBuilder:
|
|
|
717
722
|
builder.with_conversation_state(
|
|
718
723
|
ConversationState(InMemoryStateProvider())
|
|
719
724
|
)
|
|
725
|
+
```
|
|
720
726
|
"""
|
|
721
727
|
self._conversation_state = state
|
|
722
728
|
return self
|
|
@@ -47,6 +47,7 @@ class AgentConfig(BaseModel):
|
|
|
47
47
|
three-level configuration resolution: SDK > Agent > Node.
|
|
48
48
|
|
|
49
49
|
Example:
|
|
50
|
+
```python
|
|
50
51
|
config = AgentConfig(
|
|
51
52
|
name="inbox-assistant",
|
|
52
53
|
version="1.0.0",
|
|
@@ -56,6 +57,7 @@ class AgentConfig(BaseModel):
|
|
|
56
57
|
settings_class=InboxAssistantSettings,
|
|
57
58
|
llm=AgentLLMConfig(model="gpt-4o"),
|
|
58
59
|
)
|
|
60
|
+
```
|
|
59
61
|
"""
|
|
60
62
|
|
|
61
63
|
model_config = ConfigDict(frozen=True, arbitrary_types_allowed=True)
|
|
@@ -4,7 +4,8 @@ Middleware hooks are called before and after each node execution,
|
|
|
4
4
|
allowing logging, metrics, tracing, and input/output transformation
|
|
5
5
|
without modifying node code.
|
|
6
6
|
|
|
7
|
-
Example
|
|
7
|
+
Example:
|
|
8
|
+
```python
|
|
8
9
|
|
|
9
10
|
class MetricsMiddleware:
|
|
10
11
|
async def before_node(self, node_name, input_data):
|
|
@@ -24,6 +25,7 @@ Example::
|
|
|
24
25
|
.with_middleware(MetricsMiddleware())
|
|
25
26
|
.build()
|
|
26
27
|
)
|
|
28
|
+
```
|
|
27
29
|
"""
|
|
28
30
|
|
|
29
31
|
from __future__ import annotations
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/response_workflow.py
RENAMED
|
@@ -21,6 +21,7 @@ This module is transport-agnostic: it has no dependency on any specific
|
|
|
21
21
|
message broker. Wire it to whatever transport your application uses.
|
|
22
22
|
|
|
23
23
|
Example:
|
|
24
|
+
```python
|
|
24
25
|
class MyRabbitMQWorkflow:
|
|
25
26
|
async def send_response(
|
|
26
27
|
self,
|
|
@@ -38,6 +39,7 @@ Example:
|
|
|
38
39
|
.with_response_workflow(MyRabbitMQWorkflow())
|
|
39
40
|
.build()
|
|
40
41
|
)
|
|
42
|
+
```
|
|
41
43
|
"""
|
|
42
44
|
|
|
43
45
|
from __future__ import annotations
|
|
@@ -99,6 +101,7 @@ class StreamingResponseWorkflow(Protocol):
|
|
|
99
101
|
send_response() is still called at the end with the complete response.
|
|
100
102
|
|
|
101
103
|
Example:
|
|
104
|
+
```python
|
|
102
105
|
class MySSEWorkflow:
|
|
103
106
|
async def on_stream_event(
|
|
104
107
|
self,
|
|
@@ -113,6 +116,7 @@ class StreamingResponseWorkflow(Protocol):
|
|
|
113
116
|
context: ExecutionContext,
|
|
114
117
|
) -> None:
|
|
115
118
|
await self._sse_channel.send_final(response.model_dump_json())
|
|
119
|
+
```
|
|
116
120
|
"""
|
|
117
121
|
|
|
118
122
|
async def on_stream_event(
|
|
@@ -162,7 +166,8 @@ class BaseDelegationResponseWorkflow:
|
|
|
162
166
|
the ``result`` string. If *None*, the entire content dict is
|
|
163
167
|
serialized as JSON. Defaults to *None*.
|
|
164
168
|
|
|
165
|
-
Example
|
|
169
|
+
Example:
|
|
170
|
+
```python
|
|
166
171
|
|
|
167
172
|
async def publish(payload: dict) -> None:
|
|
168
173
|
await my_transport.publish_reply(reply_to, correlation_id, payload)
|
|
@@ -171,6 +176,7 @@ class BaseDelegationResponseWorkflow:
|
|
|
171
176
|
publish_fn=publish,
|
|
172
177
|
output_field="report",
|
|
173
178
|
)
|
|
179
|
+
```
|
|
174
180
|
"""
|
|
175
181
|
|
|
176
182
|
def __init__(
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/agent_settings.py
RENAMED
|
@@ -55,12 +55,13 @@ class BaseAgentSettings(AgentSettings):
|
|
|
55
55
|
variables), so a ``{api_key}`` placeholder can never inline a secret. Read
|
|
56
56
|
them at the point of use with ``.get_secret_value()``.
|
|
57
57
|
|
|
58
|
-
Example
|
|
59
|
-
|
|
58
|
+
Example:
|
|
59
|
+
```python
|
|
60
60
|
class MySettings(BaseAgentSettings):
|
|
61
61
|
CREDENTIAL_FIELDS = BaseAgentSettings.CREDENTIAL_FIELDS | {"search_api_key"}
|
|
62
62
|
|
|
63
63
|
search_api_key: SecretStr = SecretStr("")
|
|
64
|
+
```
|
|
64
65
|
"""
|
|
65
66
|
|
|
66
67
|
# --- LLM gateway (canonical platform keys) ---
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/config/runtime_config.py
RENAMED
|
@@ -38,11 +38,13 @@ class AgentSettings(BaseModel):
|
|
|
38
38
|
required and optional runtime configuration variables.
|
|
39
39
|
|
|
40
40
|
Example:
|
|
41
|
+
```python
|
|
41
42
|
class MyAgentSettings(AgentSettings):
|
|
42
43
|
reasoning_model: str # required
|
|
43
44
|
fast_model: str # required
|
|
44
45
|
max_retries: int = 3 # optional with default
|
|
45
46
|
temperature: float = 0.7 # optional with default
|
|
47
|
+
```
|
|
46
48
|
"""
|
|
47
49
|
|
|
48
50
|
model_config = ConfigDict(
|
|
@@ -85,6 +87,7 @@ class SettingsResolver(Generic[SettingsT]):
|
|
|
85
87
|
graph execution without explicit parameter passing.
|
|
86
88
|
|
|
87
89
|
Example:
|
|
90
|
+
```python
|
|
88
91
|
resolver = SettingsResolver(MyAgentSettings)
|
|
89
92
|
|
|
90
93
|
# Resolve from incoming message
|
|
@@ -98,6 +101,7 @@ class SettingsResolver(Generic[SettingsT]):
|
|
|
98
101
|
|
|
99
102
|
# Clear after execution
|
|
100
103
|
resolver.clear()
|
|
104
|
+
```
|
|
101
105
|
"""
|
|
102
106
|
|
|
103
107
|
def __init__(self, settings_class: type[SettingsT]) -> None:
|
|
@@ -73,10 +73,12 @@ class SDKConfig(BaseModel):
|
|
|
73
73
|
when setting up their agent. All values have sensible defaults.
|
|
74
74
|
|
|
75
75
|
Example:
|
|
76
|
+
```python
|
|
76
77
|
config = SDKConfig(
|
|
77
78
|
llm=LLMConfig(model="gpt-4o-mini"),
|
|
78
79
|
strict_validation=True,
|
|
79
80
|
)
|
|
81
|
+
```
|
|
80
82
|
"""
|
|
81
83
|
|
|
82
84
|
model_config = ConfigDict(frozen=True)
|
|
@@ -35,11 +35,13 @@ class ConfigSource(Protocol):
|
|
|
35
35
|
return type.
|
|
36
36
|
|
|
37
37
|
Example:
|
|
38
|
+
```python
|
|
38
39
|
class DatabaseConfigSource:
|
|
39
40
|
async def fetch(
|
|
40
41
|
self, agent_name: str, conversation_id: str | None = None
|
|
41
42
|
) -> dict[str, Any]:
|
|
42
43
|
return await my_db.get_agent_config(agent_name)
|
|
44
|
+
```
|
|
43
45
|
"""
|
|
44
46
|
|
|
45
47
|
async def fetch(self, agent_name: str, conversation_id: str | None = None) -> dict[str, Any]:
|
|
@@ -66,8 +68,10 @@ class StaticConfigSource:
|
|
|
66
68
|
fixed configuration applies to every agent and conversation.
|
|
67
69
|
|
|
68
70
|
Example:
|
|
71
|
+
```python
|
|
69
72
|
source = StaticConfigSource({"model_name": "gpt-4o-mini", "api_key": "..."})
|
|
70
73
|
config = await source.fetch("my_agent")
|
|
74
|
+
```
|
|
71
75
|
"""
|
|
72
76
|
|
|
73
77
|
def __init__(self, config: dict[str, Any]) -> None:
|
|
@@ -104,8 +108,10 @@ class EnvConfigSource:
|
|
|
104
108
|
export SOFIAS_AGENT_CONFIG='{"model_name": "gpt-4o-mini", "api_key": "sk-..."}'
|
|
105
109
|
|
|
106
110
|
Example:
|
|
111
|
+
```python
|
|
107
112
|
source = EnvConfigSource() # reads SOFIAS_AGENT_CONFIG
|
|
108
113
|
config = await source.fetch("my_agent")
|
|
114
|
+
```
|
|
109
115
|
"""
|
|
110
116
|
|
|
111
117
|
def __init__(self, env_var: str = "SOFIAS_AGENT_CONFIG") -> None:
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/agent_contracts.py
RENAMED
|
@@ -8,6 +8,7 @@ strongly-typed envelopes that carry domain data plus transport metadata.
|
|
|
8
8
|
- AgentResponse wraps the validated output with execution metadata.
|
|
9
9
|
|
|
10
10
|
Example:
|
|
11
|
+
```python
|
|
11
12
|
class MyInput(InputContract):
|
|
12
13
|
query: str
|
|
13
14
|
|
|
@@ -22,6 +23,7 @@ Example:
|
|
|
22
23
|
print(response.content) # validated output dict
|
|
23
24
|
print(response.execution_path) # ["classifier", "responder"]
|
|
24
25
|
print(response.execution_time_ms) # 1234.5
|
|
26
|
+
```
|
|
25
27
|
"""
|
|
26
28
|
|
|
27
29
|
from __future__ import annotations
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/base_contracts.py
RENAMED
|
@@ -6,6 +6,7 @@ a common protocol so that any delegating node knows exactly what to send and
|
|
|
6
6
|
what to expect back, without needing to know the internals of the target agent.
|
|
7
7
|
|
|
8
8
|
Example:
|
|
9
|
+
```python
|
|
9
10
|
# Agent A delegates to Agent B
|
|
10
11
|
request = DelegationRequest(
|
|
11
12
|
input="Summarize this document",
|
|
@@ -18,6 +19,7 @@ Example:
|
|
|
18
19
|
result="The document discusses...",
|
|
19
20
|
extras={"word_count": 150, "confidence": 0.95},
|
|
20
21
|
)
|
|
22
|
+
```
|
|
21
23
|
"""
|
|
22
24
|
|
|
23
25
|
from __future__ import annotations
|
|
@@ -153,12 +153,14 @@ class ErrorHandler:
|
|
|
153
153
|
callable provided by the agent.
|
|
154
154
|
|
|
155
155
|
Example:
|
|
156
|
+
```python
|
|
156
157
|
handler = ErrorHandler(config=config, store=store)
|
|
157
158
|
result = await handler.handle_node_execution(
|
|
158
159
|
node_name="processor",
|
|
159
160
|
execute_fn=node.execute,
|
|
160
161
|
input_data={"query": "hello"},
|
|
161
162
|
)
|
|
163
|
+
```
|
|
162
164
|
"""
|
|
163
165
|
|
|
164
166
|
def __init__(
|
|
@@ -332,6 +332,7 @@ class DelegationTarget(BaseModel):
|
|
|
332
332
|
the communication with a specific target agent.
|
|
333
333
|
|
|
334
334
|
Example:
|
|
335
|
+
```python
|
|
335
336
|
target = DelegationTarget(
|
|
336
337
|
agent_name="summarizer",
|
|
337
338
|
routing_key="agents.summarizer.tasks",
|
|
@@ -339,6 +340,7 @@ class DelegationTarget(BaseModel):
|
|
|
339
340
|
output_contract=SummaryOutput,
|
|
340
341
|
timeout_seconds=120,
|
|
341
342
|
)
|
|
343
|
+
```
|
|
342
344
|
|
|
343
345
|
.. note::
|
|
344
346
|
Unlike the internal platform, this SDK does **not** assume any
|
|
@@ -394,12 +396,14 @@ class DelegationStep(BaseModel):
|
|
|
394
396
|
on other steps. Used when dynamic targets are enabled.
|
|
395
397
|
|
|
396
398
|
Example:
|
|
399
|
+
```python
|
|
397
400
|
step = DelegationStep(
|
|
398
401
|
id="step_1",
|
|
399
402
|
agent_name="web-search",
|
|
400
403
|
input={"query": "Bitcoin price"},
|
|
401
404
|
depends_on=[],
|
|
402
405
|
)
|
|
406
|
+
```
|
|
403
407
|
"""
|
|
404
408
|
|
|
405
409
|
model_config = {"frozen": True}
|
|
@@ -445,6 +449,7 @@ class DelegationPlan(BaseModel):
|
|
|
445
449
|
delegation node running in DAG mode with dynamic targets.
|
|
446
450
|
|
|
447
451
|
Example:
|
|
452
|
+
```python
|
|
448
453
|
plan = DelegationPlan(
|
|
449
454
|
steps=[
|
|
450
455
|
DelegationStep(id="s1", agent_name="search", input={"q": "A"}),
|
|
@@ -452,6 +457,7 @@ class DelegationPlan(BaseModel):
|
|
|
452
457
|
DelegationStep(id="s3", agent_name="synthesizer", input={}, depends_on=["s1", "s2"]),
|
|
453
458
|
]
|
|
454
459
|
)
|
|
460
|
+
```
|
|
455
461
|
"""
|
|
456
462
|
|
|
457
463
|
model_config = {"frozen": True}
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/aggregator_config.py
RENAMED
|
@@ -19,6 +19,7 @@ class AggregatorNodeConfig(BaseModel):
|
|
|
19
19
|
to a configurable policy (all, any, majority).
|
|
20
20
|
|
|
21
21
|
Example:
|
|
22
|
+
```python
|
|
22
23
|
config = AggregatorNodeConfig(
|
|
23
24
|
name="collect_results",
|
|
24
25
|
description="Collects responses from all sub-agents",
|
|
@@ -26,6 +27,7 @@ class AggregatorNodeConfig(BaseModel):
|
|
|
26
27
|
timeout_seconds=120.0,
|
|
27
28
|
on_timeout="partial_result",
|
|
28
29
|
)
|
|
30
|
+
```
|
|
29
31
|
"""
|
|
30
32
|
|
|
31
33
|
model_config = ConfigDict(frozen=True)
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/aggregator_node.py
RENAMED
|
@@ -53,6 +53,7 @@ class AggregatorNode(BaseNode):
|
|
|
53
53
|
controlled by retry_timeout_seconds (or timeout_seconds if not set).
|
|
54
54
|
|
|
55
55
|
Example:
|
|
56
|
+
```python
|
|
56
57
|
config = AggregatorNodeConfig(
|
|
57
58
|
name="collect_results",
|
|
58
59
|
resolution_policy="all",
|
|
@@ -73,6 +74,7 @@ class AggregatorNode(BaseNode):
|
|
|
73
74
|
# "total_expected": 2,
|
|
74
75
|
# "total_received": 2,
|
|
75
76
|
# }
|
|
77
|
+
```
|
|
76
78
|
"""
|
|
77
79
|
|
|
78
80
|
def __init__(
|
|
@@ -50,10 +50,12 @@ class BaseNode(ABC):
|
|
|
50
50
|
- FunctionNode: Nodes that execute deterministic Python logic.
|
|
51
51
|
|
|
52
52
|
Example:
|
|
53
|
+
```python
|
|
53
54
|
class MyCustomNode(BaseNode):
|
|
54
55
|
async def _run(self, input_data: dict, context: dict | None = None) -> dict:
|
|
55
56
|
# Custom logic here
|
|
56
57
|
return {"result": "processed"}
|
|
58
|
+
```
|
|
57
59
|
"""
|
|
58
60
|
|
|
59
61
|
def __init__(
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/delegation_config.py
RENAMED
|
@@ -26,6 +26,7 @@ class DelegationTarget(BaseModel):
|
|
|
26
26
|
the communication with a specific target agent.
|
|
27
27
|
|
|
28
28
|
Example:
|
|
29
|
+
```python
|
|
29
30
|
target = DelegationTarget(
|
|
30
31
|
agent_name="summarizer",
|
|
31
32
|
routing_key="agent.summarizer",
|
|
@@ -33,6 +34,7 @@ class DelegationTarget(BaseModel):
|
|
|
33
34
|
output_contract=SummaryOutput,
|
|
34
35
|
timeout_seconds=120,
|
|
35
36
|
)
|
|
37
|
+
```
|
|
36
38
|
"""
|
|
37
39
|
|
|
38
40
|
model_config = ConfigDict(frozen=True)
|
|
@@ -69,12 +71,14 @@ class DelegationStep(BaseModel):
|
|
|
69
71
|
on other steps. Used when dynamic_targets is enabled.
|
|
70
72
|
|
|
71
73
|
Example:
|
|
74
|
+
```python
|
|
72
75
|
step = DelegationStep(
|
|
73
76
|
id="step_1",
|
|
74
77
|
agent_name="web-search",
|
|
75
78
|
input={"query": "Bitcoin price"},
|
|
76
79
|
depends_on=[],
|
|
77
80
|
)
|
|
81
|
+
```
|
|
78
82
|
"""
|
|
79
83
|
|
|
80
84
|
model_config = ConfigDict(frozen=True)
|
|
@@ -107,6 +111,7 @@ class DelegationPlan(BaseModel):
|
|
|
107
111
|
when execution_mode='dag' and dynamic_targets=True.
|
|
108
112
|
|
|
109
113
|
Example:
|
|
114
|
+
```python
|
|
110
115
|
plan = DelegationPlan(
|
|
111
116
|
steps=[
|
|
112
117
|
DelegationStep(id="s1", agent_name="search", input={"q": "A"}),
|
|
@@ -114,6 +119,7 @@ class DelegationPlan(BaseModel):
|
|
|
114
119
|
DelegationStep(id="s3", agent_name="synthesizer", input={}, depends_on=["s1", "s2"]),
|
|
115
120
|
]
|
|
116
121
|
)
|
|
122
|
+
```
|
|
117
123
|
"""
|
|
118
124
|
|
|
119
125
|
model_config = ConfigDict(frozen=True)
|
|
@@ -63,6 +63,7 @@ class FunctionNode(BaseNode):
|
|
|
63
63
|
return {"merged": ...}
|
|
64
64
|
|
|
65
65
|
Example:
|
|
66
|
+
```python
|
|
66
67
|
node = FunctionNode(
|
|
67
68
|
name="transformer",
|
|
68
69
|
contract=NodeContract(input_schema=RawInput, output_schema=FormattedOutput),
|
|
@@ -70,6 +71,7 @@ class FunctionNode(BaseNode):
|
|
|
70
71
|
)
|
|
71
72
|
result = await node.execute({"input": 5})
|
|
72
73
|
# result: {"value": 10}
|
|
74
|
+
```
|
|
73
75
|
"""
|
|
74
76
|
|
|
75
77
|
def __init__(
|
|
@@ -133,6 +133,7 @@ class LLMNode(BaseNode):
|
|
|
133
133
|
result.
|
|
134
134
|
|
|
135
135
|
Example:
|
|
136
|
+
```python
|
|
136
137
|
node = LLMNode(
|
|
137
138
|
config=node_config,
|
|
138
139
|
contract=NodeContract(input_schema=MyInput, output_schema=MyOutput),
|
|
@@ -140,6 +141,7 @@ class LLMNode(BaseNode):
|
|
|
140
141
|
tools=[tool1, tool2],
|
|
141
142
|
)
|
|
142
143
|
result = await node.execute({"query": "Hello"})
|
|
144
|
+
```
|
|
143
145
|
"""
|
|
144
146
|
|
|
145
147
|
def __init__(
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/llm_node_config.py
RENAMED
|
@@ -157,6 +157,7 @@ class LLMNodeConfig(BaseModel):
|
|
|
157
157
|
are optional and default to None, meaning "inherit from parent level".
|
|
158
158
|
|
|
159
159
|
Example:
|
|
160
|
+
```python
|
|
160
161
|
config = LLMNodeConfig(
|
|
161
162
|
name="classifier",
|
|
162
163
|
description="Classifies incoming emails",
|
|
@@ -168,6 +169,7 @@ class LLMNodeConfig(BaseModel):
|
|
|
168
169
|
template_variables={"categories": ["spam", "urgent", "normal"]},
|
|
169
170
|
),
|
|
170
171
|
)
|
|
172
|
+
```
|
|
171
173
|
"""
|
|
172
174
|
|
|
173
175
|
model_config = ConfigDict(frozen=True)
|
|
@@ -256,11 +258,13 @@ class FunctionNodeConfig(BaseModel):
|
|
|
256
258
|
without an LLM. No prompt, tool loop, or LLM settings are needed.
|
|
257
259
|
|
|
258
260
|
Example:
|
|
261
|
+
```python
|
|
259
262
|
config = FunctionNodeConfig(
|
|
260
263
|
name="data_merger",
|
|
261
264
|
description="Merges outputs from multiple upstream nodes",
|
|
262
265
|
retry_policy=RetryPolicy(max_retries=2),
|
|
263
266
|
)
|
|
267
|
+
```
|
|
264
268
|
"""
|
|
265
269
|
|
|
266
270
|
model_config = ConfigDict(frozen=True)
|
|
@@ -38,6 +38,7 @@ class PlannerNode(BaseNode):
|
|
|
38
38
|
routes the output to PlanExecutor for execution.
|
|
39
39
|
|
|
40
40
|
Example:
|
|
41
|
+
```python
|
|
41
42
|
planner = PlannerNode(
|
|
42
43
|
name="planner",
|
|
43
44
|
contract=planner_contract,
|
|
@@ -47,6 +48,7 @@ class PlannerNode(BaseNode):
|
|
|
47
48
|
NodeDescriptor(name="summarize", node_type=NodeType.LLM, description="Summarize text"),
|
|
48
49
|
],
|
|
49
50
|
)
|
|
51
|
+
```
|
|
50
52
|
"""
|
|
51
53
|
|
|
52
54
|
def __init__(
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/prompt_assembler.py
RENAMED
|
@@ -33,12 +33,14 @@ class PromptAssembler:
|
|
|
33
33
|
variables merged with runtime variables (runtime takes precedence).
|
|
34
34
|
|
|
35
35
|
Example:
|
|
36
|
+
```python
|
|
36
37
|
assembler = PromptAssembler(
|
|
37
38
|
config=node_config,
|
|
38
39
|
tools=[tool_spec_1, tool_spec_2],
|
|
39
40
|
output_contract=MyOutputContract,
|
|
40
41
|
)
|
|
41
42
|
prompt = assembler.assemble(runtime_vars={"user_name": "Alice"})
|
|
43
|
+
```
|
|
42
44
|
"""
|
|
43
45
|
|
|
44
46
|
def __init__(
|
|
@@ -134,6 +134,7 @@ class EventAdapter:
|
|
|
134
134
|
- Error handling and logging
|
|
135
135
|
|
|
136
136
|
Example:
|
|
137
|
+
```python
|
|
137
138
|
publisher = RabbitMQPublisher(connection)
|
|
138
139
|
listener = RabbitMQListener(connection)
|
|
139
140
|
events = EventAdapter(publisher, listener)
|
|
@@ -151,6 +152,7 @@ class EventAdapter:
|
|
|
151
152
|
agent_name="inbox_assist",
|
|
152
153
|
handler=my_handler,
|
|
153
154
|
)
|
|
155
|
+
```
|
|
154
156
|
"""
|
|
155
157
|
|
|
156
158
|
def __init__(
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/tracing.py
RENAMED
|
@@ -215,6 +215,7 @@ class TracingAdapter:
|
|
|
215
215
|
- No-op behavior when provider is None
|
|
216
216
|
|
|
217
217
|
Example:
|
|
218
|
+
```python
|
|
218
219
|
provider = OTelTracingProvider("my-agent-service")
|
|
219
220
|
tracing = TracingAdapter(provider)
|
|
220
221
|
|
|
@@ -226,6 +227,7 @@ class TracingAdapter:
|
|
|
226
227
|
# Trace node execution
|
|
227
228
|
with tracing.trace_node_execution("classifier", input_data) as span:
|
|
228
229
|
result = await node.execute(input_data)
|
|
230
|
+
```
|
|
229
231
|
"""
|
|
230
232
|
|
|
231
233
|
def __init__(self, provider: TracingProvider | None = None) -> None:
|
|
@@ -298,9 +300,11 @@ class TracingAdapter:
|
|
|
298
300
|
The span for adding events and attributes.
|
|
299
301
|
|
|
300
302
|
Example:
|
|
303
|
+
```python
|
|
301
304
|
with tracing.trace_agent_execution("my_agent", "1.0.0") as span:
|
|
302
305
|
span.set_attribute("input.type", "email")
|
|
303
306
|
response = agent.execute(message)
|
|
307
|
+
```
|
|
304
308
|
"""
|
|
305
309
|
attributes = {
|
|
306
310
|
"agent.name": agent_name,
|
|
@@ -27,7 +27,8 @@ class RabbitMQConsumer:
|
|
|
27
27
|
The handler receives a :class:`MessageContext` with the deserialized
|
|
28
28
|
payload, AMQP metadata, and ack/nack helpers.
|
|
29
29
|
|
|
30
|
-
Example
|
|
30
|
+
Example:
|
|
31
|
+
```python
|
|
31
32
|
|
|
32
33
|
async with RabbitMQClient(config) as client:
|
|
33
34
|
consumer = RabbitMQConsumer(
|
|
@@ -40,6 +41,7 @@ class RabbitMQConsumer:
|
|
|
40
41
|
await asyncio.Event().wait()
|
|
41
42
|
except asyncio.CancelledError:
|
|
42
43
|
await consumer.stop()
|
|
44
|
+
```
|
|
43
45
|
"""
|
|
44
46
|
|
|
45
47
|
def __init__(
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/rabbitmq/delegation_transport.py
RENAMED
|
@@ -38,6 +38,7 @@ class RabbitMQDelegationTransport:
|
|
|
38
38
|
- Responses arriving before wait_* are buffered, not lost
|
|
39
39
|
|
|
40
40
|
Example:
|
|
41
|
+
```python
|
|
41
42
|
client = RabbitMQClient(config)
|
|
42
43
|
await client.connect()
|
|
43
44
|
|
|
@@ -65,6 +66,7 @@ class RabbitMQDelegationTransport:
|
|
|
65
66
|
print(f"{cid} responded with: {response}")
|
|
66
67
|
|
|
67
68
|
await client.disconnect()
|
|
69
|
+
```
|
|
68
70
|
"""
|
|
69
71
|
|
|
70
72
|
def __init__(
|
|
@@ -38,6 +38,7 @@ class RabbitMQRPCClient:
|
|
|
38
38
|
3. Waits for responses matching the correlation_id
|
|
39
39
|
|
|
40
40
|
Example:
|
|
41
|
+
```python
|
|
41
42
|
client = RabbitMQClient(config)
|
|
42
43
|
await client.connect()
|
|
43
44
|
|
|
@@ -49,6 +50,7 @@ class RabbitMQRPCClient:
|
|
|
49
50
|
)
|
|
50
51
|
|
|
51
52
|
await client.disconnect()
|
|
53
|
+
```
|
|
52
54
|
"""
|
|
53
55
|
|
|
54
56
|
def __init__(
|
|
@@ -31,6 +31,7 @@ class Router:
|
|
|
31
31
|
graph. Execution is handled by the agent (Phase 5).
|
|
32
32
|
|
|
33
33
|
Example:
|
|
34
|
+
```python
|
|
34
35
|
router = Router()
|
|
35
36
|
router.add_route(
|
|
36
37
|
"classifier",
|
|
@@ -47,6 +48,7 @@ class Router:
|
|
|
47
48
|
# Later, during execution:
|
|
48
49
|
next_node = router.resolve("classifier", {"category": "urgent"})
|
|
49
50
|
# Returns "priority_handler"
|
|
51
|
+
```
|
|
50
52
|
"""
|
|
51
53
|
|
|
52
54
|
def __init__(self) -> None:
|
|
@@ -57,6 +57,7 @@ class FieldValueStrategy:
|
|
|
57
57
|
outputs where different categories lead to different processing paths.
|
|
58
58
|
|
|
59
59
|
Example:
|
|
60
|
+
```python
|
|
60
61
|
strategy = FieldValueStrategy(
|
|
61
62
|
field="category",
|
|
62
63
|
mapping={"urgent": "priority_handler", "spam": "discard"},
|
|
@@ -65,6 +66,7 @@ class FieldValueStrategy:
|
|
|
65
66
|
# If output["category"] == "urgent" -> "priority_handler"
|
|
66
67
|
# If output["category"] == "spam" -> "discard"
|
|
67
68
|
# If output["category"] == "other" -> "normal_handler" (default)
|
|
69
|
+
```
|
|
68
70
|
"""
|
|
69
71
|
|
|
70
72
|
def __init__(
|
|
@@ -127,6 +129,7 @@ class ConfidenceThresholdStrategy:
|
|
|
127
129
|
leads to automated processing and low confidence requires human review.
|
|
128
130
|
|
|
129
131
|
Example:
|
|
132
|
+
```python
|
|
130
133
|
strategy = ConfidenceThresholdStrategy(
|
|
131
134
|
field="confidence",
|
|
132
135
|
threshold=0.8,
|
|
@@ -135,6 +138,7 @@ class ConfidenceThresholdStrategy:
|
|
|
135
138
|
)
|
|
136
139
|
# If output["confidence"] >= 0.8 -> "auto_respond"
|
|
137
140
|
# If output["confidence"] < 0.8 -> "human_review"
|
|
141
|
+
```
|
|
138
142
|
"""
|
|
139
143
|
|
|
140
144
|
def __init__(
|
|
@@ -199,6 +203,7 @@ class FieldPresenceStrategy:
|
|
|
199
203
|
"present" if it exists, is not None, and is not empty (for collections).
|
|
200
204
|
|
|
201
205
|
Example:
|
|
206
|
+
```python
|
|
202
207
|
strategy = FieldPresenceStrategy(
|
|
203
208
|
field="tool_calls",
|
|
204
209
|
present="tool_executor",
|
|
@@ -206,6 +211,7 @@ class FieldPresenceStrategy:
|
|
|
206
211
|
)
|
|
207
212
|
# If output["tool_calls"] has content -> "tool_executor"
|
|
208
213
|
# If output["tool_calls"] is None/empty -> "final_response"
|
|
214
|
+
```
|
|
209
215
|
"""
|
|
210
216
|
|
|
211
217
|
def __init__(
|
|
@@ -270,12 +276,14 @@ class ConditionalStrategy:
|
|
|
270
276
|
and returns the target node name.
|
|
271
277
|
|
|
272
278
|
Example:
|
|
279
|
+
```python
|
|
273
280
|
def custom_router(output: dict) -> str:
|
|
274
281
|
if output["score"] > 0.9 and output["verified"]:
|
|
275
282
|
return "premium_handler"
|
|
276
283
|
return "standard_handler"
|
|
277
284
|
|
|
278
285
|
strategy = ConditionalStrategy(condition=custom_router)
|
|
286
|
+
```
|
|
279
287
|
"""
|
|
280
288
|
|
|
281
289
|
def __init__(
|
|
@@ -325,12 +333,14 @@ class FanOutStrategy:
|
|
|
325
333
|
collects the results after all parallel branches complete.
|
|
326
334
|
|
|
327
335
|
Example:
|
|
336
|
+
```python
|
|
328
337
|
strategy = FanOutStrategy(
|
|
329
338
|
targets=["sentiment", "entities", "summary"],
|
|
330
339
|
join_node="merger",
|
|
331
340
|
)
|
|
332
341
|
# Dispatches to all three nodes in parallel.
|
|
333
342
|
# After all complete, execution continues at "merger".
|
|
343
|
+
```
|
|
334
344
|
"""
|
|
335
345
|
|
|
336
346
|
def __init__(
|
|
@@ -402,6 +412,7 @@ class CompositeStrategy:
|
|
|
402
412
|
default.
|
|
403
413
|
|
|
404
414
|
Example:
|
|
415
|
+
```python
|
|
405
416
|
strategy = CompositeStrategy(
|
|
406
417
|
strategies=[
|
|
407
418
|
FieldPresenceStrategy("error", "error_handler", None),
|
|
@@ -409,6 +420,7 @@ class CompositeStrategy:
|
|
|
409
420
|
],
|
|
410
421
|
default="fallback",
|
|
411
422
|
)
|
|
423
|
+
```
|
|
412
424
|
"""
|
|
413
425
|
|
|
414
426
|
def __init__(
|
|
@@ -455,8 +467,10 @@ class StaticRoute:
|
|
|
455
467
|
For conditional routing, use FieldValueStrategy or ConditionalStrategy.
|
|
456
468
|
|
|
457
469
|
Example:
|
|
470
|
+
```python
|
|
458
471
|
strategy = StaticRoute("responder")
|
|
459
472
|
# output is ignored — always returns "responder"
|
|
473
|
+
```
|
|
460
474
|
"""
|
|
461
475
|
|
|
462
476
|
def __init__(self, target: str) -> None:
|
|
@@ -4,7 +4,8 @@ Subclass and implement:
|
|
|
4
4
|
- build_agent(settings, workflow) -> Agent
|
|
5
5
|
- prepare_input(task, history, role) -> AgentMessage
|
|
6
6
|
|
|
7
|
-
Example
|
|
7
|
+
Example:
|
|
8
|
+
```python
|
|
8
9
|
|
|
9
10
|
class MyAgentRunner(AgentRunner):
|
|
10
11
|
settings_class = MySettings
|
|
@@ -30,6 +31,7 @@ Example::
|
|
|
30
31
|
agent_name="my_agent",
|
|
31
32
|
rabbitmq=RabbitMQConfig(host="localhost"),
|
|
32
33
|
)).run()
|
|
34
|
+
```
|
|
33
35
|
"""
|
|
34
36
|
|
|
35
37
|
from __future__ import annotations
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/state/conversation_state.py
RENAMED
|
@@ -105,12 +105,14 @@ class ConversationStateAdapter:
|
|
|
105
105
|
(``raise_on_error=False``).
|
|
106
106
|
|
|
107
107
|
Example:
|
|
108
|
+
```python
|
|
108
109
|
provider = InMemoryStateProvider()
|
|
109
110
|
state = ConversationStateAdapter(provider)
|
|
110
111
|
|
|
111
112
|
await state.set("conv-123", "validation:doc1", {"questions": [...]})
|
|
112
113
|
data = await state.get("conv-123", "validation:doc1")
|
|
113
114
|
await state.delete("conv-123", "validation:doc1")
|
|
115
|
+
```
|
|
114
116
|
"""
|
|
115
117
|
|
|
116
118
|
def __init__(
|
|
@@ -221,11 +223,13 @@ class InMemoryStateProvider:
|
|
|
221
223
|
(state is lost on process restart).
|
|
222
224
|
|
|
223
225
|
Example:
|
|
226
|
+
```python
|
|
224
227
|
provider = InMemoryStateProvider()
|
|
225
228
|
await provider.set("conv-1", "key-a", {"foo": "bar"})
|
|
226
229
|
data = await provider.get("conv-1", "key-a") # {"foo": "bar"}
|
|
227
230
|
await provider.delete("conv-1", "key-a")
|
|
228
231
|
data = await provider.get("conv-1", "key-a") # None
|
|
232
|
+
```
|
|
229
233
|
"""
|
|
230
234
|
|
|
231
235
|
def __init__(self) -> None:
|
|
@@ -114,9 +114,11 @@ class InMemoryHistory:
|
|
|
114
114
|
(history is lost on process restart).
|
|
115
115
|
|
|
116
116
|
Example:
|
|
117
|
+
```python
|
|
117
118
|
history = InMemoryHistory()
|
|
118
119
|
await history.append("conv-1", Message(role="user", content="hi"))
|
|
119
120
|
messages = await history.get("conv-1") # [Message(role="user", ...)]
|
|
121
|
+
```
|
|
120
122
|
"""
|
|
121
123
|
|
|
122
124
|
def __init__(self) -> None:
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/agent/execution_context.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/node_contracts.py
RENAMED
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/contracts/strict_contract.py
RENAMED
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/errors/circuit_breaker.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
@@ -232,6 +232,14 @@ def create_llm(
|
|
|
232
232
|
"reasoning_effort": reasoning_effort,
|
|
233
233
|
},
|
|
234
234
|
)
|
|
235
|
+
if not config.base_url.strip():
|
|
236
|
+
raise LLMConfigurationError(
|
|
237
|
+
f"No LLM gateway URL configured for model '{config.model}'. On the Sofias "
|
|
238
|
+
f"platform {ENV_LLM_BASE_URL} is injected automatically; to run locally, "
|
|
239
|
+
"export it or install a fake LLM with default_llm(...).",
|
|
240
|
+
missing=["base_url"],
|
|
241
|
+
)
|
|
242
|
+
|
|
235
243
|
if not config.api_key.get_secret_value():
|
|
236
244
|
logger.warning(
|
|
237
245
|
"LLM gateway configured without an API key; requests will be unauthenticated",
|
|
@@ -251,14 +259,6 @@ def create_llm(
|
|
|
251
259
|
if config.temperature is not None:
|
|
252
260
|
common["temperature"] = config.temperature
|
|
253
261
|
|
|
254
|
-
if not config.base_url.strip():
|
|
255
|
-
raise LLMConfigurationError(
|
|
256
|
-
f"No LLM gateway URL configured for model '{config.model}'. On the Sofias "
|
|
257
|
-
f"platform {ENV_LLM_BASE_URL} is injected automatically; to run locally, "
|
|
258
|
-
"export it or install a fake LLM with default_llm(...).",
|
|
259
|
-
missing=["base_url"],
|
|
260
|
-
)
|
|
261
|
-
|
|
262
262
|
provider_name = config.provider.lower()
|
|
263
263
|
if provider_name == PROVIDER_GATEWAY:
|
|
264
264
|
return GatewayLLM(reasoning_effort=config.reasoning_effort, **common)
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/llm/openai_compatible.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/delegation_node.py
RENAMED
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/delegation_transport.py
RENAMED
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/nodes/planning_models.py
RENAMED
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/observability/trace_context.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sofias_sdk_lite-0.2.0 → sofias_sdk_lite-0.2.1}/src/sofias_sdk_lite/workflows/streaming_chat.py
RENAMED
|
File without changes
|