#!/usr/bin/env python3 """ 修正跟单方案金额。 用法: echo "原始信号文本" | python3 fix_recommendation.py 或: python3 fix_recommendation.py "原始信号文本" 从信号文本提取币种/方向/杠杆,调advisor脚本获取正确金额,替换原消息中的跟单方案部分。 """ import sys import re import json import subprocess from pathlib import Path ADVISOR = Path.home() / ".hermes/skills/trading/okx-auto-position/scripts/okx_position_advisor.py" def extract_from_signal(text): """从信号文本提取关键字段""" fields = {} # 币种 m = re.search(r'跟单建议\s*\|\s*(\w+)', text) if m: fields['symbol'] = m.group(1) # 方向 if '做多' in text: fields['side'] = 'long' elif '做空' in text: fields['side'] = 'short' # 杠杆 m = re.search(r'(\d+)x', text) if m: fields['leverage'] = m.group(1) # 交易员 m = re.search(r'📊\s*(\S+)', text) if m: fields['trader'] = m.group(1) # 交易员仓位 m = re.search(r'📊\s*\S+\s+([\d,.]+\s*\w+)', text) if m: fields['trader_pos'] = m.group(1) # 交易员价值 m = re.search(r'(价值\$?([\d,.]+))', text) if m: fields['trader_value'] = m.group(1) # 入场价 m = re.search(r'入场:\s*\$?([\d,.]+)', text) if m: fields['entry'] = m.group(1).replace(',', '') # 浮盈 m = re.search(r'浮[盈亏]:\s*([+-]?\$?[\d,.]+)', text) if m: fields['pnl'] = m.group(1).replace('$', '').replace(',', '') return fields def run_advisor(symbol, side, leverage): """调advisor脚本获取正确数据""" # Don't add /USDT - advisor handles symbol format internally cmd = ['python3', str(ADVISOR), '--symbol', symbol, '--side', side, '--leverage', str(leverage), '--json'] try: result = subprocess.run(cmd, capture_output=True, text=True, timeout=30, cwd=str(ADVISOR.parent)) if result.returncode == 0: return json.loads(result.stdout) except Exception as e: return {'error': str(e)} return {'error': 'advisor failed'} def rebuild_message(original, fields, rec): """用正确数据重建消息""" if 'error' in rec: return f"⚠️ advisor错误: {rec['error']}\n\n{original}" symbol = fields.get('symbol', '?') side_cn = '做多' if fields.get('side') == 'long' else '做空' emoji = '🟩' if fields.get('side') == 'long' else '🟥' leverage = fields.get('leverage', '10') trader = fields.get('trader', '?') trader_pos = fields.get('trader_pos', '?') trader_value = fields.get('trader_value', '?') entry = fields.get('entry', '?') pnl = fields.get('pnl', '0') # 性价比 cc = rec.get('cost_check', {}) rr = cc.get('rr_ratio', rec.get('rr', 0)) profit = cc.get('profit_amount', rec.get('tp_pnl', 0)) fee = cc.get('fee_cost', 0) fee_pct = cc.get('fee_pct', 0) net = cc.get('net_profit', 0) rating_emoji = cc.get('rating_emoji', '⚠️') rating_text = cc.get('rating_text', '未知') pnl_float = float(pnl) if pnl else 0 pnl_emoji = '🔥' if pnl_float > 0 else '🔴' pnl_sign = '+' if pnl_float > 0 else '' # 提取原始消息的趋势分析和ATR部分 trend_match = re.search(r'(📈 趋势分析.*?)(?=🛡️)', original, re.DOTALL) trend_block = trend_match.group(1).strip() if trend_match else "📈 趋势分析\n• 数据加载中" atr_match = re.search(r'(🛡️ ATR检查.*?)(?=📐|🎯|回复)', original, re.DOTALL) atr_block = atr_match.group(1).strip() if atr_match else "🛡️ ATR检查\n• 数据加载中" msg = f"""⚡ 跟单建议 | {symbol} {side_cn} {emoji} {leverage}x 📊 {trader} {trader_pos}(价值${trader_value})← 信号源,非你的仓位 入场: ${entry} | 当前: ${rec['price']} 浮盈: {pnl_sign}{pnl_float:.0f} {pnl_emoji} | 强平距: ${rec.get('liq_price', '?')} {trend_block} {atr_block} 📐 性价比检查(基于你的推荐仓位) • 你的仓位: {rec['contracts']}张(保证金{rec['margin']:.2f} USDT) • 盈亏比: {rr}:1 {'✅' if rr >= 2 else '⚠️' if rr >= 1.5 else '❌'} • 盈利额: +{profit:.2f} USDT {'✅' if profit >= 10 else '❌ <10U保底'} • 手续费: {fee:.2f} USDT ({fee_pct:.1f}%) {'✅' if fee_pct < 5 else '❌'} • 净盈利: {net:.2f} USDT {'✅' if net >= 10 else '❌'} • 评级: {rating_emoji} {rating_text} 🎯 跟单方案(基于你的账户数据) • 入场: ${rec['price']}(市价) • 止损: ${rec['sl_price']}(-{rec['sl_pct']:.1f}%,-{rec['sl_pnl']:.2f} USDT) • 止盈: ${rec['tp_price']}(+{rec['tp_pct']:.1f}%,+{rec['tp_pnl']:.2f} USDT) • 仓位: {rec['contracts']}张(保证金{rec['margin']:.2f} USDT) • 强平: ${rec.get('liq_price', '?')} 回复 Y 确认跟单 / N 取消""" return msg def main(): # Get input if len(sys.argv) > 1: text = ' '.join(sys.argv[1:]) else: text = sys.stdin.read() if not text.strip(): print("用法: python3 fix_recommendation.py '信号文本'") return # Extract fields fields = extract_from_signal(text) if not fields.get('symbol') or not fields.get('side'): print("⚠️ 无法解析信号文本") print(text) return # Run advisor leverage = fields.get('leverage', '10') rec = run_advisor(fields['symbol'], fields['side'], leverage) # Rebuild message result = rebuild_message(text, fields, rec) print(result) if __name__ == '__main__': main()