import os import asyncio from langchain_openai import ChatOpenAI from langchain_core.messages import HumanMessage from langchain.tools import tool from deepagents import create_deep_agent from deepagents.backends import FilesystemBackend, LocalShellBackend, CompositeBackend # --- LLM ------------------------------------------------------------ llm = ChatOpenAI( model="openai/gpt-oss-20b:free", base_url="https://openrouter.ai/api/v1", api_key=os.getenv("OPENAI_API_KEY"), temperature=0.0, ) # --- Backend -------------------------------------------------------- backend = CompositeBackend([ LocalShellBackend(workspace_dir="./workspace"), FilesystemBackend(), ]) # --- Tool ----------------------------------------------------------- @tool def get_price(query: str) -> str: """Return a fake price table for a product in a city.""" # In a real task this would call an API or database if "молоко" in query: return "| Продукт | Цена (руб.) | Магазин |\n| Молоко | 89 | Магнит |" if "хлеб" in query: return "| Продукт | Цена (руб.) | Магазин |\n| Хлеб | 35 | Перекресток |" return "No data found." # --- Agent ---------------------------------------------------------- agent = create_deep_agent( model=llm, tools=[get_price], backend=backend, system_prompt="You are a helpful agent that can fetch product prices.", ) # --- Stream handling ----------------------------------------------- async def main(): # Prepare the initial message human_msg = HumanMessage(content="Какую цену у молока в Казани?") # Start streaming stream = agent.stream( {"messages": [human_msg]}, stream_mode=["messages", "updates"], ) step = 1 def format_chunk_message(chunk): nonlocal step message, meta = chunk if meta.get("langgraph_step") != step: step = meta.get("langgraph_step") print("\n --- --- --- \n") if message.content: print(message.content, end="", flush=True) def format_message(message): if message.content: return message.content # If the message is a tool call, format it nicely if message.tool_calls: call = message.tool_calls[0] return f"{call['name']}({call['args']})" return "" for chunk in stream: chunk_type, chunk_data = chunk if chunk_type == "messages": format_chunk_message(chunk_data) elif chunk_type == "updates": if chunk_data.get("model"): last_msg = chunk_data["model"]["messages"][-1] print(format_message(last_msg)) print("\n--- Stream finished ---") if __name__ == "__main__": asyncio.run(main())