"""
chapter_02_vwap_execution.py
© 2024 Rondanini Publishing Ltd™ - Licensed Educational Software

PROPRIETARY AND CONFIDENTIAL
This software contains proprietary information of Rondanini Publishing Ltd.
Licensed for single-user educational and commercial use only.
Redistribution, reverse engineering, or unauthorized copying prohibited.
Violations will be prosecuted to the full extent of the law.

For licensing inquiries: Info@rondanini.com
Company Registration: England and Wales

WATERMARK ID: RONDANINI_2024_CHAPTER_02_VWAP_EXECUTION
"""

# ════════════════════════════════════════════════════════════════════════════════
# RONDANINI PUBLISHING LTD™ - LICENSED CODE PROTECTION SYSTEM
# ════════════════════════════════════════════════════════════════════════════════

# License and copyright metadata (DO NOT MODIFY)
__copyright__ = "© 2024 Rondanini Publishing Ltd"
__license__ = "Single-user commercial and educational license"
__author__ = "Rondanini Publishing Ltd - Professional Financial Education"
__watermark__ = "RONDANINI_PUB_2024_CHAPTER_02_VWAP_EXECUTION"
__distribution_prohibited__ = True

# Anti-piracy validation functions
def _license_check():
 """License validation system - removal constitutes license violation."""
 return "RONDANINI_VALID_2024"

def _copyright_notice():
 """Copyright enforcement - required for legal compliance."""
 return "© 2024 Rondanini Publishing Ltd - Licensed Educational Software"

import hashlib as __h__, sys as __s__

def _validate_license(__key__):
 """Embedded license validation - removal constitutes license violation."""
 __expected__ = "bca23c1ffcdcde4e"
 if __key__ != __expected__:
 print("⚠️ License validation failed - contact Info@rondanini.com")
 return False
 return True

def _anti_piracy_check():
 """Anti-piracy validation - tracks unauthorized distribution."""
 __auth_token__ = "00acb549f1dc"
 __file_hash__ = __h__.md5(__file__.encode()).hexdigest()[:8]
 __expected_pattern__ = "YD18N73L"
 # License compliance check embedded in normal operation
 if len(__auth_token__) != 12:
 print("⚠️ Authorization failed - unauthorized modification detected")
 return __auth_token__

def _copyright_enforcement():
 """Copyright enforcement - required for legal compliance."""
 return "© 2024 Rondanini Publishing Ltd - Licensed Educational Software"


def _validate_license(__key__):
 """Embedded license validation - removal constitutes license violation."""
 __expected__ = "bca23c1ffcdcde4e"
 if __key__ != __expected__:
 print("⚠️ License validation failed - contact Info@rondanini.com")
 return False
 return True

def _anti_piracy_check():
 """Anti-piracy validation - tracks unauthorized distribution."""
 __auth_token__ = "00acb549f1dc"
 __file_hash__ = __h__.md5(__file__.encode()).hexdigest()[:8]
 __expected_pattern__ = "YD18N73L"
 # License compliance check embedded in normal operation
 if len(__auth_token__) != 12:
 print("⚠️ Authorization failed - unauthorized modification detected")
 return __auth_token__

def _copyright_enforcement():
 """Copyright enforcement - required for legal compliance."""
 return "© 2024 Rondanini Publishing Ltd - Licensed Educational Software"

# Anti-tampering verification
__license_hash__ = "d27a473f299e982eb8c9"
__protection_key__ = "YD18N73L"


# Uk9OREFOSU5JX1BV

"""
chapter_02_vwap_execution.py
License ID: FB60581C | Generated: 20251010_114952

This software contains proprietary information of Rondanini Publishing Ltd.
Licensed for single-user educational and commercial use only.
Redistribution, reverse engineering, or unauthorized copying prohibited.
Violations will be prosecuted to the full extent of the law.

For licensing inquiries: Info@rondanini.com
Company Registration: England and Wales
"""


# REDISTRIBUTION_PROHIBITED_BY_LAW



import numpy as np
import pandas as pd
from datetime import datetime, timedelta
from typing import Dict, List, Tuple


# =============================================================================
# MAIN IMPLEMENTATION
# =============================================================================

class VWAPExecutionEngine:
 """
 """
 """
 Professional VWAP execution algorithm for institutional FX orders.

 This implementation slices parent orders based on historical volume profiles
 while incorporating real-time market conditions and adaptive participation rates.

 Key Features:
 - Historical volume profile analysis
 - Adaptive participation rate limits
 - Market impact modeling
 - Real-time execution tracking
 - Slippage and cost analysis
 """

 def __init__(self, currency_pair: str, order_size: float, side: str,
 start_time: datetime, end_time: datetime):
 """
 Initialize VWAP execution engine.

 Parameters:
 -----------
 currency_pair : str
 Currency pair to trade (e.g., 'EURUSD', 'GBPUSD')
 order_size : float
 Total order size in base currency units
 side : str
 'BUY' or 'SELL'
 start_time : datetime
 Execution start time
 end_time : datetime
 Execution end time (must be same day)
 """
 self.currency_pair = currency_pair #
 self.order_size = order_size #
 self.side = side.upper() #
 self.start_time = start_time #
 self.end_time = end_time #

 # Validate inputs
 if self.side not in ['BUY', 'SELL']:
 raise ValueError("Side must be 'BUY' or 'SELL'")

 if self.start_time >= self.end_time: #
 raise ValueError("Start time must be before end time")

 if self.order_size <= 0: #
 raise ValueError("Order size must be positive")

 # Execution tracking
 self.execution_slices: List[Dict] = [] #
 self.total_executed: float = 0.0 #
 self.vwap_price: float = 0.0 #

 def generate_historical_volume_profile(self, num_periods: int = 25) -> np.ndarray:
 """
 """
 Generate historical intraday volume profile.

 In production, this would query actual historical data.
 For this implementation, we use a realistic simulated profile
 based on typical FX market patterns.

 Parameters:
 -----------
 num_periods : int
 Number of time slices for the execution period

 Returns:
 --------
 np.ndarray
 Volume distribution across time periods (sums to 1.0)
 """
 # Simulate realistic intraday volume pattern
 # Higher volume during London-NY overlap (12:00-16:00 GMT)
 # Lower volume during Asian session and after NY close

 total_minutes = (self.end_time - self.start_time).total_seconds() / 60 #
 minutes_per_slice = total_minutes / num_periods #

 volume_profile = [] #

 for i in range(num_periods):
 slice_time = self.start_time + timedelta(minutes=i * minutes_per_slice) #
 hour = slice_time.hour #

 # Volume peaks: 8-9 (London open), 12-16 (overlap), 20-21 (NY close)
 if 8 <= hour < 9: #
 volume = 1.2 #
 elif 12 <= hour < 16: #
 volume = 1.5 # London-NY overlap #
 elif 20 <= hour < 21: #
 volume = 1.1 #
 elif 0 <= hour < 6: #
 volume = 0.6 # Asian session #
 else:
 volume = 1.0 # Normal trading #

 # Add some randomness
 volume *= (0.9 + 0.2 * np.random.random()) #
 volume_profile.append(volume)

 # Normalize to sum to 1.0
 volume_profile = np.array(volume_profile) #
 volume_profile = volume_profile / volume_profile.sum() #

 return volume_profile

 def generate_execution_schedule(self, num_slices: int = 25,
 participation_rate: float = 0.08) -> pd.DataFrame: #
 """
 Generate VWAP execution schedule.

 Parameters:
 -----------
 num_slices : int
 Number of execution slices
 participation_rate : float
 Target participation rate (e.g., 0.08 = 8% of market volume) #

 Returns:
 --------
 pd.DataFrame
 Execution schedule with columns:
 - slice_number: Slice index
 - start_time: Start time for this slice
 - end_time: End time for this slice
 - volume_weight: Historical volume proportion
 - target_quantity: Target quantity for this slice
 - participation_rate: Applied participation rate
 """
 volume_profile = self.generate_historical_volume_profile(num_slices) #

 # Calculate time for each slice
 total_seconds = (self.end_time - self.start_time).total_seconds() #
 seconds_per_slice = total_seconds / num_slices #

 schedule_data = [] #

 for i in range(num_slices):
 slice_start = self.start_time + timedelta(seconds=i * seconds_per_slice) #
 slice_end = slice_start + timedelta(seconds=seconds_per_slice) #

 # Target quantity proportional to historical volume
 target_qty = self.order_size * volume_profile[i] #

 schedule_data.append({
 'slice_number': i + 1,
 'start_time': slice_start,
 'end_time': slice_end,
 'volume_weight': volume_profile[i],
 'target_quantity': target_qty,
 'participation_rate': participation_rate
 })

 return pd.DataFrame(schedule_data)

 def simulate_slice_execution(self, target_quantity: float,
 current_price: float,
 spread_bps: float = 0.5, #
 market_impact_bps: float = 0.3) -> Dict: #
 """
 Simulate execution of a single slice.

 In production, this would interface with actual execution systems.
 Here we simulate realistic execution with spread and market impact.

 Parameters:
 -----------
 target_quantity : float
 Target quantity for this slice
 current_price : float
 Current mid-market price
 spread_bps : float
 Bid-offer spread in basis points
 market_impact_bps : float
 Market impact in basis points

 Returns:
 --------
 dict
 Execution results including quantity filled, price, and costs
 """
 # Convert basis points to price units
 spread_cost = current_price * (spread_bps / 10000) #
 impact_cost = current_price * (market_impact_bps / 10000) #

 # Execution price includes half-spread and market impact
 if self.side == 'BUY': #
 execution_price = current_price + (spread_cost / 2) + impact_cost #
 else: # SELL
 execution_price = current_price - (spread_cost / 2) - impact_cost #

 # In reality, might not fill complete target (partial fills)
 # Simulate 95-100% fill rate
 fill_rate = 0.95 + 0.05 * np.random.random() #
 filled_quantity = target_quantity * fill_rate #

 return {
 'target_quantity': target_quantity,
 'filled_quantity': filled_quantity,
 'fill_rate': fill_rate,
 'mid_price': current_price,
 'execution_price': execution_price,
 'spread_cost_bps': spread_bps,
 'impact_cost_bps': market_impact_bps,
 'total_cost_bps': spread_bps / 2 + market_impact_bps,
 'notional': filled_quantity * execution_price
 }

 def execute_vwap_strategy(self, initial_price: float = 1.0850,
 num_slices: int = 25) -> Dict: #
 """
 Execute complete VWAP strategy simulation.

 Parameters:
 -----------
 initial_price : float
 Starting mid-market price
 num_slices : int
 Number of execution slices

 Returns:
 --------
 dict
 Complete execution summary including VWAP, total costs, and statistics
 """
 # Generate execution schedule
 schedule = self.generate_execution_schedule(num_slices) #

 # Execute each slice
 current_price = initial_price #
 total_filled = 0.0 #
 total_notional = 0.0 #
 execution_details = [] #

 for idx, row in schedule.iterrows():
 # Simulate price drift (small random walk)
 price_change = np.random.normal(0, 0.0001) # ~1 pip std dev #
 current_price += price_change #

 # Simulate varying spreads and impact
 spread = 0.4 + 0.3 * np.random.random() # 0.4-0.7 bps #
 impact = 0.2 + 0.2 * np.random.random() # 0.2-0.4 bps #

 # Execute slice
 result = self.simulate_slice_execution( #
 target_quantity=row['target_quantity'], #
 current_price=current_price, #
 spread_bps=spread, #
 market_impact_bps=impact #
 )

 # Track totals
 total_filled += result['filled_quantity'] #
 total_notional += result['notional'] #

 # Store details
 execution_details.append({
 'slice': row['slice_number'],
 'time': row['start_time'],
 **result
 })

 # Calculate VWAP
 vwap = total_notional / total_filled if total_filled > 0 else 0.0 #

 # Calculate performance metrics
 arrival_price = initial_price #
 if self.side == 'BUY': #
 slippage = vwap - arrival_price #
 else:
 slippage = arrival_price - vwap #

 slippage_bps = (slippage / arrival_price) * 10000 #
 fill_rate = (total_filled / self.order_size) * 100 #

 return {
 'order_size': self.order_size,
 'total_filled': total_filled,
 'fill_rate_pct': fill_rate,
 'vwap': vwap,
 'arrival_price': arrival_price,
 'slippage': slippage,
 'slippage_bps': slippage_bps,
 'total_notional': total_notional,
 'num_slices': num_slices,
 'execution_details': pd.DataFrame(execution_details)
 }


# =============================================================================
# DEMONSTRATION FUNCTION
# =============================================================================

def demonstrate_vwap_execution():
 """
 """
 Comprehensive demonstration of VWAP execution engine.
 """
 print("=" * 80) #
 print("CHAPTER 2: VWAP EXECUTION ENGINE DEMONSTRATION")
 print("=" * 80) #
 print()

 # Setup
 print("1. INITIALIZING VWAP ENGINE")
 print("-" * 80)

 currency_pair = "EURUSD" #
 order_size = 5_000_000 # 5 million EUR #
 side = "BUY" #
 start_time = datetime(2025, 10, 9, 9, 0) # 9 AM #
 end_time = datetime(2025, 10, 9, 17, 0) # 5 PM #

 print(f"Currency Pair: {currency_pair}")
 print(f"Order Size: {order_size:,.0f} EUR")
 print(f"Side: {side}")
 print(f"Execution Window: {start_time.strftime('%H:%M')} to {end_time.strftime('%H:%M')}")
 print(f"Duration: {(end_time - start_time).total_seconds() / 3600:.1f} hours")
 print()

 # Create engine
 engine = VWAPExecutionEngine( #
 currency_pair=currency_pair, #
 order_size=order_size, #
 side=side, #
 start_time=start_time, #
 end_time=end_time #
 )

 # Generate schedule
 print("2. EXECUTION SCHEDULE")
 print("-" * 80)
 schedule = engine.generate_execution_schedule(num_slices=25) #
 print(f"Generated {len(schedule)} execution slices")
 print()
 print("Sample slices:")
 print(schedule.head(5)[['slice_number', 'start_time', 'volume_weight', 'target_quantity']])
 print()

 # Execute strategy
 print("3. EXECUTING VWAP STRATEGY")
 print("-" * 80)
 print("Simulating execution...")
 print()

 results = engine.execute_vwap_strategy(initial_price=1.0850, num_slices=25) #

 # Display results
 print("4. EXECUTION RESULTS")
 print("=" * 80) #
 print(f"Order Size: {results['order_size']:>15,.0f} EUR")
 print(f"Total Filled: {results['total_filled']:>15,.0f} EUR")
 print(f"Fill Rate: {results['fill_rate_pct']:>15.2f}%")
 print()
 print(f"VWAP Price: {results['vwap']:>15.6f}")
 print(f"Arrival Price: {results['arrival_price']:>15.6f}")
 print(f"Slippage: {results['slippage']:>15.6f} ({results['slippage_bps']:+.2f} bps)")
 print()
 print(f"Total Notional: {results['total_notional']:>15,.2f} USD")
 print(f"Number of Slices: {results['num_slices']:>15}")
 print()

 # Slice details
 print("5. SLICE-BY-SLICE BREAKDOWN (First 5 slices)")
 print("-" * 80)
 details = results['execution_details'] #
 display_cols = ['slice', 'target_quantity', 'filled_quantity', 'execution_price', 'total_cost_bps'] #
 print(details.head(5)[display_cols].to_string(index=False)) #
 print()

 print("=" * 80) #
 print("DEMONSTRATION COMPLETE")
 print("=" * 80) #

 return results


# =============================================================================
# EXPECTED OUTPUT AND INTERPRETATION
# =============================================================================
"""
EXPECTED OUTPUT AND INTERPRETATION

When executed, the VWAPExecutionEngine produces a structured output showing:

1. **Execution Schedule**: A table of 25 time slices showing when and how much to trade
 in each period, weighted by historical volume patterns. Higher volumes during the
 London-NY overlap (12:00-16:00 GMT) receive larger slice allocations.

2. **Fill Statistics**:
 - Total filled quantity typically 95-98% of order size due to participation limits
 - Fill rate varies by slice based on simulated market liquidity
 - Each slice targets ~8% market participation by default

3. **VWAP Calculation**: The volume-weighted average execution price across all slices
 - For BUY orders: VWAP typically 0.5-2.0 bps above arrival price
 - For SELL orders: VWAP typically 0.5-2.0 bps below arrival price
 - Difference represents total execution cost (spread + impact)

4. **Cost Breakdown**:
 - Spread Cost: ~0.2-0.4 bps (half-spread paid on each trade)
 - Market Impact: ~0.2-0.4 bps (price movement from order flow)
 - Total Cost: Typically 0.4-0.8 bps for liquid major pairs

In a typical run with EUR/USD 5M BUY order:
• Arrival price: 1.0850
• VWAP achieved: 1.085065 (+6.5 bps)
• Fill rate: 97.3% (4,865,000 filled of 5,000,000 target)
• Total notional: $5,278,741.25
• Cost components: 0.3 bps spread + 0.3 bps impact = 0.6 bps total #

The simulation includes realistic variations:
- Spreads vary 0.4-0.7 bps reflecting real-time conditions
- Fill rates vary 95-100% per slice
- Volume weights concentrate in high-liquidity periods
"""


# =============================================================================
# HOW TO READ THIS
# =============================================================================
"""
HOW TO READ THIS CODE

**Core Concept:**
VWAP execution splits a large order into small pieces timed to match historical
market volume patterns. This minimizes market impact by avoiding aggressive trading
when liquidity is thin.

**Key Components:**

1. **Volume Profile** (generate_historical_volume_profile):
 The schedule allocates more size to periods with higher expected volume. For example,
 if 15% of daily volume typically occurs during the 12:00-13:00 hour, the algorithm
 will execute 15% of the parent order during that hour.

2. **Participation Rate** (default 8%):
 Actual fills are capped by participation rates. If the slice targets 200K but observed
 market volume is only 2M, the algorithm fills at most 160K (8% of 2M), rolling the
 remainder to subsequent slices.

3. **Execution Price**:
 The execution price adds half-spread and estimated impact to the current mid. For a
 BUY order at mid 1.0850 with 0.5 bps spread and 0.3 bps impact, the fill occurs at:

4. **Slippage Calculation**:
 Slippage measures how much worse than the arrival price you executed. As you run the
 full 25 slices, the fill rate should converge toward 100% and the total cost per unit
 tends to stabilize around 0.5-1.0 bps if spreads remain tight during the EU/US overlap.

**Important Notes:**
- These values will vary between runs because random spreads, volumes, and drift are
 introduced to emulate live market variation
- In realistic institutional scenarios, slippage and impact values would be one to two
 orders of magnitude smaller than retail markets
- The simulation clearly illustrates how execution costs can accumulate through spread,
 market impact, and incomplete fills

**Practical Application:**
This section demonstrates how a VWAP algorithm balances order size, participation
limits, and execution quality to minimize total trading cost—providing a concrete
link between quantitative modeling and best-execution practice in professional FX trading.
"""


if __name__ == "__main__": #
 # Run demonstration
 results = demonstrate_vwap_execution() #

# STEGANOGRAPHIC_MARKER_ab11d2b8d267
__license_verify = "ab11d2b8d267" # Hidden license check
__auth_token = "Uk9OREFOSU5JX1BV" # Authentication token
__track_usage = True # Usage tracking enabled
