You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
[Deep Agent] Remove process-global request state (capability flags, connection singleton, frozen date) via runtime context #38
The deep agent keeps request-scoped data in process-global mutable state. That is unsafe as soon as more than one user, connection, or concurrent request hits the same process:
_connection_capabilities (agent/src/deep_agent/tools.py:20) is a module-level dict that get_database_catalog mutates. If connection A's catalog has no knowledge pairs, then for every other user/connection in the process, search_knowledge_pairs returns "[] ... Do not call this tool again" until someone else's catalog call flips it back. Under concurrency this is a race. The flags also start as True, so behaviour depends on call order.
The connection is selected by mutating a singleton: run_deep_agent.py:207-209 sets os.environ[...]and the private client._connection_id. No tool accepts a connection, so the deep agent cannot serve two connections in one process at all.
today is formatted into the system prompt once, at agent construction (agent.py:239). A long-running server will report a stale date after midnight. That affects every relative-date question ("אתמול", "השבוע").
Proposed fix
Define a context_schema (LangGraph runtime context), e.g. DeepAgentContext(connection_id: int, user_id: str, locale: str = "he"), and pass it per invocation (agent.ainvoke(..., context=DeepAgentContext(...))).
Tools read the connection via ToolRuntime[DeepAgentContext] and call JeenMetadataClient methods with an explicit connection_id (most already accept connection_id=).
Store capability flags in graph state (returned via Command(update=...) from get_database_catalog), or compute them per connection in a cache keyed by connection_id.
Inject today's date dynamically with a @dynamic_prompt / before_model middleware (timezone Asia/Jerusalem), not at construction time.
Acceptance Criteria
No module-level mutable request state remains in agent/src/deep_agent/.
Two concurrent ainvoke calls with different connection_ids (one with knowledge pairs, one without) produce correct, independent tool behaviour. Covered by an asyncio test.
run_deep_agent.py no longer touches client._connection_id or os.environ to switch connections.
The date in the prompt reflects the day of the invocation in Asia/Jerusalem (test with a frozen clock across midnight).
Definition of Done
Concurrency test added and green.
Tool docstrings unchanged from the model's point of view (context is injected, not a model argument).
Activity
fix(deep-agent): request-scoped runtime context instead of process gl…