
    Zil                    L   d Z ddlmZ ddlmZ ddlmZ ddlZddl	Z
	 ddlZdZed   ZddZdd	dd
Ze G d d             Zedk(  rG e         e       Zej-                  dd      Z eej3                                 ed ee             yy# e$ rZdZeZY dZ[zdZ[ww xY w)a  
Historical market data loading and normalization for a multi-timeframe system.

- Daily bars: macro momentum filter (e.g. SPY/QQQ regime).
- Intraday bars (1h / 15m): micro mean-reversion / stat-arb style signals.

Dependencies: pandas, numpy, yfinance (install: pip install yfinance).
    )annotations)	dataclass)LiteralN)15m30m60m1h1dc                 4    t         t        dt               y )NzSyfinance is required. Install with: python -m pip install yfinance
Original error: )yfImportError_YF_IMPORT_ERROR     >/opt/rentech/trading_bot/RenTech/strategy_stack/data_loader.py_require_yfinancer      s)    	z/02
 	
 r   T)prefer_adjustedc                  | j                   rt        j                         S | j                         }t	        |j
                  t        j                        rm|j
                  j                  dkD  rT|j
                  j                  dk(  r|j
                  j                  d      n|j
                  j                  d      |_        dddddd	d
}|j                  |j                         D ci c]  \  }}||j
                  v s|| c}}      }|rd|j
                  v r|d   |d<   g d}|D cg c]  }||j
                  vs| }}|r$t        d| dt        |j
                               ||   j                  t        j                         }|j#                         }||j$                  j'                  d          }|S c c}}w c c}w )z
    Normalize yfinance output to lowercase OHLCV columns with a DatetimeIndex.

    Handles both single-ticker (flat columns) and occasional MultiIndex columns.
          r   openhighlowclose	adj_closevolume)OpenHighLowClosez	Adj CloseVolume)columns)r   r   r   r   r   z0Expected OHLCV columns missing after normalize: z. Got: last)keep)emptypd	DataFramecopy
isinstancer"   
MultiIndexnlevels	droplevelget_level_valuesrenameitems
ValueErrorlistastypenpfloat64
sort_indexindex
duplicated)	dfr   out
rename_mapkvrequiredcmissings	            r   _standardize_ohlcvr@   &   s    
xx||~
'')C#++r}}-;;"69kk6I6IQ6N#++//2TWT_T_TpTpqrTsCK  J **z/?/?/AVtq!Q#++EUadV*
WC;#++5;'G9H";Qas{{&:q;G;KG9T[\`adalal\m[nopp
h-

rzz
*C
..
C
syy###00
1CJ W <s   )G
 G
.GGc                      e Zd ZU dZdZded<   	 dddd	 	 	 	 	 	 	 	 	 ddZddddd		 	 	 	 	 	 	 	 	 	 	 dd
Zdd	 	 	 	 	 ddZy)
DataLoaderz
    Fetch and clean OHLCV history from Yahoo Finance.

    Example
    -------
    >>> loader = DataLoader()
    >>> daily = loader.fetch_daily("SPY", period="5y")
    >>> hourly = loader.fetch_intraday("AAPL", interval="1h", period="60d")
    Fboolauto_adjustN)startendperiodc               @   t                t        j                  |      }|r|j                  |d| j                        }n|j                  ||d| j                        }t        |      }t        j                  |j                        j                  d      |_        |S )z
        Load daily OHLCV for momentum / regime models.

        Provide either (start & end) or period (e.g. '5y', 'max'), not both if yfinance conflicts.
        r
   rG   intervalrD   rE   rF   rJ   rD   N)
r   r   TickerhistoryrD   r@   r&   to_datetimer6   tz_localize)selftickerrE   rF   rG   trawr9   s           r   fetch_dailyzDataLoader.fetch_daily]   s     	IIf))6DdFVFV)WC))%S4TM]M])^C %NN399-99$?	
r   r	   )rJ   rE   rF   rG   c                  t                |dv rdn|}t        j                  |      }|r|j                  ||| j                        }n|j                  |||| j                        }t        |      }	t        j                  |	j                        |	_        |	j                  j                  /|	j                  j                  d      j                  d      |	_        |	S )z
        Load intraday OHLCV for mean-reversion / rolling z-score engines.

        Note: Yahoo limits intraday depth (often ~730 days for hourly; shorter for 15m).
        Prefer `period='60d'` or similar when using 15m bars.
        )r	   r   r   rI   rK   NUTC)r   r   rL   rM   rD   r@   r&   rN   r6   tz
tz_convertrO   )
rP   rQ   rJ   rE   rF   rG   ivrR   rS   r9   s
             r   fetch_intradayzDataLoader.fetch_intradayt   s     	-/UXIIf))6BDDTDT)UC))%S24K[K[)\C %NN399-	99<<#		,,U3??ECI
r   zAmerica/New_York)day_tzc               B   |j                   r|S |j                  }|r@|j                  |j                  d      n|j	                  d      }|j	                  |      }n|}|j                         }t        j                  |j                         j                        |d<   |S )z
        Optional: assign a calendar date column for merging intraday bars with daily regime.

        Intraday index is timestamp; we add `trade_date` as the session date in `day_tz`.
        rV   
trade_date)
r%   r6   rW   rO   rX   r(   r&   rN   	normalizedate)rP   intradayr[   idxtsr9   s         r   align_to_trading_daysz DataLoader.align_to_trading_days   s     >>Onn+.66>'s~~e?TBv&BBmmoNN2<<>+>+>?L
r   )
rQ   strrE   str | pd.Timestamp | NonerF   re   rG   
str | Nonereturnpd.DataFrame)rQ   rd   rJ   IntradayIntervalrE   re   rF   re   rG   rf   rg   rh   )r`   rh   r[   rf   rg   rh   )	__name__
__module____qualname____doc__rD   __annotations__rT   rZ   rc   r   r   r   rB   rB   N   s     Ki ,0)-! )	
 '  
6 &*+/)-! #	
 ) '  
B 0	 	
 
r   rB   __main__SPY6mo)rG   rows)rg   None)r8   rh   r   rC   rg   rh   )rm   
__future__r   dataclassesr   typingr   numpyr3   pandasr&   yfinancer   r   r   eri   r   r@   rB   rj   dlrT   dprinttaillenr   r   r   <module>r      s    # !   
  :; 
 EI %P W W Wt z	B
uU+A	!&&(O	&#a& k  	Bs   B B#BB#