aip-agents-binary 0.4.8__cp312-cp312-win_amd64.whl → 0.5.4__cp312-cp312-win_amd64.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.
- aip_agents/__init__.pyi +19 -0
- aip_agents/a2a/__init__.pyi +1 -1
- aip_agents/a2a/server/base_executor.pyi +6 -6
- aip_agents/a2a/server/google_adk_executor.pyi +11 -11
- aip_agents/a2a/server/langflow_executor.pyi +43 -0
- aip_agents/a2a/server/langgraph_executor.pyi +10 -11
- aip_agents/a2a/types.pyi +54 -47
- aip_agents/agent/__init__.pyi +3 -1
- aip_agents/agent/base_agent.pyi +24 -8
- aip_agents/agent/base_langgraph_agent.pyi +67 -25
- aip_agents/agent/google_adk_agent.pyi +34 -21
- aip_agents/agent/google_adk_constants.pyi +3 -0
- aip_agents/agent/hitl/__init__.pyi +6 -0
- aip_agents/agent/hitl/config.pyi +15 -0
- aip_agents/agent/hitl/langgraph_hitl_mixin.pyi +42 -0
- aip_agents/agent/hitl/manager.pyi +199 -0
- aip_agents/agent/hitl/models.pyi +3 -0
- aip_agents/agent/hitl/prompt/__init__.pyi +4 -0
- aip_agents/agent/hitl/prompt/base.pyi +24 -0
- aip_agents/agent/hitl/prompt/deferred.pyi +30 -0
- aip_agents/agent/interface.pyi +5 -5
- aip_agents/agent/interfaces.pyi +44 -0
- aip_agents/agent/langflow_agent.pyi +133 -0
- aip_agents/agent/langgraph_memory_enhancer_agent.pyi +49 -0
- aip_agents/agent/langgraph_react_agent.pyi +50 -57
- aip_agents/agent/system_instruction_context.pyi +13 -0
- aip_agents/clients/__init__.pyi +4 -0
- aip_agents/clients/langflow/__init__.pyi +4 -0
- aip_agents/clients/langflow/client.pyi +140 -0
- aip_agents/clients/langflow/types.pyi +7 -0
- aip_agents/constants.pyi +1 -0
- aip_agents/examples/compare_streaming_client.pyi +48 -0
- aip_agents/examples/compare_streaming_server.pyi +18 -0
- aip_agents/examples/demo_memory_recall.pyi +58 -0
- aip_agents/examples/hello_world_a2a_google_adk_client.pyi +2 -2
- aip_agents/examples/hello_world_a2a_google_adk_client_agent.pyi +2 -2
- aip_agents/examples/hello_world_a2a_google_adk_client_streaming.pyi +2 -2
- aip_agents/examples/hello_world_a2a_google_adk_server.pyi +7 -2
- aip_agents/examples/hello_world_a2a_langchain_client.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langchain_client_agent.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langchain_client_lm_invoker.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langchain_client_streaming.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langchain_reference_client_streaming.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langchain_reference_server.pyi +8 -3
- aip_agents/examples/hello_world_a2a_langchain_server.pyi +7 -2
- aip_agents/examples/hello_world_a2a_langchain_server_lm_invoker.pyi +7 -2
- aip_agents/examples/hello_world_a2a_langflow_client.pyi +9 -0
- aip_agents/examples/hello_world_a2a_langflow_server.pyi +14 -0
- aip_agents/examples/hello_world_a2a_langgraph_artifact_client.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langgraph_artifact_client_streaming.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langgraph_artifact_server.pyi +7 -2
- aip_agents/examples/hello_world_a2a_langgraph_client.pyi +2 -2
- aip_agents/examples/hello_world_a2a_langgraph_client_agent.pyi +2 -2
- aip_agents/examples/hello_world_a2a_langgraph_client_agent_lm_invoker.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langgraph_client_streaming.pyi +3 -3
- aip_agents/examples/hello_world_a2a_langgraph_client_streaming_lm_invoker.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langgraph_client_streaming_tool_streaming.pyi +1 -1
- aip_agents/examples/hello_world_a2a_langgraph_server.pyi +7 -2
- aip_agents/examples/hello_world_a2a_langgraph_server_lm_invoker.pyi +7 -2
- aip_agents/examples/hello_world_a2a_langgraph_server_tool_streaming.pyi +7 -2
- aip_agents/examples/hello_world_a2a_mcp_langgraph.pyi +1 -1
- aip_agents/examples/hello_world_a2a_three_level_agent_hierarchy_client.pyi +31 -6
- aip_agents/examples/hello_world_a2a_three_level_agent_hierarchy_server.pyi +33 -5
- aip_agents/examples/hello_world_a2a_with_metadata_langchain_client.pyi +1 -1
- aip_agents/examples/hello_world_a2a_with_metadata_langchain_server_lm_invoker.pyi +7 -2
- aip_agents/examples/hello_world_langchain_mcp_http_interactive.pyi +16 -0
- aip_agents/examples/hello_world_langchain_mcp_multi_server.pyi +18 -0
- aip_agents/examples/hello_world_langflow_agent.pyi +35 -0
- aip_agents/examples/hello_world_model_switch_cli.pyi +18 -3
- aip_agents/examples/hello_world_pii_logger.pyi +1 -1
- aip_agents/examples/hello_world_sentry.pyi +1 -1
- aip_agents/examples/hello_world_step_limits.pyi +17 -0
- aip_agents/examples/hello_world_stock_a2a_server.pyi +7 -2
- aip_agents/examples/hello_world_tool_output_client.pyi +1 -1
- aip_agents/examples/hello_world_tool_output_server.pyi +7 -2
- aip_agents/examples/hitl_demo.pyi +67 -0
- aip_agents/examples/pii_demo_langgraph_client.pyi +5 -0
- aip_agents/examples/pii_demo_langgraph_server.pyi +20 -0
- aip_agents/examples/pii_demo_multi_agent_client.pyi +5 -0
- aip_agents/examples/pii_demo_multi_agent_server.pyi +40 -0
- aip_agents/examples/todolist_planning_a2a_langchain_client.pyi +5 -0
- aip_agents/examples/todolist_planning_a2a_langgraph_server.pyi +19 -0
- aip_agents/examples/tools/__init__.pyi +3 -1
- aip_agents/examples/tools/adk_weather_tool.pyi +1 -1
- aip_agents/examples/tools/data_visualization_tool.pyi +2 -0
- aip_agents/examples/tools/image_artifact_tool.pyi +2 -0
- aip_agents/examples/tools/langchain_arithmetic_tools.pyi +7 -0
- aip_agents/examples/tools/langchain_currency_exchange_tool.pyi +0 -1
- aip_agents/examples/tools/langchain_graph_artifact_tool.pyi +2 -0
- aip_agents/examples/tools/langchain_weather_tool.pyi +1 -1
- aip_agents/examples/tools/langgraph_streaming_tool.pyi +1 -1
- aip_agents/examples/tools/mock_retrieval_tool.pyi +13 -0
- aip_agents/examples/tools/pii_demo_tools.pyi +54 -0
- aip_agents/examples/tools/random_chart_tool.pyi +20 -0
- aip_agents/examples/tools/stock_tools.pyi +18 -3
- aip_agents/mcp/client/__init__.pyi +4 -3
- aip_agents/mcp/client/base_mcp_client.pyi +148 -0
- aip_agents/mcp/client/connection_manager.pyi +48 -0
- aip_agents/mcp/client/google_adk/__init__.pyi +1 -1
- aip_agents/mcp/client/google_adk/client.pyi +50 -13
- aip_agents/mcp/client/langchain/__init__.pyi +1 -1
- aip_agents/mcp/client/langchain/client.pyi +47 -2
- aip_agents/mcp/client/persistent_session.pyi +113 -0
- aip_agents/mcp/client/session_pool.pyi +101 -0
- aip_agents/mcp/client/transports.pyi +123 -0
- aip_agents/mcp/utils/__init__.pyi +0 -0
- aip_agents/mcp/utils/config_validator.pyi +82 -0
- aip_agents/memory/adapters/__init__.pyi +4 -0
- aip_agents/memory/adapters/base_adapter.pyi +150 -0
- aip_agents/memory/adapters/mem0.pyi +22 -0
- aip_agents/memory/base.pyi +3 -3
- aip_agents/memory/constants.pyi +9 -0
- aip_agents/memory/factory.pyi +1 -1
- aip_agents/memory/guidance.pyi +3 -0
- aip_agents/middleware/__init__.pyi +5 -0
- aip_agents/middleware/base.pyi +71 -0
- aip_agents/middleware/manager.pyi +80 -0
- aip_agents/middleware/todolist.pyi +125 -0
- aip_agents/schema/__init__.pyi +9 -0
- aip_agents/schema/a2a.pyi +40 -0
- aip_agents/schema/agent.pyi +65 -0
- aip_agents/schema/hitl.pyi +89 -0
- aip_agents/schema/langgraph.pyi +28 -0
- aip_agents/schema/model_id.pyi +54 -0
- aip_agents/schema/step_limit.pyi +63 -0
- aip_agents/schema/storage.pyi +21 -0
- aip_agents/sentry/__init__.pyi +1 -1
- aip_agents/sentry/sentry.pyi +2 -2
- aip_agents/storage/base.pyi +1 -2
- aip_agents/storage/config.pyi +9 -46
- aip_agents/storage/providers/base.pyi +2 -3
- aip_agents/storage/providers/object_storage.pyi +1 -1
- aip_agents/tools/__init__.pyi +1 -1
- aip_agents/tools/bosa_tools.pyi +2 -2
- aip_agents/tools/constants.pyi +105 -100
- aip_agents/tools/memory_search/__init__.pyi +5 -0
- aip_agents/tools/memory_search/base.pyi +69 -0
- aip_agents/tools/memory_search/mem0.pyi +19 -0
- aip_agents/tools/memory_search/schema.pyi +15 -0
- aip_agents/tools/memory_search_tool.pyi +3 -0
- aip_agents/types/__init__.pyi +19 -3
- aip_agents/types/a2a_events.pyi +2 -73
- aip_agents/utils/__init__.pyi +7 -2
- aip_agents/utils/a2a_connector.pyi +14 -4
- aip_agents/utils/artifact_helpers.pyi +26 -2
- aip_agents/utils/constants.pyi +10 -0
- aip_agents/utils/datetime/__init__.pyi +4 -0
- aip_agents/utils/datetime/normalization.pyi +95 -0
- aip_agents/utils/datetime/timezone.pyi +48 -0
- aip_agents/utils/env_loader.pyi +2 -2
- aip_agents/utils/event_handler_registry.pyi +23 -0
- aip_agents/utils/final_response_builder.pyi +34 -0
- aip_agents/utils/formatter_llm_client.pyi +71 -0
- aip_agents/utils/langgraph/converter.pyi +1 -1
- aip_agents/utils/langgraph/tool_managers/a2a_tool_manager.pyi +2 -2
- aip_agents/utils/langgraph/tool_managers/base_tool_manager.pyi +2 -3
- aip_agents/utils/langgraph/tool_managers/delegation_tool_manager.pyi +14 -8
- aip_agents/utils/langgraph/tool_output_management.pyi +15 -2
- aip_agents/utils/logger.pyi +60 -0
- aip_agents/utils/metadata/__init__.pyi +5 -0
- aip_agents/utils/metadata/activity_metadata_helper.pyi +25 -0
- aip_agents/utils/metadata/activity_narrative/__init__.pyi +7 -0
- aip_agents/utils/metadata/activity_narrative/builder.pyi +35 -0
- aip_agents/utils/metadata/activity_narrative/constants.pyi +10 -0
- aip_agents/utils/metadata/activity_narrative/context.pyi +32 -0
- aip_agents/utils/metadata/activity_narrative/formatters.pyi +48 -0
- aip_agents/utils/metadata/activity_narrative/utils.pyi +12 -0
- aip_agents/utils/metadata/schemas/__init__.pyi +4 -0
- aip_agents/utils/metadata/schemas/activity_schema.pyi +18 -0
- aip_agents/utils/metadata/schemas/thinking_schema.pyi +20 -0
- aip_agents/utils/metadata/thinking_metadata_helper.pyi +4 -0
- aip_agents/utils/metadata_helper.pyi +50 -34
- aip_agents/utils/name_preprocessor/base_name_preprocessor.pyi +1 -2
- aip_agents/utils/name_preprocessor/google_name_preprocessor.pyi +1 -1
- aip_agents/utils/name_preprocessor/name_preprocessor.pyi +4 -4
- aip_agents/utils/name_preprocessor/openai_name_preprocessor.pyi +1 -1
- aip_agents/utils/pii/__init__.pyi +5 -0
- aip_agents/utils/pii/pii_handler.pyi +86 -0
- aip_agents/utils/pii/pii_helper.pyi +69 -0
- aip_agents/utils/pii/uuid_deanonymizer_mapping.pyi +62 -0
- aip_agents/utils/reference_helper.pyi +38 -6
- aip_agents/utils/sse_chunk_transformer.pyi +166 -0
- aip_agents/utils/step_limit_manager.pyi +112 -0
- aip_agents/utils/token_usage_helper.pyi +1 -1
- aip_agents.cp312-win_amd64.pyd +0 -0
- aip_agents.pyi +92 -34
- aip_agents_binary-0.5.4.dist-info/METADATA +649 -0
- aip_agents_binary-0.5.4.dist-info/RECORD +242 -0
- {aip_agents_binary-0.4.8.dist-info → aip_agents_binary-0.5.4.dist-info}/WHEEL +2 -1
- aip_agents_binary-0.5.4.dist-info/top_level.txt +1 -0
- aip_agents/agent/types.pyi +0 -109
- aip_agents/examples/hello_world_a2a_mem0_coordinator_client.pyi +0 -14
- aip_agents/examples/hello_world_a2a_mem0_coordinator_server.pyi +0 -10
- aip_agents/examples/hello_world_a2a_multi_agent_coordinator_client.pyi +0 -19
- aip_agents/examples/hello_world_a2a_multi_agent_coordinator_client_streaming.pyi +0 -9
- aip_agents/examples/hello_world_a2a_multi_agent_coordinator_server.pyi +0 -12
- aip_agents/examples/hello_world_langgraph_bosa.pyi +0 -5
- aip_agents/examples/hello_world_mem0_coordinator.pyi +0 -5
- aip_agents/examples/tools/pr_details_bosa_tool.pyi +0 -26
- aip_agents/memory/mem0_memory.pyi +0 -94
- aip_agents/tools/base.pyi +0 -44
- aip_agents/tools/base_bosa_tools.pyi +0 -12
- aip_agents/tools/bosa_connector.pyi +0 -30
- aip_agents/tools/bosa_tools_interface.pyi +0 -26
- aip_agents/utils/logger_manager.pyi +0 -151
- aip_agents.build/.gitignore +0 -1
- aip_agents_binary-0.4.8.dist-info/METADATA +0 -280
- aip_agents_binary-0.4.8.dist-info/RECORD +0 -166
|
@@ -1,18 +1,19 @@
|
|
|
1
1
|
from _typeshed import Incomplete
|
|
2
|
-
from a2a.types import AgentCard
|
|
2
|
+
from a2a.types import AgentCard
|
|
3
3
|
from aip_agents.agent.base_agent import BaseAgent as BaseAgent
|
|
4
|
-
from aip_agents.
|
|
4
|
+
from aip_agents.agent.google_adk_constants import DEFAULT_AUTH_URL as DEFAULT_AUTH_URL
|
|
5
|
+
from aip_agents.mcp.client.google_adk.client import GoogleADKMCPClient as GoogleADKMCPClient
|
|
5
6
|
from aip_agents.utils.a2a_connector import A2AConnector as A2AConnector
|
|
6
|
-
from aip_agents.utils.
|
|
7
|
+
from aip_agents.utils.logger import get_logger as get_logger
|
|
8
|
+
from collections.abc import AsyncGenerator, AsyncIterator
|
|
7
9
|
from google.adk.agents import LlmAgent
|
|
8
10
|
from google.adk.tools.langchain_tool import LangchainTool
|
|
9
11
|
from langchain.tools import BaseTool as LangchainBaseTool
|
|
10
12
|
from pydantic import BaseModel
|
|
11
|
-
from typing import Any
|
|
13
|
+
from typing import Any
|
|
12
14
|
|
|
13
15
|
logger: Incomplete
|
|
14
16
|
MODEL_TEMPERATURE: float
|
|
15
|
-
DEFAULT_AUTH_URL: str
|
|
16
17
|
|
|
17
18
|
class A2AToolInput(BaseModel):
|
|
18
19
|
"""Input for the A2ATool."""
|
|
@@ -26,14 +27,28 @@ class A2ATool(LangchainBaseTool):
|
|
|
26
27
|
agent_card: AgentCard
|
|
27
28
|
|
|
28
29
|
def create_a2a_tool(agent_card: AgentCard) -> LangchainTool:
|
|
29
|
-
"""Create a LangChain tool from an A2A agent card.
|
|
30
|
+
"""Create a LangChain tool from an A2A agent card.
|
|
31
|
+
|
|
32
|
+
Args:
|
|
33
|
+
agent_card (AgentCard): The A2A agent card to create a tool for.
|
|
34
|
+
|
|
35
|
+
Returns:
|
|
36
|
+
LangchainTool: A LangChain tool that can communicate with the A2A agent.
|
|
37
|
+
"""
|
|
30
38
|
|
|
31
39
|
class GoogleADKAgent(BaseAgent):
|
|
32
|
-
"""An agent that wraps a native Google ADK Agent.
|
|
40
|
+
"""An agent that wraps a native Google ADK Agent with MCP support.
|
|
33
41
|
|
|
34
42
|
This class implements the AgentInterface and uses Google's LlmAgent
|
|
35
43
|
to handle the core conversation and tool execution logic via ADK's
|
|
36
|
-
async-first design.
|
|
44
|
+
async-first design. It includes persistent MCP session management for
|
|
45
|
+
stateful tool execution across multiple calls.
|
|
46
|
+
|
|
47
|
+
The agent supports:
|
|
48
|
+
- Native ADK tools (FunctionTool, LangchainTool)
|
|
49
|
+
- MCP tools via GoogleADKMCPClient with session persistence
|
|
50
|
+
- Sub-agent delegation using ADK's built-in multi-agent capabilities
|
|
51
|
+
- A2A communication through tool integration
|
|
37
52
|
"""
|
|
38
53
|
adk_native_agent: LlmAgent
|
|
39
54
|
model: Incomplete
|
|
@@ -43,7 +58,7 @@ class GoogleADKAgent(BaseAgent):
|
|
|
43
58
|
session_service: Incomplete
|
|
44
59
|
name: Incomplete
|
|
45
60
|
def __init__(self, name: str, instruction: str, model: str, tools: list[Any] | None = None, description: str | None = None, max_iterations: int = 3, agents: list['GoogleADKAgent'] | None = None, **kwargs: Any) -> None:
|
|
46
|
-
'''Initializes the GoogleADKAgent.
|
|
61
|
+
'''Initializes the GoogleADKAgent with MCP support.
|
|
47
62
|
|
|
48
63
|
Args:
|
|
49
64
|
name: The name of this wrapper agent.
|
|
@@ -73,15 +88,20 @@ class GoogleADKAgent(BaseAgent):
|
|
|
73
88
|
or for other unhandled errors during synchronous execution.
|
|
74
89
|
'''
|
|
75
90
|
async def arun(self, query: str, **kwargs: Any) -> dict[str, Any]:
|
|
76
|
-
'''Asynchronously runs the agent with
|
|
91
|
+
'''Asynchronously runs the agent with MCP tool support.
|
|
92
|
+
|
|
93
|
+
This method ensures MCP tools are properly initialized before execution
|
|
94
|
+
and provides persistent session management for stateful MCP tools.
|
|
77
95
|
|
|
78
96
|
Args:
|
|
79
97
|
query: The user\'s query to process.
|
|
80
98
|
**kwargs: Additional keyword arguments. Supports "session_id", "user_id", "app_name".
|
|
81
99
|
|
|
82
100
|
Returns:
|
|
83
|
-
A dictionary containing the output and
|
|
101
|
+
A dictionary containing the output, tool_calls, and session_id.
|
|
84
102
|
'''
|
|
103
|
+
async def cleanup(self) -> None:
|
|
104
|
+
"""Clean up ADK and MCP resources."""
|
|
85
105
|
async def arun_stream(self, query: str, **kwargs: Any) -> AsyncIterator[str]:
|
|
86
106
|
'''Runs the agent with the given query and streams the response parts.
|
|
87
107
|
|
|
@@ -98,18 +118,11 @@ class GoogleADKAgent(BaseAgent):
|
|
|
98
118
|
This method takes the agents from a2a_config.known_agents, creates A2AAgent
|
|
99
119
|
instances for each one, and wraps them in LangChain tools.
|
|
100
120
|
|
|
101
|
-
Returns:
|
|
102
|
-
None: The tools are added to the existing tools list.
|
|
103
|
-
"""
|
|
104
|
-
def add_mcp_server(self, mcp_config: dict[str, dict[str, Any]]) -> None:
|
|
105
|
-
"""Adds a new MCP server configuration.
|
|
106
|
-
|
|
107
121
|
Args:
|
|
108
|
-
|
|
122
|
+
agent_cards (list[AgentCard]): List of A2A agent cards to register as tools.
|
|
109
123
|
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
KeyError: If any server name already exists in the configuration.
|
|
124
|
+
Returns:
|
|
125
|
+
None: The tools are added to the existing tools list.
|
|
113
126
|
"""
|
|
114
127
|
async def arun_a2a_stream(self, query: str, configurable: dict[str, Any] | None = None, **kwargs: Any) -> AsyncGenerator[dict[str, Any], None]:
|
|
115
128
|
'''Asynchronously streams the agent\'s response in a format compatible with A2A.
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
from aip_agents.agent.hitl.config import ToolApprovalConfig as ToolApprovalConfig
|
|
2
|
+
from aip_agents.agent.hitl.manager import ApprovalManager as ApprovalManager
|
|
3
|
+
from aip_agents.agent.hitl.prompt import BasePromptHandler as BasePromptHandler, DeferredPromptHandler as DeferredPromptHandler
|
|
4
|
+
from aip_agents.schema.hitl import ApprovalDecision as ApprovalDecision, ApprovalLogEntry as ApprovalLogEntry, ApprovalRequest as ApprovalRequest
|
|
5
|
+
|
|
6
|
+
__all__ = ['ToolApprovalConfig', 'ApprovalManager', 'ApprovalDecision', 'ApprovalLogEntry', 'ApprovalRequest', 'BasePromptHandler', 'DeferredPromptHandler']
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
from dataclasses import dataclass
|
|
2
|
+
|
|
3
|
+
@dataclass
|
|
4
|
+
class ToolApprovalConfig:
|
|
5
|
+
"""Configuration for HITL approval behavior attached to a tool.
|
|
6
|
+
|
|
7
|
+
Supplying this configuration marks the tool as requiring approval. Only the
|
|
8
|
+
timeout is configurable; timeouts always result in a safe skip.
|
|
9
|
+
|
|
10
|
+
Attributes:
|
|
11
|
+
timeout_seconds: Defaults to 300; must be >0.
|
|
12
|
+
"""
|
|
13
|
+
timeout_seconds: int = ...
|
|
14
|
+
def __post_init__(self) -> None:
|
|
15
|
+
"""Validate configuration after initialization."""
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
from _typeshed import Incomplete
|
|
2
|
+
from aip_agents.agent.hitl.config import ToolApprovalConfig as ToolApprovalConfig
|
|
3
|
+
from aip_agents.agent.hitl.manager import ApprovalManager as ApprovalManager
|
|
4
|
+
from aip_agents.schema.hitl import ApprovalDecision as ApprovalDecision, ApprovalDecisionType as ApprovalDecisionType, ApprovalRequest as ApprovalRequest, HitlMetadata as HitlMetadata
|
|
5
|
+
from aip_agents.schema.langgraph import ToolCallResult as ToolCallResult
|
|
6
|
+
from aip_agents.tools.tool_config_injector import TOOL_CONFIGS_KEY as TOOL_CONFIGS_KEY
|
|
7
|
+
from aip_agents.utils.datetime import ensure_utc_datetime as ensure_utc_datetime
|
|
8
|
+
from aip_agents.utils.logger import get_logger as get_logger
|
|
9
|
+
from collections.abc import Callable
|
|
10
|
+
from typing import Any
|
|
11
|
+
|
|
12
|
+
logger: Incomplete
|
|
13
|
+
MAX_CONTEXT_MESSAGE_LENGTH: int
|
|
14
|
+
|
|
15
|
+
class LangGraphHitLMixin:
|
|
16
|
+
"""Provide Human-in-the-Loop helpers for LangGraph agents."""
|
|
17
|
+
tool_configs: dict[str, Any] | None
|
|
18
|
+
name: str
|
|
19
|
+
@property
|
|
20
|
+
def hitl_manager(self) -> ApprovalManager | None:
|
|
21
|
+
"""Return the active ``ApprovalManager``, creating one if needed."""
|
|
22
|
+
@hitl_manager.setter
|
|
23
|
+
def hitl_manager(self, manager: ApprovalManager | None) -> None:
|
|
24
|
+
"""Set the HITL approval manager instance.
|
|
25
|
+
|
|
26
|
+
Args:
|
|
27
|
+
manager: ApprovalManager instance or None.
|
|
28
|
+
"""
|
|
29
|
+
def ensure_hitl_manager(self) -> ApprovalManager | None:
|
|
30
|
+
"""Ensure an ``ApprovalManager`` exists when HITL configs are present."""
|
|
31
|
+
def use_hitl_manager(self, manager: ApprovalManager) -> None:
|
|
32
|
+
"""Replace the current ``ApprovalManager`` with the supplied instance.
|
|
33
|
+
|
|
34
|
+
Args:
|
|
35
|
+
manager: The ApprovalManager instance to use for HITL approvals.
|
|
36
|
+
"""
|
|
37
|
+
def register_hitl_notifier(self, notifier: Callable[[ApprovalRequest], None]) -> None:
|
|
38
|
+
"""Register a notifier callback to receive HITL approval requests.
|
|
39
|
+
|
|
40
|
+
Args:
|
|
41
|
+
notifier: Callback function that will be called with approval requests.
|
|
42
|
+
"""
|
|
@@ -0,0 +1,199 @@
|
|
|
1
|
+
from _typeshed import Incomplete
|
|
2
|
+
from aip_agents.agent.hitl.config import ToolApprovalConfig as ToolApprovalConfig
|
|
3
|
+
from aip_agents.agent.hitl.prompt import BasePromptHandler as BasePromptHandler, DeferredPromptHandler as DeferredPromptHandler
|
|
4
|
+
from aip_agents.schema.hitl import ApprovalDecision as ApprovalDecision, ApprovalDecisionType as ApprovalDecisionType, ApprovalLogEntry as ApprovalLogEntry, ApprovalRequest as ApprovalRequest
|
|
5
|
+
from collections.abc import Callable as Callable, Iterable
|
|
6
|
+
from typing import Any
|
|
7
|
+
|
|
8
|
+
MAX_ARGUMENTS_PREVIEW_LENGTH: int
|
|
9
|
+
DECISION_MESSAGE_MAP: Incomplete
|
|
10
|
+
TOOL_EXECUTION_BLOCKING_DECISIONS: Incomplete
|
|
11
|
+
|
|
12
|
+
class ApprovalManager:
|
|
13
|
+
"""Manages the HITL approval workflow for tools.
|
|
14
|
+
|
|
15
|
+
This class coordinates the approval process from configuration through
|
|
16
|
+
to final decision, handling timeouts and cleanup.
|
|
17
|
+
"""
|
|
18
|
+
def __init__(self, prompt_handler: BasePromptHandler | None = None) -> None:
|
|
19
|
+
"""Initialize the approval manager.
|
|
20
|
+
|
|
21
|
+
Args:
|
|
22
|
+
prompt_handler: Optional prompt handler for user interaction.
|
|
23
|
+
Defaults to DeferredPromptHandler which exposes pending requests
|
|
24
|
+
for out-of-band resolution.
|
|
25
|
+
"""
|
|
26
|
+
def create_approval_request(self, tool_name: str, arguments: dict[str, Any], config: ToolApprovalConfig, context: dict[str, str] | None = None) -> ApprovalRequest:
|
|
27
|
+
"""Create a new approval request for a tool call.
|
|
28
|
+
|
|
29
|
+
Args:
|
|
30
|
+
tool_name: Name of the tool being called.
|
|
31
|
+
arguments: Tool arguments (will be JSON serialized).
|
|
32
|
+
config: Approval configuration for this tool.
|
|
33
|
+
context: Optional context metadata. Defaults to None.
|
|
34
|
+
|
|
35
|
+
Returns:
|
|
36
|
+
The created approval request.
|
|
37
|
+
"""
|
|
38
|
+
def get_pending_request(self, request_id: str) -> ApprovalRequest | None:
|
|
39
|
+
"""Get a pending approval request by ID.
|
|
40
|
+
|
|
41
|
+
Args:
|
|
42
|
+
request_id: The unique identifier of the approval request.
|
|
43
|
+
|
|
44
|
+
Returns:
|
|
45
|
+
The pending approval request if found, None otherwise.
|
|
46
|
+
"""
|
|
47
|
+
def approve_request(self, request: ApprovalRequest, operator_input: str = 'approved') -> ApprovalDecision:
|
|
48
|
+
'''Record an approval decision for a request.
|
|
49
|
+
|
|
50
|
+
This method creates an approval decision, calculates latency metrics,
|
|
51
|
+
and removes the request from the active requests queue.
|
|
52
|
+
|
|
53
|
+
Args:
|
|
54
|
+
request: The approval request to approve.
|
|
55
|
+
operator_input: Raw operator input that led to this decision. Defaults to "approved".
|
|
56
|
+
|
|
57
|
+
Returns:
|
|
58
|
+
The recorded approval decision.
|
|
59
|
+
'''
|
|
60
|
+
def reject_request(self, request: ApprovalRequest, operator_input: str = 'rejected') -> ApprovalDecision:
|
|
61
|
+
'''Record a rejection decision for a request.
|
|
62
|
+
|
|
63
|
+
This method creates a rejection decision, calculates latency metrics,
|
|
64
|
+
and removes the request from the active requests queue.
|
|
65
|
+
|
|
66
|
+
Args:
|
|
67
|
+
request: The approval request to reject.
|
|
68
|
+
operator_input: Raw operator input that led to this decision. Defaults to "rejected".
|
|
69
|
+
|
|
70
|
+
Returns:
|
|
71
|
+
The recorded rejection decision.
|
|
72
|
+
'''
|
|
73
|
+
def skip_request(self, request: ApprovalRequest, operator_input: str = 'skipped') -> ApprovalDecision:
|
|
74
|
+
'''Record a skip decision for a request.
|
|
75
|
+
|
|
76
|
+
This method creates a skip decision, calculates latency metrics,
|
|
77
|
+
and removes the request from the active requests queue.
|
|
78
|
+
|
|
79
|
+
Args:
|
|
80
|
+
request: The approval request to skip.
|
|
81
|
+
operator_input: Raw operator input that led to this decision. Defaults to "skipped".
|
|
82
|
+
|
|
83
|
+
Returns:
|
|
84
|
+
The recorded skip decision.
|
|
85
|
+
'''
|
|
86
|
+
def timeout_request(self, request: ApprovalRequest, operator_input: str = 'TIMEOUT') -> ApprovalDecision:
|
|
87
|
+
'''Record a timeout decision for a request, always skipping the tool.
|
|
88
|
+
|
|
89
|
+
Args:
|
|
90
|
+
request (ApprovalRequest): The approval request that timed out.
|
|
91
|
+
operator_input (str, optional): Input from the operator (defaults to "TIMEOUT").
|
|
92
|
+
|
|
93
|
+
Returns:
|
|
94
|
+
ApprovalDecision: The timeout decision.
|
|
95
|
+
'''
|
|
96
|
+
def check_timeout(self, request: ApprovalRequest) -> ApprovalDecision | None:
|
|
97
|
+
"""Check if a request has timed out and return timeout decision if so.
|
|
98
|
+
|
|
99
|
+
Args:
|
|
100
|
+
request: The approval request to check.
|
|
101
|
+
|
|
102
|
+
Returns:
|
|
103
|
+
Timeout decision if timed out, None otherwise.
|
|
104
|
+
"""
|
|
105
|
+
async def prompt_for_decision(self, request: ApprovalRequest, timeout_seconds: int, context_keys: list[str] | None = None) -> ApprovalDecision:
|
|
106
|
+
"""Prompt for a decision using the configured handler.
|
|
107
|
+
|
|
108
|
+
This method delegates to the configured prompt handler to obtain
|
|
109
|
+
an approval decision from the operator. The handler may be interactive
|
|
110
|
+
(CLI) or deferred (programmatic, resume-in-place).
|
|
111
|
+
|
|
112
|
+
Args:
|
|
113
|
+
request: The approval request to prompt for.
|
|
114
|
+
timeout_seconds: How long to wait for input.
|
|
115
|
+
context_keys: Optional keys to display from context. Defaults to None.
|
|
116
|
+
|
|
117
|
+
Returns:
|
|
118
|
+
The operator's decision on the request.
|
|
119
|
+
"""
|
|
120
|
+
def list_pending_requests(self) -> Iterable[ApprovalRequest]:
|
|
121
|
+
"""Return a snapshot of currently pending requests.
|
|
122
|
+
|
|
123
|
+
This method provides a thread-safe snapshot of all currently active
|
|
124
|
+
approval requests that are waiting for operator decisions.
|
|
125
|
+
|
|
126
|
+
Returns:
|
|
127
|
+
An iterable of all pending approval requests.
|
|
128
|
+
"""
|
|
129
|
+
def resolve_pending_request(self, request_id: str, decision: str, operator_input: str = '') -> ApprovalDecision:
|
|
130
|
+
'''Resolve a pending request with an explicit decision.
|
|
131
|
+
|
|
132
|
+
Args:
|
|
133
|
+
request_id: The unique identifier of the pending approval request.
|
|
134
|
+
decision: The decision string (e.g., "approved", "rejected", "skipped").
|
|
135
|
+
operator_input: Optional raw operator input, defaults to the decision string. Defaults to "".
|
|
136
|
+
|
|
137
|
+
Returns:
|
|
138
|
+
The recorded approval decision.
|
|
139
|
+
|
|
140
|
+
Raises:
|
|
141
|
+
KeyError: If no pending request exists with the given request_id.
|
|
142
|
+
ValueError: If the decision string is not supported.
|
|
143
|
+
'''
|
|
144
|
+
def create_log_entry(self, decision: ApprovalDecision, tool_name: str, agent_id: str | None = None, thread_id: str | None = None, additional_context: dict[str, Any] | None = None) -> ApprovalLogEntry:
|
|
145
|
+
"""Create a log entry for a decision.
|
|
146
|
+
|
|
147
|
+
Args:
|
|
148
|
+
decision: The approval decision.
|
|
149
|
+
tool_name: Name of the tool.
|
|
150
|
+
agent_id: Optional agent identifier. Defaults to None.
|
|
151
|
+
thread_id: Optional thread/session identifier. Defaults to None.
|
|
152
|
+
additional_context: Optional additional logging context. Defaults to None.
|
|
153
|
+
|
|
154
|
+
Returns:
|
|
155
|
+
Structured log entry.
|
|
156
|
+
"""
|
|
157
|
+
def cleanup_expired_requests(self) -> int:
|
|
158
|
+
"""Clean up expired requests and return count of cleaned requests.
|
|
159
|
+
|
|
160
|
+
This method removes all approval requests that have exceeded their
|
|
161
|
+
timeout period from the active requests queue. This is typically
|
|
162
|
+
called periodically to prevent memory leaks from abandoned requests.
|
|
163
|
+
|
|
164
|
+
Returns:
|
|
165
|
+
The number of expired requests that were cleaned up.
|
|
166
|
+
"""
|
|
167
|
+
def register_waiter(self, request_id: str, future: Any) -> None:
|
|
168
|
+
"""Register a waiter future for an approval request.
|
|
169
|
+
|
|
170
|
+
Args:
|
|
171
|
+
request_id: The id for which to wait.
|
|
172
|
+
future: An asyncio.Future that will receive a tuple(decision, operator_input).
|
|
173
|
+
"""
|
|
174
|
+
def unregister_waiter(self, request_id: str) -> None:
|
|
175
|
+
"""Unregister a waiter if present (used on timeout/cancellation).
|
|
176
|
+
|
|
177
|
+
Args:
|
|
178
|
+
request_id (str): The ID of the request to unregister the waiter for.
|
|
179
|
+
"""
|
|
180
|
+
async def wait_for_pending_decision(self, request: ApprovalRequest, timeout_seconds: int) -> ApprovalDecision:
|
|
181
|
+
"""Wait for a pending request to be resolved and return the final decision.
|
|
182
|
+
|
|
183
|
+
Args:
|
|
184
|
+
request: The pending approval request to wait for.
|
|
185
|
+
timeout_seconds: Maximum time to wait before treating as timeout.
|
|
186
|
+
|
|
187
|
+
Returns:
|
|
188
|
+
The finalized approval decision.
|
|
189
|
+
"""
|
|
190
|
+
@staticmethod
|
|
191
|
+
def get_decision_message(decision: ApprovalDecision) -> str:
|
|
192
|
+
"""Get the appropriate message for a HITL decision.
|
|
193
|
+
|
|
194
|
+
Args:
|
|
195
|
+
decision: The approval decision to get a message for.
|
|
196
|
+
|
|
197
|
+
Returns:
|
|
198
|
+
A human-readable message explaining the decision outcome.
|
|
199
|
+
"""
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
from aip_agents.schema.hitl import ApprovalDecision as ApprovalDecision, ApprovalDecisionType as ApprovalDecisionType, ApprovalLogEntry as ApprovalLogEntry, ApprovalRequest as ApprovalRequest
|
|
2
|
+
|
|
3
|
+
__all__ = ['ApprovalDecisionType', 'ApprovalRequest', 'ApprovalDecision', 'ApprovalLogEntry']
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
from abc import ABC, abstractmethod
|
|
2
|
+
from aip_agents.agent.hitl.manager import ApprovalManager as ApprovalManager
|
|
3
|
+
from aip_agents.schema.hitl import ApprovalDecision as ApprovalDecision, ApprovalRequest as ApprovalRequest
|
|
4
|
+
|
|
5
|
+
class BasePromptHandler(ABC):
|
|
6
|
+
"""Abstract base class for prompt handlers used in HITL flows."""
|
|
7
|
+
def attach_manager(self, manager: ApprovalManager) -> None:
|
|
8
|
+
"""Optionally attach the ``ApprovalManager`` coordinating approvals.
|
|
9
|
+
|
|
10
|
+
Args:
|
|
11
|
+
manager (ApprovalManager): The approval manager instance to attach.
|
|
12
|
+
"""
|
|
13
|
+
@abstractmethod
|
|
14
|
+
async def prompt_for_decision(self, request: ApprovalRequest, timeout_seconds: int, context_keys: list[str] | None = None) -> ApprovalDecision:
|
|
15
|
+
"""Collect and return a decision for the given approval request.
|
|
16
|
+
|
|
17
|
+
Args:
|
|
18
|
+
request (ApprovalRequest): The approval request to prompt for.
|
|
19
|
+
timeout_seconds (int): Maximum time to wait for a decision in seconds.
|
|
20
|
+
context_keys (list[str] | None, optional): Optional keys for additional context. Defaults to None.
|
|
21
|
+
|
|
22
|
+
Returns:
|
|
23
|
+
ApprovalDecision: The decision made for the approval request.
|
|
24
|
+
"""
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
from aip_agents.agent.hitl.manager import ApprovalManager as ApprovalManager
|
|
2
|
+
from aip_agents.agent.hitl.prompt.base import BasePromptHandler as BasePromptHandler
|
|
3
|
+
from aip_agents.schema.hitl import ApprovalDecision as ApprovalDecision, ApprovalDecisionType as ApprovalDecisionType, ApprovalRequest as ApprovalRequest
|
|
4
|
+
from collections.abc import Callable
|
|
5
|
+
|
|
6
|
+
class DeferredPromptHandler(BasePromptHandler):
|
|
7
|
+
"""Prompt handler that defers tool execution until an external decision is received."""
|
|
8
|
+
def __init__(self, notify: Callable[[ApprovalRequest], None] | None = None) -> None:
|
|
9
|
+
"""Initialize the deferred prompt handler.
|
|
10
|
+
|
|
11
|
+
Args:
|
|
12
|
+
notify: Optional callback function to notify when an approval request is made.
|
|
13
|
+
"""
|
|
14
|
+
def attach_manager(self, manager: ApprovalManager) -> None:
|
|
15
|
+
"""Attach the ApprovalManager orchestrating approvals.
|
|
16
|
+
|
|
17
|
+
Args:
|
|
18
|
+
manager: The ApprovalManager instance to attach for handling approval decisions.
|
|
19
|
+
"""
|
|
20
|
+
async def prompt_for_decision(self, request: ApprovalRequest, timeout_seconds: int, context_keys: list[str] | None = None) -> ApprovalDecision:
|
|
21
|
+
"""Register a waiter and return a pending decision sentinel.
|
|
22
|
+
|
|
23
|
+
Args:
|
|
24
|
+
request: The approval request containing the tool call details and context.
|
|
25
|
+
timeout_seconds: Number of seconds to wait for approval before timing out.
|
|
26
|
+
context_keys: Optional list of context keys to include in the approval request.
|
|
27
|
+
|
|
28
|
+
Returns:
|
|
29
|
+
ApprovalDecision with PENDING status and registered waiter for external resolution.
|
|
30
|
+
"""
|
aip_agents/agent/interface.pyi
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
import abc
|
|
2
1
|
from a2a.types import AgentCard as AgentCard
|
|
3
2
|
from abc import ABC, abstractmethod
|
|
4
|
-
from aip_agents.agent
|
|
5
|
-
from
|
|
6
|
-
from
|
|
3
|
+
from aip_agents.schema.agent import BaseAgentConfig as BaseAgentConfig
|
|
4
|
+
from collections.abc import AsyncGenerator
|
|
5
|
+
from gllm_inference.lm_invoker.lm_invoker import BaseLMInvoker
|
|
6
|
+
from typing import Any
|
|
7
7
|
|
|
8
|
-
class AgentInterface(ABC
|
|
8
|
+
class AgentInterface(ABC):
|
|
9
9
|
"""A general and minimal interface for agent implementations.
|
|
10
10
|
|
|
11
11
|
Defines core execution methods (`__init__`, `run`, `arun`, `arun_stream`).
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
from collections.abc import AsyncIterator
|
|
2
|
+
from typing import Any, Protocol
|
|
3
|
+
|
|
4
|
+
class LangGraphAgentProtocol(Protocol):
|
|
5
|
+
"""Minimal interface required by LangGraphA2AExecutor."""
|
|
6
|
+
name: str
|
|
7
|
+
async def arun_a2a_stream(self, query: str, **kwargs: Any) -> AsyncIterator[dict[str, Any]]:
|
|
8
|
+
"""Stream A2A-compatible chunks for the given query.
|
|
9
|
+
|
|
10
|
+
Args:
|
|
11
|
+
query (str): The query to execute and stream.
|
|
12
|
+
**kwargs (Any): Additional keyword arguments for execution.
|
|
13
|
+
|
|
14
|
+
Yields:
|
|
15
|
+
dict[str, Any]: A2A-compatible streaming chunks.
|
|
16
|
+
"""
|
|
17
|
+
|
|
18
|
+
class LangflowAgentProtocol(Protocol):
|
|
19
|
+
"""Minimal interface required by LangflowA2AExecutor."""
|
|
20
|
+
name: str
|
|
21
|
+
async def arun_a2a_stream(self, query: str, **kwargs: Any) -> AsyncIterator[dict[str, Any]]:
|
|
22
|
+
"""Stream A2A-compatible chunks for the given query.
|
|
23
|
+
|
|
24
|
+
Args:
|
|
25
|
+
query (str): The query to execute and stream.
|
|
26
|
+
**kwargs (Any): Additional keyword arguments for execution.
|
|
27
|
+
|
|
28
|
+
Yields:
|
|
29
|
+
dict[str, Any]: A2A-compatible streaming chunks.
|
|
30
|
+
"""
|
|
31
|
+
|
|
32
|
+
class GoogleADKAgentProtocol(Protocol):
|
|
33
|
+
"""Minimal interface required by GoogleADKExecutor."""
|
|
34
|
+
name: str
|
|
35
|
+
async def arun_a2a_stream(self, query: str, **kwargs: Any) -> AsyncIterator[dict[str, Any]]:
|
|
36
|
+
"""Stream A2A-compatible chunks for the given query.
|
|
37
|
+
|
|
38
|
+
Args:
|
|
39
|
+
query (str): The query to execute and stream.
|
|
40
|
+
**kwargs (Any): Additional keyword arguments for execution.
|
|
41
|
+
|
|
42
|
+
Yields:
|
|
43
|
+
dict[str, Any]: A2A-compatible streaming chunks.
|
|
44
|
+
"""
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
from _typeshed import Incomplete
|
|
2
|
+
from a2a.types import AgentCard as AgentCard
|
|
3
|
+
from aip_agents.agent.base_agent import BaseAgent as BaseAgent
|
|
4
|
+
from aip_agents.clients.langflow import LangflowApiClient as LangflowApiClient
|
|
5
|
+
from aip_agents.clients.langflow.types import LangflowEventType as LangflowEventType
|
|
6
|
+
from aip_agents.schema.agent import LangflowAgentConfig as LangflowAgentConfig
|
|
7
|
+
from aip_agents.types import A2AEvent as A2AEvent, A2AStreamEventType as A2AStreamEventType
|
|
8
|
+
from aip_agents.utils.logger import get_logger as get_logger
|
|
9
|
+
from aip_agents.utils.sse_chunk_transformer import SSEChunkTransformer as SSEChunkTransformer
|
|
10
|
+
from collections.abc import AsyncGenerator
|
|
11
|
+
from typing import Any
|
|
12
|
+
|
|
13
|
+
logger: Incomplete
|
|
14
|
+
|
|
15
|
+
class LangflowAgent(BaseAgent):
|
|
16
|
+
"""Langflow agent implementation for executing Langflow flows.
|
|
17
|
+
|
|
18
|
+
This agent integrates with Langflow APIs to execute flows while providing
|
|
19
|
+
full compatibility with the SDK's agent framework, including:
|
|
20
|
+
- Synchronous and asynchronous execution
|
|
21
|
+
- Regular and A2A streaming support
|
|
22
|
+
- Session management for conversation continuity
|
|
23
|
+
- Error handling and retry logic
|
|
24
|
+
- Credential management through BaseAgent
|
|
25
|
+
|
|
26
|
+
The agent builds on BaseAgent to gain shared A2A utilities while focusing on
|
|
27
|
+
Langflow-specific execution logic.
|
|
28
|
+
"""
|
|
29
|
+
langflow_config: Incomplete
|
|
30
|
+
flow_id: Incomplete
|
|
31
|
+
api_client: Incomplete
|
|
32
|
+
def __init__(self, name: str, flow_id: str, description: str | None = None, base_url: str | None = None, api_key: str | None = None, config: LangflowAgentConfig | dict[str, Any] | None = None, **kwargs: Any) -> None:
|
|
33
|
+
"""Initialize the LangflowAgent.
|
|
34
|
+
|
|
35
|
+
Args:
|
|
36
|
+
name: The name of the agent.
|
|
37
|
+
flow_id: The unique identifier of the Langflow flow to execute.
|
|
38
|
+
description: Human-readable description.
|
|
39
|
+
base_url: The base URL of the Langflow API server.
|
|
40
|
+
api_key: The API key for Langflow authentication.
|
|
41
|
+
config: Langflow-specific configuration or dict.
|
|
42
|
+
**kwargs: Additional keyword arguments passed to BaseAgent.
|
|
43
|
+
"""
|
|
44
|
+
def run(self, query: str, **kwargs: Any) -> dict[str, Any]:
|
|
45
|
+
"""Synchronously run the Langflow agent.
|
|
46
|
+
|
|
47
|
+
Args:
|
|
48
|
+
query: The input query for the agent.
|
|
49
|
+
**kwargs: Additional keyword arguments.
|
|
50
|
+
|
|
51
|
+
Returns:
|
|
52
|
+
Dictionary containing the agent's response.
|
|
53
|
+
"""
|
|
54
|
+
async def arun(self, query: str, **kwargs: Any) -> dict[str, Any]:
|
|
55
|
+
"""Asynchronously run the Langflow agent.
|
|
56
|
+
|
|
57
|
+
Args:
|
|
58
|
+
query: The input query for the agent.
|
|
59
|
+
**kwargs: Additional keyword arguments.
|
|
60
|
+
|
|
61
|
+
Returns:
|
|
62
|
+
Dictionary containing the agent's response and metadata.
|
|
63
|
+
"""
|
|
64
|
+
async def arun_stream(self, query: str, **kwargs: Any) -> AsyncGenerator[str | dict[str, Any], None]:
|
|
65
|
+
"""Asynchronously stream the Langflow agent's response.
|
|
66
|
+
|
|
67
|
+
Args:
|
|
68
|
+
query: The input query for the agent.
|
|
69
|
+
**kwargs: Additional keyword arguments.
|
|
70
|
+
|
|
71
|
+
Yields:
|
|
72
|
+
Chunks of output (strings or dicts) from the streaming response.
|
|
73
|
+
"""
|
|
74
|
+
async def arun_a2a_stream(self, query: str, **kwargs: Any) -> AsyncGenerator[dict[str, Any], None]:
|
|
75
|
+
"""Asynchronously stream the agent's response in A2A format.
|
|
76
|
+
|
|
77
|
+
This method converts Langflow streaming events into A2A-compatible events
|
|
78
|
+
following the patterns established by BaseLangGraphAgent.
|
|
79
|
+
|
|
80
|
+
Args:
|
|
81
|
+
query: The input query for the agent.
|
|
82
|
+
**kwargs: Additional keyword arguments.
|
|
83
|
+
|
|
84
|
+
Yields:
|
|
85
|
+
A2A-compatible event dictionaries with semantic event types.
|
|
86
|
+
"""
|
|
87
|
+
async def arun_sse_stream(self, query: str, task_id: str | None = None, context_id: str | None = None, **kwargs: Any) -> AsyncGenerator[dict[str, Any], None]:
|
|
88
|
+
'''Stream agent response as SSE-compatible chunks.
|
|
89
|
+
|
|
90
|
+
This method wraps arun_a2a_stream and transforms output to the normalized
|
|
91
|
+
dict format matching A2AConnector.astream_to_agent output, enabling direct
|
|
92
|
+
streaming without A2A server overhead.
|
|
93
|
+
|
|
94
|
+
Args:
|
|
95
|
+
query: The input query for the agent.
|
|
96
|
+
task_id: Optional task identifier for the stream.
|
|
97
|
+
context_id: Optional context identifier for the stream.
|
|
98
|
+
**kwargs: Additional arguments passed to arun_a2a_stream.
|
|
99
|
+
|
|
100
|
+
Yields:
|
|
101
|
+
SSEChunk dicts with normalized structure:
|
|
102
|
+
- status: "success" | "error"
|
|
103
|
+
- task_state: "working" | "completed" | "failed" | "canceled"
|
|
104
|
+
- content: Text content or None
|
|
105
|
+
- event_type: Always string (never enum)
|
|
106
|
+
- final: True for terminal events
|
|
107
|
+
- metadata: Normalized metadata dict
|
|
108
|
+
- artifacts: Only present when non-empty
|
|
109
|
+
'''
|
|
110
|
+
def register_a2a_agents(self, agents: list[AgentCard]) -> None:
|
|
111
|
+
"""Register A2A agents (not supported for Langflow agents).
|
|
112
|
+
|
|
113
|
+
Args:
|
|
114
|
+
agents: List of AgentCard instances.
|
|
115
|
+
|
|
116
|
+
Raises:
|
|
117
|
+
NotImplementedError: Langflow agents don't support A2A agent registration.
|
|
118
|
+
"""
|
|
119
|
+
def add_mcp_server(self, mcp_config: dict[str, dict[str, Any]]) -> None:
|
|
120
|
+
"""Add MCP server configuration (not supported for Langflow agents).
|
|
121
|
+
|
|
122
|
+
Args:
|
|
123
|
+
mcp_config: MCP server configuration.
|
|
124
|
+
|
|
125
|
+
Raises:
|
|
126
|
+
NotImplementedError: Langflow agents don't support MCP servers.
|
|
127
|
+
"""
|
|
128
|
+
async def health_check(self) -> bool:
|
|
129
|
+
"""Check if the Langflow API is accessible.
|
|
130
|
+
|
|
131
|
+
Returns:
|
|
132
|
+
True if the API is accessible, False otherwise.
|
|
133
|
+
"""
|