compare.py 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. """
  2. A2A vs 直连 对比测试
  3. 交互式输入问题,同时展示两种调用方式的结果
  4. 运行前提:问答 Agent (server.py) 必须在 9999 端口运行
  5. """
  6. import asyncio
  7. import httpx
  8. from datetime import datetime
  9. from openai import AsyncOpenAI
  10. from a2a.client import A2ACardResolver, ClientConfig, create_client
  11. from a2a.helpers import new_text_message
  12. from a2a.types import Role, SendMessageRequest
  13. DEEPSEEK_API_KEY = "你的APIKEY"
  14. A2A_SERVER_URL = "http://127.0.0.1:9999"
  15. def extract_text(task) -> str:
  16. texts = []
  17. if task.artifacts:
  18. for artifact in task.artifacts:
  19. for part in artifact.parts:
  20. t = part.text.strip() if part.text else ""
  21. if t:
  22. texts.append(t)
  23. return "\n".join(texts)
  24. async def direct_call(question: str) -> str:
  25. """方式 A:直连 DeepSeek,不经过 A2A"""
  26. client = AsyncOpenAI(
  27. api_key=DEEPSEEK_API_KEY,
  28. base_url="https://api.deepseek.com/v1",
  29. )
  30. response = await client.chat.completions.create(
  31. model="deepseek-chat",
  32. messages=[
  33. {"role": "system", "content": "你是一个有用的 AI 助手,请用简洁的中文回答用户的问题。"},
  34. {"role": "user", "content": question},
  35. ],
  36. temperature=0.7,
  37. max_tokens=1024,
  38. )
  39. result = response.choices[0].message.content
  40. await client.close()
  41. return result
  42. async def a2a_call(question: str) -> str:
  43. """方式 B:走 A2A 协议 → Server → DeepSeek"""
  44. async with httpx.AsyncClient() as http_client:
  45. resolver = A2ACardResolver(httpx_client=http_client, base_url=A2A_SERVER_URL)
  46. agent_card = await resolver.get_agent_card()
  47. config = ClientConfig(streaming=False)
  48. client = await create_client(agent=agent_card, client_config=config)
  49. message = new_text_message(question, role=Role.ROLE_USER)
  50. request = SendMessageRequest(message=message)
  51. result = ""
  52. async for response in client.send_message(request):
  53. result = extract_text(response.task)
  54. await client.close()
  55. return result
  56. async def main():
  57. print("=" * 72)
  58. print(" A2A vs 直连 — 交互式对比测试")
  59. print(" =============================")
  60. print(" 方式 A:Client → DeepSeek API(直连,无 A2A)")
  61. print(" 方式 B:Client → A2A Server → DeepSeek API(经过 A2A 协议)")
  62. print("=" * 72)
  63. # 先检查 A2A Server 是否在运行
  64. print("\n[*] 检查 A2A Server 状态...", end=" ")
  65. try:
  66. async with httpx.AsyncClient() as c:
  67. r = await c.get(f"{A2A_SERVER_URL}/.well-known/agent-card.json", timeout=3)
  68. if r.status_code == 200:
  69. print("✅ 运行中")
  70. else:
  71. print(f"⚠️ 响应异常 ({r.status_code})")
  72. except Exception:
  73. print("❌ 未运行!请先启动:python server.py")
  74. return
  75. while True:
  76. question = input("\n" + "─" * 72 + "\n输入问题(输入 exit 退出)> ").strip()
  77. if not question:
  78. continue
  79. if question.lower() in ("exit", "quit", "q"):
  80. print("bye")
  81. break
  82. print()
  83. # 方式 A:直连
  84. t0 = datetime.now()
  85. print(" ┌─ [A] 直连 DeepSeek ──────────────────────────────")
  86. try:
  87. direct_result = await direct_call(question)
  88. t1 = datetime.now()
  89. for line in direct_result.split("\n"):
  90. print(f" │ {line}")
  91. print(f" └─ ⏱ {(t1 - t0).total_seconds():.2f}s")
  92. except Exception as e:
  93. print(f" │ ❌ {e}")
  94. print(" └─")
  95. print()
  96. # 方式 B:走 A2A
  97. t2 = datetime.now()
  98. print(" ┌─ [B] 通过 A2A 协议 ──────────────────────────────")
  99. print(" │ Client → A2A Server → DeepSeek")
  100. try:
  101. a2a_result = await a2a_call(question)
  102. t3 = datetime.now()
  103. for line in a2a_result.split("\n"):
  104. print(f" │ {line}")
  105. print(f" └─ ⏱ {(t3 - t2).total_seconds():.2f}s")
  106. except Exception as e:
  107. print(f" │ ❌ {e}")
  108. print(" └─")
  109. if __name__ == "__main__":
  110. asyncio.run(main())