test_feishu_approval.py 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. #!/usr/bin/env python3
  2. """
  3. 测试飞书审批消息发送(不真正执行API)
  4. """
  5. import asyncio
  6. import sys
  7. import json
  8. from pathlib import Path
  9. from datetime import datetime
  10. # 添加项目根目录到路径
  11. PROJECT_ROOT = Path(__file__).parent.parent.parent
  12. sys.path.insert(0, str(PROJECT_ROOT))
  13. from examples.auto_put_ad_mini.tools.im_approval import send_approval_request
  14. from examples.auto_put_ad_mini.config import (
  15. IM_ENABLED,
  16. FEISHU_OPERATOR_OPEN_ID,
  17. FEISHU_OPERATOR_CHAT_ID
  18. )
  19. # 模拟ToolContext
  20. class SimpleContext:
  21. """简单的上下文模拟"""
  22. def __init__(self):
  23. self.config = {}
  24. async def test_feishu_message():
  25. """测试飞书消息发送"""
  26. print("=" * 70)
  27. print(" 测试飞书审批消息发送")
  28. print("=" * 70)
  29. if not IM_ENABLED:
  30. print("\n❌ IM_ENABLED=False,飞书功能未启用")
  31. print(" 请在 config.py 中设置 IM_ENABLED=True")
  32. return False
  33. print(f"\n✅ IM_ENABLED=True,飞书功能已启用")
  34. print(f" 接收人 OPEN_ID: {FEISHU_OPERATOR_OPEN_ID}")
  35. print(f" 接收群 CHAT_ID: {FEISHU_OPERATOR_CHAT_ID}")
  36. # 创建一个测试决策CSV(包含所有必需字段)
  37. test_decisions = [
  38. {
  39. "ad_id": "99999999999",
  40. "ad_name": "【测试】R500-回流330+-广告测试",
  41. "action": "bid_down",
  42. "final_action": "bid_down", # IM工具需要这个字段
  43. "dimension": "测试维度",
  44. "reason": "这是一条测试消息,验证飞书审批功能是否正常工作。动态ROI为2.5,低于R500组中位数3.74的33%,建议降价5%。",
  45. "confidence": "high",
  46. "recommended_change_pct": -0.05,
  47. "current_bid": 100.0,
  48. "new_bid": 95.0,
  49. "cost_7d_avg": 500.0,
  50. "roi": 2.5,
  51. "tier": 1,
  52. "audience_tier": "R500",
  53. "ad_age_days": 15,
  54. "roi_valid_days": 7,
  55. }
  56. ]
  57. # 保存测试决策CSV
  58. outputs_dir = Path(__file__).parent / "outputs" / "reports"
  59. outputs_dir.mkdir(parents=True, exist_ok=True)
  60. test_csv = outputs_dir / "test_approval_decisions.csv"
  61. import pandas as pd
  62. df = pd.DataFrame(test_decisions)
  63. df.to_csv(test_csv, index=False, encoding='utf-8-sig')
  64. print(f"\n📝 创建测试决策文件: {test_csv}")
  65. print(f" 决策数量: {len(test_decisions)}")
  66. print(f" 测试广告ID: {test_decisions[0]['ad_id']}")
  67. # 发送审批请求
  68. print(f"\n📤 发送飞书审批请求...")
  69. ctx = SimpleContext()
  70. try:
  71. result = await send_approval_request(
  72. ctx,
  73. validated_csv=str(test_csv),
  74. timeout_minutes=30
  75. )
  76. print(f"\n✅ 飞书消息发送成功!")
  77. print(f" {result.title}")
  78. print(f"\n📋 输出信息:")
  79. for line in result.output.split('\n'):
  80. print(f" {line}")
  81. # 检查metadata
  82. if result.metadata:
  83. print(f"\n📊 元数据:")
  84. for key, value in result.metadata.items():
  85. print(f" {key}: {value}")
  86. print(f"\n💡 请检查您的飞书:")
  87. print(f" 1. 打开飞书App")
  88. print(f" 2. 查找来自「增长投放」机器人的消息")
  89. print(f" 3. 消息中应包含测试广告的决策信息")
  90. return True
  91. except Exception as e:
  92. print(f"\n❌ 发送失败: {e}")
  93. import traceback
  94. traceback.print_exc()
  95. print(f"\n🔍 可能的原因:")
  96. print(f" 1. 飞书应用凭据不正确(APP_ID/APP_SECRET)")
  97. print(f" 2. 接收人/群聊ID不正确")
  98. print(f" 3. 网络问题或代理设置")
  99. print(f" 4. 飞书应用权限不足")
  100. return False
  101. async def main():
  102. print("\n" + "🧪" * 35)
  103. print(" " * 15 + "飞书审批功能测试")
  104. print("🧪" * 35)
  105. success = await test_feishu_message()
  106. print("\n" + "=" * 70)
  107. print(" 测试结果")
  108. print("=" * 70)
  109. if success:
  110. print("✅ 飞书消息发送成功,请检查飞书App")
  111. print("\n📝 下一步:")
  112. print(" 1. 在飞书中确认收到测试消息")
  113. print(" 2. 如需实际执行决策,设置 EXECUTION_ENABLED=True")
  114. print(" 3. 运行完整流程: python3 execute_once.py")
  115. else:
  116. print("❌ 飞书消息发送失败,请检查配置")
  117. return 0 if success else 1
  118. if __name__ == "__main__":
  119. sys.exit(asyncio.run(main()))