Riy777 commited on
Commit
66489a8
·
verified ·
1 Parent(s): 20b5499

Update trade_manager.py

Browse files
Files changed (1) hide show
  1. trade_manager.py +36 -32
trade_manager.py CHANGED
@@ -1,5 +1,5 @@
1
  # ============================================================
2
- # 🛡️ trade_manager.py (V37.0 - GEM-Architect: Governance Integrated)
3
  # ============================================================
4
 
5
  import asyncio
@@ -12,7 +12,7 @@ from typing import List, Dict, Any
12
  # استيراد المكونات الأساسية
13
  from smart_portfolio import SmartPortfolio
14
  from ml_engine.processor import SystemLimits
15
- # ✅ استيراد محرك الحوكمة الجديد (مجلس الشيوخ)
16
  from governance_engine import GovernanceEngine
17
 
18
  class TradeManager:
@@ -45,7 +45,7 @@ class TradeManager:
45
  }
46
 
47
  self.execution_lock = asyncio.Lock()
48
- print(f"🛡️ [TradeManager V37.0] Full System Online (Governance Layer Active).")
49
 
50
  async def initialize_sentry_exchanges(self):
51
  """تهيئة المحفظة واستعادة الحالة"""
@@ -112,7 +112,7 @@ class TradeManager:
112
  print(f" -> ⚠️ [Skip] {symbol}: Insufficient 1m data.")
113
  continue
114
 
115
- # فحص Sniper (يستخدم الآن الإعدادات المحقونة في Processor)
116
  sniper_result = await self.processor.check_sniper_entry(ohlcv_1m, order_book)
117
  sniper_signal = sniper_result.get('signal', 'WAIT')
118
  final_conf = sniper_result.get('confidence_prob', 0.0)
@@ -147,7 +147,6 @@ class TradeManager:
147
  """تنفيذ الدخول الفعلي مع فحص الحوكمة وإدارة المحفظة"""
148
  try:
149
  # 🏛️ الخطوة 1: استشارة مجلس الحوكمة (Governance Layer)
150
- # نحتاج إلى تجميع البيانات المطلوبة للحوكمة (خاصة فريم 15 دقيقة)
151
  print(f" 🏛️ [Governance] Convening Senate for {symbol}...")
152
 
153
  t15_task = self.data_manager.get_latest_ohlcv(symbol, '15m', 200)
@@ -167,12 +166,12 @@ class TradeManager:
167
 
168
  print(f" ✅ [Governance PASS] Grade: {gov_decision['grade']} | Score: {gov_decision['governance_score']:.1f}")
169
 
170
- # دمج نتائج الحوكمة في بيانات الإشارة لتراها المحفظة
171
  signal_data['governance_grade'] = gov_decision['grade']
172
  signal_data['governance_score'] = gov_decision['governance_score']
173
  signal_data['governance_details'] = gov_decision['components']
174
 
175
- # 💰 الخطوة 2: طلب الموافقة من المحفظة الذكية (تستخدم الـ Grade لتحديد الحجم)
176
  is_approved, plan = await self.smart_portfolio.request_entry_approval(signal_data, len(self.open_positions))
177
 
178
  if not is_approved:
@@ -196,6 +195,7 @@ class TradeManager:
196
  'oracle_conf': signal_data.get('confidence', 0),
197
  'governance_grade': gov_decision['grade'], # تسجيل الجودة
198
  'governance_score': gov_decision['governance_score'],
 
199
  'system_confidence': system_conf,
200
  'market_mood': market_mood,
201
  'regime_at_entry': getattr(SystemLimits, 'CURRENT_REGIME', 'UNKNOWN')
@@ -213,13 +213,8 @@ class TradeManager:
213
  'last_update': datetime.now().isoformat(),
214
  'last_oracle_check': datetime.now().isoformat(),
215
  'strategy': 'OracleV4_Governance_Hydra',
216
- 'initial_oracle_strength': float(signal_data.get('strength', 0.5)),
217
- 'initial_oracle_class': signal_data.get('target_class', 'TP2'),
218
- 'oracle_tp_map': signal_data.get('tp_map', {}),
219
  'entry_capital': approved_size_usd,
220
  'entry_fee_usd': entry_fee_usd,
221
- 'l1_score': float(signal_data.get('enhanced_final_score', 0.0)),
222
- 'target_class_int': 3,
223
  'decision_data': decision_snapshot,
224
  'highest_price': current_price
225
  }
@@ -303,7 +298,7 @@ class TradeManager:
303
  'volume_30m_usd': vol_30m_sum
304
  }
305
 
306
- # ✅ استدعاء الحراس (يستخدمون SystemLimits المحدثة ديناميكياً)
307
  decision = self.processor.consult_dual_guardians(symbol, d1, d5, d15, context_data, order_book_snapshot=d_ob)
308
  action = decision.get('action', 'HOLD')
309
  reason = decision.get('reason', '')
@@ -322,7 +317,7 @@ class TradeManager:
322
  last_ai_check_time = time.time()
323
  self.open_positions[symbol]['last_update'] = datetime.now().isoformat()
324
 
325
- # 3. إعادة فحص Oracle (كل 15 دقيقة)
326
  last_oracle = datetime.fromisoformat(trade.get('last_oracle_check', datetime.now().isoformat()))
327
  if (datetime.now() - last_oracle).total_seconds() > self.ORACLE_CHECK_INTERVAL:
328
  self.open_positions[symbol]['last_oracle_check'] = datetime.now().isoformat()
@@ -351,7 +346,6 @@ class TradeManager:
351
  await self.r2.save_open_trades_async(list(self.open_positions.values()))
352
 
353
  async def _consult_oracle_strategy_update(self, symbol, trade):
354
- """إعادة استشارة Oracle أثناء الصفقة"""
355
  try:
356
  tasks = [self.data_manager.get_latest_ohlcv(symbol, tf, limit=100) for tf in ["15m", "1h", "4h"]]
357
  results = await asyncio.gather(*tasks)
@@ -367,13 +361,6 @@ class TradeManager:
367
  print(f"🚨 [Oracle] Outlook Bearish. Exiting {symbol}...")
368
  await self.force_exit_by_manager(symbol, reason="Oracle_Bearish_Flip")
369
  return
370
-
371
- if oracle.get('strength', 0.5) < (trade.get('initial_oracle_strength', 0.5) * 0.6):
372
- tp_map = trade.get('oracle_tp_map', {})
373
- cons_tp = tp_map.get('TP1')
374
- if cons_tp and cons_tp > curr_p and cons_tp < trade['tp_price']:
375
- print(f"⚠️ [Oracle] Weakening. Lowering TP to {cons_tp}")
376
- self.open_positions[symbol]['tp_price'] = cons_tp
377
  except Exception: pass
378
 
379
  def _launch_post_exit_analysis(self, symbol, exit_price, exit_time, position_size_usd, ai_scores=None, trade_obj=None):
@@ -398,10 +385,6 @@ class TradeManager:
398
  is_good_exit = change_pct < 0
399
 
400
  self._update_specific_stat("hybrid", is_good_exit, usd_impact)
401
- if ai_scores:
402
- if ai_scores.get('crash', 0) >= 0.60: self._update_specific_stat("crash", is_good_exit, usd_impact)
403
- if ai_scores.get('giveback', 0) >= 0.70: self._update_specific_stat("giveback", is_good_exit, usd_impact)
404
- if ai_scores.get('stagnation', 0) >= 0.50: self._update_specific_stat("stagnation", is_good_exit, usd_impact)
405
 
406
  record = {"symbol": symbol, "exit_price": exit_price, "price_15m": curr, "usd_impact": usd_impact, "verdict": "SUCCESS" if is_good_exit else "MISS"}
407
  await self.r2.append_deep_steward_audit(record)
@@ -415,7 +398,7 @@ class TradeManager:
415
  entry_price = float(trade['entry_price']); exit_price = float(price)
416
  entry_capital = float(trade.get('entry_capital', 100.0)); entry_fee = float(trade.get('entry_fee_usd', 0.0))
417
 
418
- # Gross & Net Calculation
419
  exit_val_gross = (exit_price / entry_price) * entry_capital
420
  exit_fee = exit_val_gross * self.FEE_RATE
421
  total_fees = entry_fee + exit_fee
@@ -424,7 +407,7 @@ class TradeManager:
424
  true_net_pnl_usd = gross_pnl_usd - total_fees
425
  true_net_pct = (true_net_pnl_usd / entry_capital) * 100
426
 
427
- # Update Portfolio with Net PnL
428
  await self.smart_portfolio.register_closed_position(entry_capital, gross_pnl_usd, total_fees)
429
 
430
  trade.update({
@@ -451,16 +434,37 @@ class TradeManager:
451
 
452
  print(f"✅ [EXIT] {symbol} | Net PnL: {true_net_pct:.2f}% (${true_net_pnl_usd:.2f}) | {reason}")
453
 
454
- self._launch_post_exit_analysis(symbol, exit_price, trade.get('exit_time'), entry_capital, ai_scores, trade)
455
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
456
  # ==========================================================
457
  # 🧠 THE TACTICAL LEARNING LINK
458
  # ==========================================================
459
  if self.learning_hub:
460
- print(f"🎓 [Learning] Reporting trade outcome to AdaptiveHub...")
461
  asyncio.create_task(self.learning_hub.register_trade_outcome(trade))
462
- # ==========================================================
463
 
 
 
464
  self.latest_guardian_log = f"✅ Closed {symbol} ({reason})"
465
  if symbol in self.sentry_tasks: self.sentry_tasks[symbol].cancel(); del self.sentry_tasks[symbol]
466
 
 
1
  # ============================================================
2
+ # 🛡️ trade_manager.py (V37.1 - GEM-Architect: Governance Data Loop)
3
  # ============================================================
4
 
5
  import asyncio
 
12
  # استيراد المكونات الأساسية
13
  from smart_portfolio import SmartPortfolio
14
  from ml_engine.processor import SystemLimits
15
+ # ✅ استيراد محرك الحوكمة الجديد
16
  from governance_engine import GovernanceEngine
17
 
18
  class TradeManager:
 
45
  }
46
 
47
  self.execution_lock = asyncio.Lock()
48
+ print(f"🛡️ [TradeManager V37.1] Full System Online (Governance Learning Loop Active).")
49
 
50
  async def initialize_sentry_exchanges(self):
51
  """تهيئة المحفظة واستعادة الحالة"""
 
112
  print(f" -> ⚠️ [Skip] {symbol}: Insufficient 1m data.")
113
  continue
114
 
115
+ # فحص Sniper
116
  sniper_result = await self.processor.check_sniper_entry(ohlcv_1m, order_book)
117
  sniper_signal = sniper_result.get('signal', 'WAIT')
118
  final_conf = sniper_result.get('confidence_prob', 0.0)
 
147
  """تنفيذ الدخول الفعلي مع فحص الحوكمة وإدارة المحفظة"""
148
  try:
149
  # 🏛️ الخطوة 1: استشارة مجلس الحوكمة (Governance Layer)
 
150
  print(f" 🏛️ [Governance] Convening Senate for {symbol}...")
151
 
152
  t15_task = self.data_manager.get_latest_ohlcv(symbol, '15m', 200)
 
166
 
167
  print(f" ✅ [Governance PASS] Grade: {gov_decision['grade']} | Score: {gov_decision['governance_score']:.1f}")
168
 
169
+ # دمج نتائج الحوكمة في بيانات الإشارة
170
  signal_data['governance_grade'] = gov_decision['grade']
171
  signal_data['governance_score'] = gov_decision['governance_score']
172
  signal_data['governance_details'] = gov_decision['components']
173
 
174
+ # 💰 الخطوة 2: طلب الموافقة من المحفظة الذكية
175
  is_approved, plan = await self.smart_portfolio.request_entry_approval(signal_data, len(self.open_positions))
176
 
177
  if not is_approved:
 
195
  'oracle_conf': signal_data.get('confidence', 0),
196
  'governance_grade': gov_decision['grade'], # تسجيل الجودة
197
  'governance_score': gov_decision['governance_score'],
198
+ 'governance_details': gov_decision['components'], # تفاصيل الـ 156 مؤشر (مختصرة في المجالات)
199
  'system_confidence': system_conf,
200
  'market_mood': market_mood,
201
  'regime_at_entry': getattr(SystemLimits, 'CURRENT_REGIME', 'UNKNOWN')
 
213
  'last_update': datetime.now().isoformat(),
214
  'last_oracle_check': datetime.now().isoformat(),
215
  'strategy': 'OracleV4_Governance_Hydra',
 
 
 
216
  'entry_capital': approved_size_usd,
217
  'entry_fee_usd': entry_fee_usd,
 
 
218
  'decision_data': decision_snapshot,
219
  'highest_price': current_price
220
  }
 
298
  'volume_30m_usd': vol_30m_sum
299
  }
300
 
301
+ # ✅ استدعاء الحراس
302
  decision = self.processor.consult_dual_guardians(symbol, d1, d5, d15, context_data, order_book_snapshot=d_ob)
303
  action = decision.get('action', 'HOLD')
304
  reason = decision.get('reason', '')
 
317
  last_ai_check_time = time.time()
318
  self.open_positions[symbol]['last_update'] = datetime.now().isoformat()
319
 
320
+ # 3. إعادة فحص Oracle
321
  last_oracle = datetime.fromisoformat(trade.get('last_oracle_check', datetime.now().isoformat()))
322
  if (datetime.now() - last_oracle).total_seconds() > self.ORACLE_CHECK_INTERVAL:
323
  self.open_positions[symbol]['last_oracle_check'] = datetime.now().isoformat()
 
346
  await self.r2.save_open_trades_async(list(self.open_positions.values()))
347
 
348
  async def _consult_oracle_strategy_update(self, symbol, trade):
 
349
  try:
350
  tasks = [self.data_manager.get_latest_ohlcv(symbol, tf, limit=100) for tf in ["15m", "1h", "4h"]]
351
  results = await asyncio.gather(*tasks)
 
361
  print(f"🚨 [Oracle] Outlook Bearish. Exiting {symbol}...")
362
  await self.force_exit_by_manager(symbol, reason="Oracle_Bearish_Flip")
363
  return
 
 
 
 
 
 
 
364
  except Exception: pass
365
 
366
  def _launch_post_exit_analysis(self, symbol, exit_price, exit_time, position_size_usd, ai_scores=None, trade_obj=None):
 
385
  is_good_exit = change_pct < 0
386
 
387
  self._update_specific_stat("hybrid", is_good_exit, usd_impact)
 
 
 
 
388
 
389
  record = {"symbol": symbol, "exit_price": exit_price, "price_15m": curr, "usd_impact": usd_impact, "verdict": "SUCCESS" if is_good_exit else "MISS"}
390
  await self.r2.append_deep_steward_audit(record)
 
398
  entry_price = float(trade['entry_price']); exit_price = float(price)
399
  entry_capital = float(trade.get('entry_capital', 100.0)); entry_fee = float(trade.get('entry_fee_usd', 0.0))
400
 
401
+ # حساب الأرباح
402
  exit_val_gross = (exit_price / entry_price) * entry_capital
403
  exit_fee = exit_val_gross * self.FEE_RATE
404
  total_fees = entry_fee + exit_fee
 
407
  true_net_pnl_usd = gross_pnl_usd - total_fees
408
  true_net_pct = (true_net_pnl_usd / entry_capital) * 100
409
 
410
+ # تحديث المحفظة
411
  await self.smart_portfolio.register_closed_position(entry_capital, gross_pnl_usd, total_fees)
412
 
413
  trade.update({
 
434
 
435
  print(f"✅ [EXIT] {symbol} | Net PnL: {true_net_pct:.2f}% (${true_net_pnl_usd:.2f}) | {reason}")
436
 
437
+ # ==========================================================
438
+ # 🏛️ إرسال البيانات لملف تدريب الحوكمة (Governance Training Data)
439
+ # ==========================================================
440
+ try:
441
+ decision_data = trade.get('decision_data', {})
442
+ if 'governance_grade' in decision_data:
443
+ training_record = {
444
+ "symbol": symbol,
445
+ "entry_time": trade['entry_time'],
446
+ "exit_time": trade['exit_time'],
447
+ "governance_grade": decision_data['governance_grade'],
448
+ "governance_score": decision_data.get('governance_score', 0),
449
+ "governance_components": decision_data.get('governance_details', {}), # تفاصيل الـ 156 مؤشر
450
+ "entry_price": trade['entry_price'],
451
+ "exit_price": trade['exit_price'],
452
+ "profit_pct": true_net_pct,
453
+ "result": trade['result']
454
+ }
455
+ # إرسال إلى R2 في الخلفية
456
+ asyncio.create_task(self.r2.append_governance_training_data(training_record))
457
+ except Exception as ge:
458
+ print(f"⚠️ [Learning Error] Failed to save governance training data: {ge}")
459
+
460
  # ==========================================================
461
  # 🧠 THE TACTICAL LEARNING LINK
462
  # ==========================================================
463
  if self.learning_hub:
 
464
  asyncio.create_task(self.learning_hub.register_trade_outcome(trade))
 
465
 
466
+ self._launch_post_exit_analysis(symbol, exit_price, trade.get('exit_time'), entry_capital, ai_scores, trade)
467
+
468
  self.latest_guardian_log = f"✅ Closed {symbol} ({reason})"
469
  if symbol in self.sentry_tasks: self.sentry_tasks[symbol].cancel(); del self.sentry_tasks[symbol]
470