fix(live): SH01 esegue shape-ML reale, non il wrapper squeeze scartato

Bug di wiring: runner.py avvolgeva lo sleeve SH01 nel MLWorkerWrapper legacy
di multi_runner, che usa SignalEngine (famiglia squeeze ML01 SCARTATA), apre
con Signal nudo ed esce a hold_bars=3 con tick() propria. Risultato: lo sleeve
"SH01" del portafoglio live NON eseguiva SH01_shape_ml (generate_signals mai
chiamata) e il fix horizon-exit era in un ramo morto -> SH01 continuava a
chiudere a hold_limit/3.

Fix: SH01 (kind="ml") gira come StrategyWorker normale. SH01_shape_ml.
generate_signals fa il walk-forward internamente ad ogni tick ed emette
metadata.max_bars=H=12 -> exit via StrategyWorker.tick (orizzonte H, fix
applicato). Rimosso l'import/uso di MLWorkerWrapper e il blocco train esterno.

ml_wf_entries ha train_min=4000 (>=4000 barre 1h per produrre segnali):
aggiunto _ML_LOOKBACK_DAYS=365 cosi gli asset di sleeve ml fetchano >=365g
(~8760 barre), senza dipendere dal fetch 440g di TSM01/ROT02. generate_signals
su 365g: 0,17-0,24s (logit) -> trascurabile sul poll 60s.

Test: test_build_ml_sh01_is_plain_strategyworker (StrategyWorker + strategy
SH01_shape_ml + niente engine squeeze). Suite: 51 passed.

Stato live: SH01 BTC/ETH flat -> contatori resettati (capitale preservato),
trade squeeze archiviati. Rebuild+recreate: 14 worker RESUME puliti, healthy.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Adriano Dal Pastro
2026-06-01 12:24:13 +00:00
parent 56565f6f73
commit 83c4e7a334
3 changed files with 103 additions and 14 deletions
+12
View File
@@ -18,3 +18,15 @@ def test_build_pairs_worker(tmp_path):
w = build_worker_for(spec, alloc_capital=200.0, leverage=2.0, data_dir=tmp_path)
assert isinstance(w, PairsWorker)
assert w.capital == 200.0
def test_build_ml_sh01_is_plain_strategyworker(tmp_path):
"""SH01 (kind=ml) deve costruirsi come StrategyWorker che esegue SH01_shape_ml — NON il
vecchio MLWorkerWrapper (SignalEngine squeeze scartato, che ignorava la strategia ed usciva
a hold_bars=3). Regressione del bug di wiring scoperto il 2026-06-01."""
spec = SleeveSpec(kind="ml", name="SH01", sid="SH_BTC", asset="BTC")
w = build_worker_for(spec, alloc_capital=58.82, leverage=2.0, data_dir=tmp_path)
assert isinstance(w, StrategyWorker)
assert w.strategy.name == "SH01_shape_ml" # esegue davvero shape-ML
assert not hasattr(w, "engine") # niente SignalEngine squeeze
assert w.tf == "1h"