""" 配置管理模块 从环境变量加载配置 """ import os from pathlib import Path from typing import Optional from pydantic_settings import BaseSettings from functools import lru_cache # 查找.env文件的位置 def find_env_file(): """查找.env文件,支持从backend目录或项目根目录启动""" current_dir = Path.cwd() # 尝试当前目录 env_path = current_dir / ".env" if env_path.exists(): print(f"[Config] 找到.env文件: {env_path}") return str(env_path) # 尝试父目录(项目根目录) env_path = current_dir.parent / ".env" if env_path.exists(): print(f"[Config] 找到.env文件: {env_path}") return str(env_path) # 尝试backend的父目录 if current_dir.name == "backend": env_path = current_dir.parent / ".env" if env_path.exists(): print(f"[Config] 找到.env文件: {env_path}") return str(env_path) # 尝试从环境变量指定的路径 if os.getenv('ENV_FILE'): env_path = Path(os.getenv('ENV_FILE')) if env_path.exists(): print(f"[Config] 从ENV_FILE环境变量找到.env文件: {env_path}") return str(env_path) print(f"[Config] 警告:未找到.env文件,当前目录: {current_dir}") # 默认返回当前目录的.env return ".env" class Settings(BaseSettings): """应用配置""" # Tushare配置 tushare_token: str = "" # LLM配置 zhipuai_api_key: str = "" deepseek_api_key: str = "" # 数据库配置 database_url: str = "sqlite:///./stock_agent.db" # API配置 api_host: str = "0.0.0.0" api_port: int = 8000 debug: bool = True # 安全配置 secret_key: str = "change-this-secret-key-in-production" rate_limit: str = "100/minute" # JWT配置 jwt_algorithm: str = "HS256" jwt_expire_days: int = 7 # 腾讯云短信配置 tencent_sms_app_id: str = "1400961527" tencent_sms_secret_id: str = "AKIDxnbGj281iHtKallqqzvlV5YxBCrPltnS" # 腾讯云SecretId tencent_sms_secret_key: str = "ta6PXTMBsX7dzA7IN6uYUFn8F9uTovoU" # 腾讯云SecretKey tencent_sms_sign_id: str = "629073" tencent_sms_template_id: str = "2353142" # 验证码配置 code_expire_minutes: int = 5 code_resend_seconds: int = 60 code_max_per_hour: int = 10 # 白名单手机号(无需验证码即可登录) whitelist_phones: str = "18583366860,18583926860" # CORS配置 cors_origins: str = "http://localhost:8000,http://127.0.0.1:8000" # Binance 配置(公开数据不需要 API 密钥) binance_api_key: str = "" binance_api_secret: str = "" # 飞书机器人配置 feishu_crypto_webhook_url: str = "https://open.feishu.cn/open-apis/bot/v2/hook/8a1dcf69-6753-41e2-a393-edc4f7822db0" # 加密货币通知 feishu_stock_webhook_url: str = "https://open.feishu.cn/open-apis/bot/v2/hook/408ab727-0dcd-4c7a-bde7-4aad38cbf807" # 股票通知 feishu_news_webhook_url: str = "https://open.feishu.cn/open-apis/bot/v2/hook/c7fd0db7-d295-451c-b943-130278a6cd9d" # 新闻智能体通知 feishu_error_webhook_url: str = "https://open.feishu.cn/open-apis/bot/v2/hook/ba6952c9-3b0c-4bc1-8a43-ceaacb27b043" # 系统异常通知 feishu_enabled: bool = True # 是否启用飞书通知 # Telegram 机器人配置 telegram_bot_token: str = "" # 从 @BotFather 获取 telegram_channel_id: str = "" # 频道 ID,如 @your_channel 或 -1001234567890 telegram_enabled: bool = True # 是否启用 Telegram 通知 # 钉钉机器人配置 dingtalk_webhook_url: str = "https://oapi.dingtalk.com/robot/send?access_token=a4fa1c1a6a07a5ed07d79c701f79b44efb1e726da3b47b50495ebdc9190423ec" # 钉钉群机器人 Webhook dingtalk_secret: str = "SECdc6dffe3b6838a5d8afde3486d5415b9a17d3ebc9cbf934438883acee1189e8d" # 加签密钥 dingtalk_enabled: bool = True # 是否启用钉钉通知 # 加密货币交易智能体配置 crypto_symbols: str = "BTCUSDT,ETHUSDT" # 监控的交易对,逗号分隔 crypto_analysis_interval: int = 60 # 分析间隔(秒) crypto_llm_threshold: float = 0.70 # 触发 LLM 分析的置信度阈值 # 价格监控模式配置 use_bitget_websocket: bool = True # 是否使用 Bitget WebSocket 实时价格(默认 False 使用 Binance 轮询) # 波动率过滤配置(节省 LLM 调用) crypto_volatility_filter_enabled: bool = True # 是否启用波动率过滤 crypto_min_volatility_percent: float = 0.5 # 最小波动率(百分比),低于此值跳过分析 crypto_min_price_range_percent: float = 0.3 # 最小价格变动范围(百分比),低于此值跳过分析 crypto_5m_surge_threshold: float = 1.0 # 5分钟突发波动阈值(百分比),超过此值即使1小时波动率低也会触发分析 # Brave Search API 配置 brave_api_key: str = "" # 模拟交易配置 paper_trading_enabled: bool = True # 是否启用模拟交易 paper_trading_initial_balance: float = 10000 # 初始本金 (USDT) paper_trading_leverage: int = 20 # 杠杆倍数(全仓模式下的最大杠杆) paper_trading_margin_per_order: float = 1000 # 每单保证金 (USDT) paper_trading_max_orders: int = 10 # 最大持仓+挂单总数 paper_trading_auto_close_opposite: bool = False # 是否自动平掉反向持仓(智能策略) paper_trading_breakeven_threshold: float = 1 # 保本止损触发阈值(盈利百分比),0表示禁用 # 移动止损配置 paper_trading_trailing_stop_enabled: bool = True # 是否启用移动止损 paper_trading_trailing_stop_threshold_multiplier: float = 2 # 移动止损触发倍数(相对于保本阈值) paper_trading_trailing_stop_ratio: float = 0.5 # 移动止损跟随比例(0-1之间,1表示完全跟随) # 动态止盈配置(趋势过滤) paper_trading_dynamic_tp_enabled: bool = True # 是否启用动态止盈 paper_trading_strong_trend_ratio: float = 0.7 # 强趋势时移动止损跟随比例(70%) paper_trading_weak_trend_ratio: float = 0.3 # 弱趋势时移动止损跟随比例(30%) paper_trading_sideways_tp_percent: float = 3 # 震荡市固定止盈百分比(3%) # 废弃的配置(保留兼容性) paper_trading_position_a: float = 1000 # A级信号仓位 (USDT) paper_trading_position_b: float = 500 # B级信号仓位 (USDT) paper_trading_position_c: float = 200 # C级信号仓位 (USDT) # ========== 实盘交易配置 ========== # Bitget API 配置 bitget_api_key: str = "" # Bitget API Key bitget_api_secret: str = "" # Bitget API Secret bitget_passphrase: str = "" # Bitget API Passphrase bitget_use_testnet: bool = True # 是否使用测试网(测试时设为 true) # 实盘交易开关 real_trading_enabled: bool = False # 实盘交易总开关(false 时仅模拟交易生效) # 实盘交易风险控制 real_trading_max_single_position: float = 1000 # 单笔最大持仓金额 (USDT) real_trading_max_total_ratio: float = 0.5 # 最大总仓位比例(账户的50%) real_trading_default_leverage: int = 10 # 实盘默认杠杆(低于模拟) real_trading_risk_per_trade: float = 0.02 # 每笔交易风险比例(2%) real_trading_max_orders: int = 5 # 实盘最大同时持仓数 # Agent 模型配置 (可选值: zhipu, deepseek) smart_agent_model: str = "deepseek" # SmartAgent 使用的模型 crypto_agent_model: str = "deepseek" # CryptoAgent 使用的模型 stock_agent_model: str = "deepseek" # StockAgent 使用的模型 # 股票智能体配置 stock_symbols_us: str = "" # 美股代码,逗号分隔 # 港股代码:科技+新能源+芯片+AI+金融+汽车+医药+消费+能源 # 科技:腾讯控股/阿里巴巴/美团/小米集团/京东集团/网易/百度/快手/知乎/B站 # 新能源:比亚迪/理想汽车/小鹏汽车/赣锋锂业/龙源电力/信义能源 # 芯片:中芯国际/华虹半导体/上海复旦 # AI:商汤/第四范式/创新奇智/美图/联易融/百融云 # 金融:汇控/建行/工行/农行/中行/友邦/平安/国寿/中金/中信 # 汽车:蔚来/长城汽车/吉利汽车 # 医药:药明康德/药明生物/百济神州/信达生物/石药集团 # 消费:名创优品/泡泡玛特/安踏体育 # 能源:中海油/中石油/中国神华 stock_symbols_hk: str = "00700.HK,09988.HK,03690.HK,01810.HK,09618.HK,09999.HK,09888.HK,01024.HK,02390.HK,09626.HK,01211.HK,02015.HK,09868.HK,01772.HK,00916.HK,03868.HK,00981.HK,01347.HK,01385.HK,00020.HK,06682.HK,02121.HK,01357.HK,09959.HK,06608.HK,00005.HK,00939.HK,01398.HK,01288.HK,03988.HK,01299.HK,02318.HK,02628.HK,03908.HK,06030.HK,09866.HK,02333.HK,00175.HK,02359.HK,02269.HK,06160.HK,01801.HK,01093.HK,09896.HK,09992.HK,02020.HK,00883.HK,00857.HK,01088.HK" stock_analysis_interval: int = 300 # 分析间隔(秒,默认5分钟) stock_llm_threshold: float = 0.70 # 触发 LLM 分析的置信度阈值 # A股智能体配置 astock_monitor_enabled: bool = True # 是否启用A股智能体 astock_change_threshold: float = 2.0 # 涨跌幅阈值(%),超过此值触发异动 astock_top_n: int = 3 # 每个板块返回前N只龙头股 astock_check_interval: int = 30 # 检查间隔(分钟) # 钉钉通知配置(A股专用) dingtalk_astock_webhook: str = "" # A股钉钉通知 Webhook dingtalk_astock_secret: str = "" # A股钉钉通知加签密钥 class Config: env_file = find_env_file() case_sensitive = False @lru_cache() def get_settings() -> Settings: """获取配置单例""" return Settings()