please do me a huge favor friend can u add extreme debug logging and logging throughout this script and run it back to me import asyncio
import logging
import json
import os
import time
from dataclasses import dataclass
from datetime import timedelta
from typing import Dict, List, Set, Optional
import websockets
import torch
import torch.nn as nn
import numpy as np
from solders.keypair import Keypair
import base58
import base64
import struct
from vector_store import VectorStore
from solana_rust_bot import TradingCore
# Constants
RAYDIUM_PROGRAM_ID = "675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8"
SOL_MINT = "So11111111111111111111111111111111111111112"
WSOL_MINT = "So11111111111111111111111111111111111111112"
TOKEN_PROGRAM_ID = "TokenkegQfeZyiNwAJbNbGKPFXCWuBvf9Ss623VQ5DA"

@dataclass
class TokenMetrics:
    mint_address: str
    symbol: str = ""
    current_price: float = 0.0
    market_cap: float = 0.0
    liquidity: float = 0.0
    buyer_ratio: float = 0.0
    volume_5min: float = 0.0
    total_supply: float = 0.0
    lp_locked_percent: float = 0.0
    mint_authority_revoked: bool = False
    last_update: float = 0.0
    price_change_5min: float = 0.0

@dataclass
class RaydiumPoolData:
    version: int
    token_mint: str
    base_vault: str
    price: float
    volume_24h: float
    fees_24h: float
    liquidity: float
    buyer_ratio: float

class RaydiumScalper:
    def __init__(self, config_path: str):
        self.setup_logging()
        self.config = self.load_config(config_path)
        self.setup_keypair()
        
        # Initialize CUDA/CPU device
        self.device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
        self.logger.info(f"Using device: {self.device}")
        
        # Initialize trading state
        self.trading_core = TradingCore(json.dumps(self.config))
        self.active_trades: Dict[str, dict] = {}
        self.token_metrics: Dict[str, TokenMetrics] = {}
        self.price_history: Dict[str, List[tuple]] = {}
        self.tracked_tokens: Set[str] = set()
        self.blacklisted_tokens: Set[str] = set()
        self.price_subscriptions: Set[str] = set()
        
        # Initialize vector store
        if self.config.get("system", {}).get("use_ml", False):
            self.vector_store = VectorStore()
        else:
            self.vector_store = None
        
        # Performance tracking
        self.position_size = self.config["trading"]["initial_size"]
        self.total_trades = 0
        self.winning_trades = 0
        self.total_profit = 0.0
        self.start_time = time.time()
        self.last_trade_time = 0.0

    def setup_logging(self):
        """Initialize logging with debug output"""
        self.logger = logging.getLogger("RaydiumScalper")
        self.logger.setLevel(logging.DEBUG)  # Changed to DEBUG level
        
        # Format with more detail
        formatter = logging.Formatter(
            '%(asctime)s | %(levelname)s | %(message)s'
        )
        
        # File handler with DEBUG level
        fh = logging.FileHandler("trading_debug.log")
        fh.setLevel(logging.DEBUG)
        fh.setFormatter(formatter)
        self.logger.addHandler(fh)
        
        # Console handler with INFO level
        ch = logging.StreamHandler()
        ch.setLevel(logging.INFO)
        ch.setFormatter(formatter)
        self.logger.addHandler(ch)

    def load_config(self, path: str) -> dict:
        with open(path, 'r') as f:
            return json.load(f)

    def setup_keypair(self):
        try:
            private_key = os.getenv('SOLANA_PRIVATE_KEY')
            if not private_key:
                raise ValueError("SOLANA_PRIVATE_KEY not found")
            
            keypair_bytes = base58.b58decode(private_key)
            self.config["wallet"]["keypair_bytes"] = [b for b in keypair_bytes]
            
            keypair = Keypair.from_bytes(keypair_bytes)
            self.logger.info(f"Keypair loaded: {keypair.pubkey()}")
            
        except Exception as e:
            raise ValueError(f"Keypair setup failed: {str(e)}")

    def is_sol_pair(self, token_mint: str) -> bool:
        return token_mint in [SOL_MINT, WSOL_MINT]

    async def connect_jupiter_ws(self):
        """Connect to Jupiter WebSocket for price data"""
        while True:
            try:
                uri = self.config["rpc"]["quicknode"]["ws_endpoint"]
                self.logger.info(f"Connecting to Jupiter price feed: {uri}")
                
                headers = {
                    "Authorization": f"Bearer {self.config['rpc']['quicknode']['api_key']}"
                }
                
                async with websockets.connect(uri, extra_headers=headers) as ws:
                    self.logger.info("Connected to Jupiter WebSocket")
                    
                    while True:
                        try:
                            # Subscribe to new tokens
                            for token in self.tracked_tokens:
                                if token not in self.price_subscriptions:
                                    subscribe_msg = {
                                        "jsonrpc": "2.0",
                                        "id": f"price-{token[:8]}",
                                        "method": "jupiterPriceSubscribe",
                                        "params": [token]
                                    }
                                    await ws.send(json.dumps(subscribe_msg))
                                    self.price_subscriptions.add(token)
                                    self.logger.info(f"Subscribed to price updates for {token}")
                            
                            msg = await ws.recv()
                            data = json.loads(msg)
                            await self.handle_price_update(data)
                            
                        except websockets.ConnectionClosed:
                            self.logger.warning("Jupiter WebSocket closed")
                            break
                        except Exception as e:
                            self.logger.error(f"Error processing Jupiter price: {str(e)}")
                            continue
                            
            except Exception as e:
                self.logger.error(f"Jupiter WebSocket connection error: {str(e)}")
                await asyncio.sleep(5)

    async def handle_price_update(self, data: dict):
        """Handle Jupiter price updates"""
        try:
            if "params" not in data or "result" not in data["params"]:
                return
                
            price_data = data["params"]["result"]
            token = price_data.get("mint")
            price = float(price_data.get("price", 0))
            
            if not token or token not in self.token_metrics:
                return
                
            metrics = self.token_metrics[token]
            metrics.current_price = price
            
            await self.check_trading_opportunity(token)
            
        except Exception as e:
            self.logger.error(f"Price update error: {str(e)}")

    async def connect_marga_ws(self):
        while True:
            try:
                uri = self.config["helius"]["mainnet_url"]
                self.logger.info(f"Connecting to Marga: {uri}")
                
                headers = {
                    "Content-Type": "application/json",
                    "Authorization": f"Bearer {self.config['helius']['api_key']}"
                }
                
                async with websockets.connect(uri, extra_headers=headers) as ws:
                    self.logger.info("Connected to Marga WebSocket")
                    
                    subscribe_msg = {
                        "jsonrpc": "2.0",
                        "id": 1,
                        "method": "programSubscribe",
                        "params": [
                            RAYDIUM_PROGRAM_ID,
                            {
                                "encoding": "jsonParsed",
                                "commitment": "processed"
                            }
                        ]
                    }
                    
                    await ws.send(json.dumps(subscribe_msg))
                    
                    while True:
                        try:
                            msg = await ws.recv()
                            self.logger.info("Received WebSocket message")
                            data = json.loads(msg)
                            await self.handle_market_data(data)
                            
                        except websockets.ConnectionClosed:
                            self.logger.warning("Marga WebSocket closed")
                            break
                        except Exception as e:
                            self.logger.error(f"Error processing message: {str(e)}")
                            continue
                            
            except Exception as e:
                self.logger.error(f"WebSocket connection error: {str(e)}")
                await asyncio.sleep(5)

    async def handle_market_data(self, data: dict):
        """Process market data with debug logging"""
        try:
            if not isinstance(data, dict) or "params" not in data:
                self.logger.debug(f"Skipping invalid data format: {data}")
                return
                
            # Log raw data
            self.logger.debug(f"Raw WebSocket data: {json.dumps(data, indent=2)}")
            
            params = data.get("params", {})
            result = params.get("result", {})
            value = result.get("value", {})
            account = value.get("account", {})
            account_data = account.get("data", [None])[0]
            
            if not account_data:
                self.logger.debug("No account data found")
                return
                
            pubkey = value.get("pubkey", "unknown")
            self.logger.debug(f"Processing account: {pubkey}")
            
            # Log base64 data
            self.logger.debug(f"Account data (first 100 chars): {account_data[:100]}")
                
            pool_data = self.parse_raydium_pool(account_data)
            if pool_data is not None:
                self.logger.debug(f"Parsed pool data: {pool_data}")
                
                metrics = TokenMetrics(
                    mint_address=pool_data.token_mint,
                    current_price=pool_data.price,
                    liquidity=pool_data.liquidity,
                    volume_5min=pool_data.volume_24h / 288,
                    buyer_ratio=50.0,
                    last_update=time.time()
                )
                
                if metrics.current_price > 0:
                    self.logger.debug(f"Valid price found: {metrics.current_price}")
                    self.token_metrics[pool_data.token_mint] = metrics
                    self.logger.info(f"""
Pool data for {pubkey}:
Token: {pool_data.token_mint[:8]}...
Price: {pool_data.price:.8f} SOL
Volume 24h: {pool_data.volume_24h:.2f} SOL
Liquidity: {pool_data.liquidity:.2f} SOL
                    """)
                    
                    if pool_data.token_mint not in self.tracked_tokens:
                        self.tracked_tokens.add(pool_data.token_mint)
                        self.logger.info(f"New token tracked: {pool_data.token_mint[:8]}...")
                        
                    await self.check_trading_opportunity(pool_data.token_mint)
                else:
                    self.logger.debug(f"Invalid price: {metrics.current_price}")
                    
        except Exception as e:
            self.logger.error(f"Market data processing error: {str(e)}")
            # Log full error traceback
            import traceback
            self.logger.error(traceback.format_exc())
    async def check_trading_opportunity(self, token: str):
        try:
            metrics = self.token_metrics[token]
            
            if all([
                metrics.current_price > 0,
                metrics.volume_5min >= self.config["trading"]["min_volume"],
                token not in self.active_trades,
                len(self.active_trades) < self.config["trading"]["max_active_trades"],
                time.time() - self.last_trade_time >= (1.0 / self.config["trading"]["trades_per_second"])
            ]):
                await self.execute_trade(token, metrics.current_price)
                
        except Exception as e:
            self.logger.error(f"Trading check error: {str(e)}")
    def parse_raydium_pool(self, account_data: str) -> Optional[RaydiumPoolData]:
        """Parse Raydium pool data"""
        try:
            raw_data = base64.b64decode(account_data)
            
            if len(raw_data) < 752:
                return None
                
            # Get version and flags
            version = struct.unpack('<Q', raw_data[0:8])[0]
            status_flags = struct.unpack('<Q', raw_data[8:16])[0]
            
            # Get token mint address
            token_mint_data = raw_data[72:104]  # 32 bytes for pubkey
            token_mint = base58.b58encode(token_mint_data).decode('utf-8')
            
            # Get reserves for price calculation
            reserve_0 = int.from_bytes(raw_data[200:208], 'little')
            reserve_1 = int.from_bytes(raw_data[208:216], 'little')
            
            # Calculate price from reserves
            if reserve_0 > 0:
                price = (reserve_1 / 1e9) / (reserve_0 / 1e9)
            else:
                price = 0
                
            # Get volume and liquidity data
            volume = int.from_bytes(raw_data[296:304], 'little') / 1e9
            liquidity = int.from_bytes(raw_data[360:368], 'little') / 1e9
            
            # Create pool data object
            pool_data = RaydiumPoolData(
                version=version,
                token_mint=token_mint,
                base_vault=SOL_MINT,
                price=price,
                volume_24h=volume,
                fees_24h=volume * 0.0025,  # 0.25% fee
                liquidity=liquidity,
                buyer_ratio=0.0  # Will get from Jupiter
            )
            
            # Validate the data
            if self.validate_pool_data(pool_data):
                return pool_data
            return None
            
        except Exception as e:
            self.logger.error(f"Pool parsing error: {str(e)}")
            return None
            
    def validate_pool_data(self, pool_data: RaydiumPoolData) -> bool:
        """Validate pool data is within reasonable ranges"""
        try:
            # Price validation
            if not (0 < pool_data.price <= 1000):
                self.logger.debug(f"Invalid price: {pool_data.price} SOL")
                return False
                
            # Volume validation
            if pool_data.volume_24h > 1000000:  # 1M SOL daily volume cap
                self.logger.debug(f"Suspicious volume: {pool_data.volume_24h} SOL")
                return False
                
            # Liquidity validation
            min_liquidity = self.config["trading"].get("min_liquidity", 75.0)
            max_liquidity = self.config["trading"].get("max_liquidity", 20000.0)
            
            if not (min_liquidity <= pool_data.liquidity <= max_liquidity):
                self.logger.debug(f"Liquidity outside range: {pool_data.liquidity} SOL")
                return False
            
            return True
            
        except Exception:
            return False
    async def execute_trade(self, token: str, price: float):
        """Execute trade through the trading core"""
        try:
            result = self.trading_core.buy_token(token, self.position_size)
            
            if result["status"] == "success":
                self.active_trades[token] = {
                    "entry_price": price,
                    "entry_time": time.time(),
                    "position_size": self.position_size
                }
                
                self.last_trade_time = time.time()
                self.logger.info(f"Opened trade: {token} at {price:.6f} SOL")
                
        except Exception as e:
            self.logger.error(f"Trade execution error: {str(e)}")

    async def manage_positions(self):
        """Monitor and manage open positions"""
        while True:
            try:
                current_time = time.time()
                
                for token, trade in list(self.active_trades.items()):
                    if token not in self.token_metrics:
                        continue
                    
                    metrics = self.token_metrics[token]
                    profit_percent = (metrics.current_price - trade["entry_price"]) / trade["entry_price"] * 100
                    time_in_trade = current_time - trade["entry_time"]
                    
                    if profit_percent >= self.config["trading"]["take_profit"] or time_in_trade >= self.config["trading"]["max_trade_time"]:
                        await self.close_position(token, metrics.current_price, profit_percent)
                
                await asyncio.sleep(0.1)
                
            except Exception as e:
                self.logger.error(f"Position management error: {str(e)}")
                await asyncio.sleep(1)

    async def close_position(self, token: str, price: float, profit_percent: float):
        """Close position and update metrics"""
        try:
            trade = self.active_trades[token]
            result = self.trading_core.sell_token(token, trade["position_size"])
            
            if result["status"] == "success":
                self.total_trades += 1
                profit = trade["position_size"] * (profit_percent / 100)
                self.total_profit += profit
                
                if profit_percent > 0:
                    self.winning_trades += 1
                    
                    if self.winning_trades % self.config["trading"]["trades_to_scale"] == 0:
                        new_size = min(
                            self.position_size + self.config["trading"]["position_increment"],
                            self.config["trading"]["max_position_size"]
                        )
                        if new_size != self.position_size:
                            self.logger.info(f"Scaling position size: {self.position_size:.4f} -> {new_size:.4f}")
                            self.position_size = new_size
                
                self.logger.info(f"Closed position: {token} at {price:.6f} SOL, Profit: {profit_percent:.2f}%")
                del self.active_trades[token]
                
        except Exception as e:
            self.logger.error(f"Position closing error: {str(e)}")

    async def display_metrics(self):
        """Display performance metrics"""
        while True:
            try:
                os.system('cls' if os.name == 'nt' else 'clear')
                
                runtime = time.time() - self.start_time
                win_rate = (self.winning_trades / self.total_trades * 100) if self.total_trades > 0 else 0
                
                print("\nRaydium Scalper Status")
                print("=" * 40)
                print(f"Total Trades: {self.total_trades}")
                print(f"Win Rate: {win_rate:.2f}%")
                print(f"Total Profit: {self.total_profit:.4f} SOL")
                print(f"Position Size: {self.position_size:.4f} SOL")
                print(f"Active Trades: {len(self.active_trades)}")
                print(f"Runtime: {str(timedelta(seconds=int(runtime)))}")
                
                if self.token_metrics:
                    print("\nTop Tokens")
                    print("-" * 40)
                    sorted_tokens = sorted(
                        [m for m in self.token_metrics.values() if m.current_price > 0],
                        key=lambda x: x.volume_5min,
                        reverse=True
                    )[:5]
                    
                    for metrics in sorted_tokens:
                        symbol = metrics.symbol if metrics.symbol else metrics.mint_address[:8] + "..."
                        print(
                            f"{symbol}: {metrics.current_price:.8f} SOL, "
                            f"Vol: {metrics.volume_5min:.2f}, "
                            f"B/S: {metrics.buyer_ratio:.2f}%"
                        )
               
                await asyncio.sleep(1)
               
            except Exception as e:
                self.logger.error(f"Metrics display error: {str(e)}")
                await asyncio.sleep(1)
    async def run(self):
        """Main execution loop"""
        try:
            self.logger.info(f"""
Starting Raydium Scalper:
- Initial Size: {self.config["trading"]["initial_size"]} SOL
- Take Profit: {self.config["trading"]["take_profit"]}%
- Max Trade Time: {self.config["trading"]["max_trade_time"]}s
- TPS Limit: {self.config["trading"]["trades_per_second"]}
""")
            
            await asyncio.gather(
                self.connect_marga_ws(),
                self.connect_jupiter_ws(),
                self.manage_positions(),
                self.display_metrics()
            )
            
        except Exception as e:
            self.logger.error(f"Runtime error: {str(e)}")
            await self.emergency_shutdown()
    async def run(self):
        """Main execution loop"""
        try:
            self.logger.info(f"""
Starting Raydium Scalper:
- Initial Size: {self.config["trading"]["initial_size"]} SOL
- Take Profit: {self.config["trading"]["take_profit"]}%
- Max Trade Time: {self.config["trading"]["max_trade_time"]}s
- TPS Limit: {self.config["trading"]["trades_per_second"]}
""")
            
            # Start all components
            await asyncio.gather(
                self.connect_marga_ws(),
                self.manage_positions(),
                self.display_metrics()
            )
            
        except Exception as e:
            self.logger.error(f"Runtime error: {str(e)}")
            await self.emergency_shutdown()

    async def emergency_shutdown(self):
        """Emergency shutdown procedure"""
        self.logger.info("Emergency shutdown initiated")
        try:
            for token in list(self.active_trades.keys()):
                if token in self.token_metrics:
                    metrics = self.token_metrics[token]
                    await self.close_position(token, metrics.current_price, 0)
                    
            if self.vector_store is not None:
                self.vector_store.cleanup()
                
            if torch.cuda.is_available():
                torch.cuda.empty_cache()
                
        except Exception as e:
            self.logger.error(f"Shutdown error: {str(e)}")
        finally:
            self.logger.info("Shutdown complete")

if __name__ == "__main__":
    scalper = RaydiumScalper("config.json")
    try:
        asyncio.run(scalper.run())
    except KeyboardInterrupt:
        print("\nShutdown initiated...")
        asyncio.run(scalper.emergency_shutdown())
    except Exception as e:
        print(f"\nCritical error: {str(e)}")
        asyncio.run(scalper.emergency_shutdown())