""" Data normalization utilities. This module provides functions for normalizing various data formats to consistent standards across the application. """ from typing import Optional from logging import Logger def normalize_trade_side( side: str, logger: Optional[Logger] = None, component_name: str = "normalization" ) -> str: """ Normalize trade side to standard format. Args: side: Raw trade side string logger: Optional logger for error messages component_name: Name for logging Returns: Normalized side ('buy' or 'sell') Raises: ValueError: If side is invalid, empty, or unknown """ if not side or not isinstance(side, str): error_msg = f"Invalid trade side: {side}" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) normalized = side.lower().strip() # Handle common variations if normalized in ['buy', 'bid', 'b', '1']: return 'buy' elif normalized in ['sell', 'ask', 's', '0', '2']: return 'sell' else: error_msg = f"Invalid trade side: {side}" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) def validate_symbol_format( symbol: str, logger: Optional[Logger] = None, component_name: str = "normalization" ) -> str: """ Validate and normalize symbol format. Args: symbol: Trading symbol logger: Optional logger for error messages component_name: Name for logging Returns: Normalized symbol Raises: ValueError: If symbol is invalid """ if not symbol or not isinstance(symbol, str): error_msg = f"Invalid symbol: {symbol}" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) # Remove whitespace and convert to uppercase normalized = symbol.strip().upper() # Basic validation if not normalized or len(normalized) < 3: error_msg = f"Symbol too short: {symbol}" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) # Check for common delimiters if '-' not in normalized and '/' not in normalized: error_msg = f"Invalid symbol format (missing delimiter): {symbol}" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) return normalized def normalize_exchange_name( exchange: str, logger: Optional[Logger] = None, component_name: str = "normalization" ) -> str: """ Normalize exchange name. Args: exchange: Exchange name logger: Optional logger for error messages component_name: Name for logging Returns: Normalized exchange name Raises: ValueError: If exchange name is invalid """ if not exchange or not isinstance(exchange, str): error_msg = f"Invalid exchange name: {exchange}" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) normalized = exchange.lower().strip() if not normalized: error_msg = "Exchange name cannot be empty" if logger: logger.error(f"{component_name}: {error_msg}") raise ValueError(error_msg) return normalized