"""Locks the marginal-vs-TP01 scorer (altlib) — the harness fix from the 2026-06-20 sweep. The point: absolute Sharpe is not enough to earn a portfolio slot. A candidate must IMPROVE the TP01 baseline out-of-sample. These tests pin the invariants: * the TP01 baseline reproduces the canonical ~1.30 full Sharpe, * TP01-vs-itself is REDUNDANT (zero marginal), * a flat (do-nothing) sleeve never earns a slot. """ import sys from pathlib import Path import numpy as np ROOT = Path(__file__).resolve().parents[1] sys.path.insert(0, str(ROOT / "scripts" / "research" / "alt")) import altlib as al # noqa: E402 from src.strategies.trend_portfolio import CANONICAL, TrendPortfolio # noqa: E402 def test_tp01_baseline_reproduces_canonical(): r = al.tp01_baseline_daily().values sharpe = float(np.mean(r) / np.std(r) * np.sqrt(365.25)) assert 1.1 < sharpe < 1.5, f"TP01 baseline Sharpe {sharpe:.2f} off canonical ~1.30" def test_tp01_vs_itself_is_redundant(): cand = al.candidate_daily(lambda df: TrendPortfolio(**CANONICAL).target_series(df)) m = al.marginal_vs_tp01(cand) assert m["corr_full"] > 0.95 assert abs(m["blends"]["w25"]["uplift_full"]) < 0.05 assert m["marginal_verdict"] == "REDUNDANT" assert al.study_marginal("tp01-self", lambda df: TrendPortfolio(**CANONICAL).target_series(df))["earns_slot"] is False def test_flat_sleeve_earns_no_slot(): m = al.marginal_vs_tp01(al.candidate_daily(lambda df: np.zeros(len(df)))) assert m["marginal_verdict"] != "ADDS" def test_call_target_passes_asset_when_accepted(): seen = {} def two_arg(df, asset): seen[asset] = True return np.zeros(len(df)) al.candidate_daily(two_arg) assert seen == {"BTC": True, "ETH": True} # --- hardening gates (2026-06-21 ortho wave) ------------------------------------------- # A low-corr asset adds ~+0.03 Sharpe by pure diversification MATH; a sleeve that only # pays when TP01 is weak is a HEDGE; an edge living in one late window is NOT robust. # These pin that the scorer rejects all three, but still PASSES a real high-Sharpe # uncorrelated sleeve (the diversification of a genuine return stream IS value). import pandas as pd # noqa: E402 def _tp01_index(): return al.tp01_baseline_daily().index def test_noise_sleeve_is_not_adds(): """Near-zero-Sharpe, zero-corr asset = diversification math, not signal -> not ADDS.""" idx = _tp01_index() rng = np.random.default_rng(1) c = pd.Series(rng.normal(0.0001, 0.02, len(idx)), index=idx) m = al.marginal_vs_tp01(c) assert m["marginal_verdict"] != "ADDS" assert m["beats_noise_null"] is False def test_high_sharpe_uncorrelated_is_not_rejected_as_noise(): """A genuine Sharpe~1.3 uncorrelated sleeve (XS01-like) must NOT be called NOISE.""" idx = _tp01_index() rng = np.random.default_rng(2) c = pd.Series(rng.normal(0.0011, 0.013, len(idx)), index=idx) m = al.marginal_vs_tp01(c) assert m["beats_noise_null"] is True assert m["marginal_verdict"] == "ADDS" def test_hedge_only_when_tp01_weak_is_flagged(): """A sleeve that pays only when TP01 trails down is a HEDGE, not alpha -> no slot.""" B = al.tp01_baseline_daily() trail = B.rolling(60, min_periods=20).sum().shift(1) base = np.where(trail.values <= 0, 0.004, -0.001) rng = np.random.default_rng(4) c = pd.Series(base + rng.normal(0, 0.004, len(B)), index=B.index) m = al.marginal_vs_tp01(c) assert m["is_hedge"] is True assert m["marginal_verdict"] == "HEDGE" def test_flat_in_sample_late_edge_earns_no_slot(): """An edge FLAT in-sample that only appears in the recent window has NO standalone in-sample merit -> NOISE (not ADDS), no slot. This is the ortho 2025-window pattern.""" B = al.tp01_baseline_daily() rng = np.random.default_rng(3) c = pd.Series(0.0, index=B.index) # exactly flat in-sample hold = B.index >= al.HOLDOUT c[hold] = 0.004 + rng.normal(0, 0.002, int(hold.sum())) # edge only in the hold-out m = al.marginal_vs_tp01(c) assert m["has_insample_edge"] is False assert m["marginal_verdict"] == "NOISE" assert al.marginal_vs_tp01(c)["marginal_verdict"] != "ADDS" def test_pre_holdout_underperformer_earns_no_slot(): """A sleeve with no real in-sample standalone edge (it bleeds before the hold-out and only wins in the recent window) never earns a slot — the 2025-only ortho pattern.""" B = al.tp01_baseline_daily() early = B.index < al.HOLDOUT rng = np.random.default_rng(5) c = pd.Series(0.0, index=B.index) c[early] = -0.0008 + rng.normal(0, 0.012, int(early.sum())) # weak/negative in-sample c[~early] = 0.010 + rng.normal(0, 0.012, int((~early).sum())) # strong only post-hold-out m = al.marginal_vs_tp01(c) assert m["cand_insample_sharpe"] < 0.5 assert m["has_insample_edge"] is False assert m["marginal_verdict"] != "ADDS"