Files
evotraders/scripts/test_sandbox_simple.py
cillin 16b54d5ccc feat(agent): complete EvoAgent integration for all 6 agent roles
Migrate all agent roles from Legacy to EvoAgent architecture:
- fundamentals_analyst, technical_analyst, sentiment_analyst, valuation_analyst
- risk_manager, portfolio_manager

Key changes:
- EvoAgent now supports Portfolio Manager compatibility methods (_make_decision,
  get_decisions, get_portfolio_state, load_portfolio_state, update_portfolio)
- Add UnifiedAgentFactory for centralized agent creation
- ToolGuard with batch approval API and WebSocket broadcast
- Legacy agents marked deprecated (AnalystAgent, RiskAgent, PMAgent)
- Remove backend/agents/compat.py migration shim
- Add run_id alongside workspace_id for semantic clarity
- Complete integration test coverage (13 tests)
- All smoke tests passing for 6 agent roles

Constraint: Must maintain backward compatibility with existing run configs
Constraint: Memory support must work with EvoAgent (no fallback to Legacy)
Rejected: Separate PM implementation for EvoAgent | unified approach cleaner
Confidence: high
Scope-risk: broad
Directive: EVO_AGENT_IDS env var still respected but defaults to all roles
Not-tested: Kubernetes sandbox mode for skill execution
2026-04-02 00:55:08 +08:00

97 lines
2.6 KiB
Python

#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
简化测试 - 验证沙盒执行器基本功能
"""
import os
import sys
import warnings
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "backend"))
os.environ["SKILL_SANDBOX_MODE"] = "none"
def test_import():
"""测试导入"""
print("测试 1: 导入沙盒执行器")
from backend.tools.sandboxed_executor import get_sandbox, SkillSandbox
# 重置单例
SkillSandbox._instance = None
sandbox = get_sandbox()
print(f" ✓ 模式: {sandbox.current_mode}")
print(f" ✓ 后端: {type(sandbox._backend).__name__}")
return sandbox
def test_no_sandbox_backend():
"""测试无沙盒后端"""
print("\n测试 2: 无沙盒后端")
from backend.tools.sandboxed_executor import NoSandboxBackend
backend = NoSandboxBackend()
# 测试函数名解析
test_cases = [
("build_dcf_report", "dcf_report"),
("build_ev_ebitda_report", "multiple_valuation_report"),
("build_owner_earnings_report", "owner_earnings_report"),
("build_residual_income_report", "multiple_valuation_report"),
]
for func_name, expected_script in test_cases:
script_name = backend._get_script_name(func_name)
assert script_name == expected_script, f"期望 {expected_script}, 实际 {script_name}"
print(f"{func_name} -> {script_name}")
def test_module_resolution():
"""测试模块解析"""
print("\n测试 3: 模块路径解析")
from backend.tools.sandboxed_executor import NoSandboxBackend
backend = NoSandboxBackend()
skill_name = "builtin/valuation_review"
function_name = "build_dcf_report"
module_path = f"backend.skills.{skill_name.replace('/', '.')}.scripts"
script_name = backend._get_script_name(function_name)
submodule_path = f"{module_path}.{script_name}"
print(f" 技能名: {skill_name}")
print(f" 函数名: {function_name}")
print(f" 模块路径: {submodule_path}")
# 尝试导入
try:
module = __import__(submodule_path, fromlist=[function_name])
func = getattr(module, function_name)
print(f" ✓ 成功导入函数: {func.__name__}")
except Exception as e:
print(f" ✗ 导入失败: {e}")
def main():
print("=" * 50)
print("沙盒执行器简化测试")
print("=" * 50)
# 抑制警告
warnings.filterwarnings("ignore", category=RuntimeWarning)
test_import()
test_no_sandbox_backend()
test_module_resolution()
print("\n" + "=" * 50)
print("测试完成")
print("=" * 50)
if __name__ == "__main__":
main()