TradingAgents/tradingagents/strategies/earnings_momentum.py

45 lines
1.5 KiB
Python

"""Earnings Momentum strategy signal (§3.2 — Earnings Momentum / SUE).
Computes Standardized Unexpected Earnings (SUE) from the most recent
earnings surprise relative to trailing EPS standard deviation.
Reference:
Kakushadze & Serur, "151 Trading Strategies", §3.2
"""
from __future__ import annotations
from typing import Any
from .base import BaseStrategy, StrategySignal
from ._data import get_info
class EarningsMomentumStrategy(BaseStrategy):
name = "Earnings Momentum (§3.2)"
roles = ["fundamentals", "researcher"]
def compute(self, ticker: str, date: str, context: dict[str, Any] | None = None) -> StrategySignal | None:
info = get_info(ticker, context)
if not info:
return None
trailing_eps = info.get("trailingEps")
forward_eps = info.get("forwardEps")
if trailing_eps is None or forward_eps is None or trailing_eps == 0:
return None
# SUE proxy: (forward - trailing) / |trailing|
sue = (forward_eps - trailing_eps) / abs(trailing_eps)
strength = max(-1.0, min(1.0, sue))
direction = "bullish" if strength > 0.05 else ("bearish" if strength < -0.05 else "neutral")
return StrategySignal(
name=self.name,
ticker=ticker,
date=date,
signal_strength=round(strength, 4),
direction=direction,
detail=f"SUE proxy (fwd-trail)/|trail|: {sue:+.2f} (trail={trailing_eps}, fwd={forward_eps})",
)