1
0

code_runner.py 2.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. import io
  2. import contextlib
  3. from hello_agents.tools import Tool
  4. from typing import Dict, Any
  5. class CodeRunner(Tool):
  6. """
  7. 安全执行 Python 代码并返回输出的工具。
  8. 警告:此工具使用 exec(),在生产环境中不安全。
  9. 对于真实产品,请使用 Docker 等沙箱环境。
  10. """
  11. def __init__(self):
  12. super().__init__(
  13. name="code_runner",
  14. description="执行 Python 代码并返回标准输出/错误。输入应为包含 'code' 键的字典。"
  15. )
  16. def get_parameters(self) -> Dict[str, Any]:
  17. return {
  18. "type": "object",
  19. "properties": {
  20. "code": {
  21. "type": "string",
  22. "description": "要执行的 Python 代码片段"
  23. }
  24. },
  25. "required": ["code"]
  26. }
  27. def run(self, parameters: Dict[str, Any]) -> str:
  28. code = parameters.get("code", "")
  29. if not code:
  30. return "错误:未提供代码。"
  31. # 捕获标准输出和标准错误
  32. stdout_capture = io.StringIO()
  33. stderr_capture = io.StringIO()
  34. try:
  35. with contextlib.redirect_stdout(stdout_capture), contextlib.redirect_stderr(stderr_capture):
  36. # 创建受限的全局作用域
  37. safe_globals = {
  38. "__builtins__": __builtins__,
  39. "print": print,
  40. "range": range,
  41. "len": len,
  42. # 根据需要添加更多安全的内置函数
  43. }
  44. exec(code, safe_globals)
  45. output = stdout_capture.getvalue()
  46. errors = stderr_capture.getvalue()
  47. result = ""
  48. if output:
  49. result += f"输出:\n{output}\n"
  50. if errors:
  51. result += f"错误:\n{errors}\n"
  52. if not result:
  53. result = "代码执行成功,无输出。"
  54. return result
  55. except Exception as e:
  56. return f"运行时错误: {str(e)}"