495 Commits

Author SHA1 Message Date
Adriano bebfa63213 tradesdb: fill cron_log arricchiti con ora, prezzo e pos_after dal jsonl (#40)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 17:51:15 +00:00
Adriano ae887a3d98 book_execute: pos_after di nuovo nel jsonl, letta subito dopo il rebalance in un try (#39)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 17:42:34 +00:00
Adriano d34b0a81d8 merge lavoro/goldrake-u11 (secondo giro 27/09) 2026-09-27 15:40:43 +00:00
Adriano cfb0e1e57f merge lavoro/goldrake-u10 (secondo giro 27/09) 2026-09-27 15:40:43 +00:00
Adriano 39adfbf267 merge lavoro/goldrake-u9 (secondo giro 27/09) 2026-09-27 15:40:42 +00:00
Adriano 81b495eb10 merge lavoro/goldrake-u8 (secondo giro 27/09) 2026-09-27 15:40:42 +00:00
Adriano 28a6d79e4f tradesdb: refilo di uno spazio in un commento (#37 C11) 2026-09-27 15:26:43 +00:00
Adriano ac6ad7f116 revisione: tetto per-voce dedicato per CLAUDE.md (150k, il generico restava a 90k con margine minimo) e avviso quando una voce supera il 95% del suo tetto (#37 C12) 2026-09-27 15:24:36 +00:00
Adriano ddcd3773a7 cron_book/cron_cuscino: flock -n sul conto, un giro occupato si salta e si scrive (#36)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:19:49 +00:00
Adriano 213dd12bab docstring: execution/deribit/book allineati al codice attuale, niente importi cablati (#35 A9)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:19:37 +00:00
Adriano 3af6e1f0c3 telegram_daily: gate da monitor_health (non cablati), formato giorni a tre casi, header condizionale su flat (#35 C14)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:18:25 +00:00
Adriano 829ebc7f98 book: min_order_usd da config nel report (#35 A7)
book_report costruiva l'ordine con min_usd=5.0 fisso invece di leggere
min_order_usd da config/live.json, come fa gia' scripts/live/book_execute.py
(default 5.0 se assente). Oggi config = 5, nessun cambio di comportamento.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:17:42 +00:00
Adriano 52a905d497 book: leva_tetto unica per cuscino USDE e giornale (#28)
La leva lorda massima del libro era ridichiarata con tre formule diverse:
usde.frazione_cuscino (N_ASSET fisso, senza scala), la regola `leva` del
giornale (senza scala) e journal.movimenti_capitale (con scala). A scala
1,25 il cuscino USDC risultava 0,30 dell'equity invece di 0,375.

Nuova src/live/book.leva_tetto(cfg) = len(ASSETS) x min(WEIGHT, frac) x
scala, al piu' LEVA_LORDA_MAX; su ScalaNonAutorizzata non solleva, ritorna
il tetto di codice (cuscino_watch non deve morire sulla config sbagliata).
usde.frazione_cuscino e la regola `leva` del giornale ora la derivano;
movimenti_capitale idem, nel suo try/except esistente.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:17:01 +00:00
Adriano 12291709ed revisione, analista: taglio Telegram sul testo grezzo, prima di escape/markup (#35 C13)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:15:22 +00:00
Adriano 8e75e9c9a7 sleeves+edge_watch: pesi derivati da book (import locale), titolo kill corretto (#35 B12)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:15:07 +00:00
Adriano 13c136cf4b tradesdb: docstring corretto (jsonl ha l'ora vera dal 24/08, non piu' la barra); trades_db sync confronta i conteggi jsonl/DB e notifica una volta per episodio (#37 C11, #35 A9) 2026-09-27 15:14:04 +00:00
Adriano e82f2ee163 venue_probe: atteso hardcoded False in diagnose, l'unico chiamante non cade mai nello slot (#35 B11)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:11:29 +00:00
Adriano d80323ff59 analista: testata mostra trading_giorno (non l'equity grezza) e 'nel giorno', non 'oggi' (#35 C8)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:11:20 +00:00
Adriano d59aea7a0a monitor_health: giro orario dei sorveglianti da 3h con marcatore gia' detto (#30)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:11:10 +00:00
Adriano 31ec767ff5 telegram_daily: soglia di accensione generale su k flip, non il minimo fisso (#35 C3)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:10:04 +00:00
Adriano 95cfb396e7 fee_watch: realized_fee_bps sempre calcolata, divergenza da tier notificata una volta per episodio (#37 B9) 2026-09-27 15:06:40 +00:00
Adriano 604fde689e cuscino_watch: riconverti distingue parziale/fallita rileggendo la quota (#35 B10)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 15:03:02 +00:00
Adriano 841d4c78cd book_execute: integrazione U1+U2 — un solo Telegram in solo protezione, stato unknown, set_open_cap diretto (#18, #21, #22, #24)
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 14:14:28 +00:00
Adriano 0e6cf17081 merge lavoro/goldrake-u4 (revisione 27/09) 2026-09-27 13:53:10 +00:00
Adriano dab8a88e1c merge lavoro/goldrake-u3 (revisione 27/09) 2026-09-27 13:53:10 +00:00
Adriano ed4f8fd39b merge lavoro/goldrake-u2 (revisione 27/09) 2026-09-27 13:53:10 +00:00
Adriano 8405fe2a7d merge lavoro/goldrake-u1 (revisione 27/09) 2026-09-27 13:53:10 +00:00
Adriano 7234625863 usde_convert: residui cercati sotto USDC e USDE (#26)
Non e' verificato sotto quale valuta Deribit elenchi lo spot USDE_USDC: la
quotazione (USDC) o la base (USDE). cancella_residui interroga entrambe e
unisce per order_id prima di applicare il filtro instrument+label, cosi' un
residuo elencato sotto USDE non si accumula in eterno per non essere mai
letto. Se una delle due letture solleva, solleva come prima (nessun try
aggiunto attorno al giro).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:45:04 +00:00
Adriano 9ce924d97c book_execute: chiama set_open_cap (U1) se il trader lo espone, prima di rebalance_signed
hasattr perche' U1 e U2 si uniscono dopo questo rilascio: DeribitTrader oggi non ha
set_open_cap, e l'hasattr evita che l'unione dei due rami rompa in un senso o nell'altro.
Si toglie l'hasattr al merge.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:41:07 +00:00
Adriano 7c72308852 live/deribit,execution: open_orders non ingoia gli errori; ensure_disaster_sl -> unknown (#24)
open_orders solleva RuntimeError se 'all' o 'trigger_all' falliscono, invece di ritornare []
(un bracket disaster-SL perso su 'trigger_all' e' lo stesso difetto di una posizione persa su
'all'). ensure_disaster_sl avvolge la lettura di posizione+open_orders in try/except: su
eccezione ritorna {"state": "unknown", "notes": ...} senza cancellare ne' piazzare, distinto
da "naked" (protezione tolta e non rimessa). shadow.shadow_report chiama open_orders gia'
dentro try/except (non toccato).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:40:50 +00:00
Adriano 65a7f0d8fc book_execute: SOLO PROTEZIONE su equity/SKH ignoti; fill mai persi su rebalance parziale (#21, #22, #23)
Prima, con equity reale non leggibile il giro dimensionava comunque un ordine sul paper_cap
($2.000 nominali) e lo mandava; con SKH ignoto il target restava quello (fail-safe solo nel
segno). Ora: se non si sa quanto vale il conto o qual e' il segnale, nessun rebalance_signed —
ma il disaster-SL si controlla LO STESSO per ogni asset (dipende da posizione/mark, non da
equity/segnale). Giro degradato -> exit 2, solo se armato (non in anteprima dry-run).

Fill persi: rebalance_signed puo' eseguire un fill (es. il close di un flip) e poi sollevare nel
passo successivo (l'open dall'altra parte) — quel fill spariva perche' la lettura di `newpos`,
PRIMA del giro che lo registrava, andava in eccezione a sua volta. Estratta la registrazione in
_registra_fill(...), chiamata SUBITO dopo ogni fill (anche quelli di RebalanceParziale, nuova
eccezione di execution.py con .fills/.causa) e PRIMA di leggere la posizione; la lettura ora e'
in un try separato, non fatale (pos_after=None + "reconcile: pos illeggibile" se fallisce).

Aggiornati due test che assumevano il comportamento vecchio (eq_fallback "prosegue" sul paper
capital) e il guard sulla sorgente di test_tradesdb.py (bar_ts ora e' un parametro di
_registra_fill, non piu' `r['last_data']` inline).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:40:15 +00:00
Adriano f79fb54221 live/execution: tetto di apertura per strumento da config, non solo MAX_AMOUNT fisso (#18)
DeribitTrader.set_open_cap(instrument, usd_cap, mark) deriva amount_max = 1,10*usd_cap/mark
dal cap di config del libro; _submit lo usa quando presente, MAX_AMOUNT resta il DEFAULT per
chi non lo chiama (il micro-test). Firma per chi la richiama prima di rebalance_signed (U2):
trader.set_open_cap(inst, r["cap_per_asset"] * r["scala"], mark).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:39:54 +00:00
Adriano 4725839041 usde_watch: notify affidabile (allertati) e quota derivata, non piu' rinviata (#29 B2, #35 B3/B4)
#29 B2: lo stato si salvava PRIMA dell'invio e il ritorno di notify() non si
leggeva — un invio fallito restava "gia' detto" per l'episodio intero. Schema
di cuscino_watch.py: nuove_condizioni()/rec["allertati"] contano una
condizione come "gia' detta" solo se l'invio precedente e' RIUSCITO; un
record vecchio senza `allertati` vale come "tutto allertato" (nessun rispam
retroattivo). Lo stato si scrive una volta sola, a fine giro.

#35 B3/B4: la quota non e' piu' una decisione dell'operatore rinviata a
lunedi' — dal 10/09 (issue #7) e' DERIVATA dal cuscino USDC
(usde._nota_cuscino) — quindi tolti DECISIONE_QUOTA_DAL, quota_da_decidere()
e la notify "la decisione di QUOTA e' dovuta". Il tetto di allerta IDONEO
legge c["quota_max_frac"] invece del 50% cablato. La riga "margine" non dice
piu' "conto SEGREGATO" (il modello e' Cross X:SM dal 31/08): stampa il totale
USDC + USDE scontato del cross, coi numeri che la funzione ha gia'.

Le due modifiche toccano lo stesso blocco (allarmi + STATE write + stampa) e
non si possono separare per hunk senza rischio: un solo commit per il file.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:38:46 +00:00
Adriano 5acc31e390 venue_watch: BLIND ha una severity propria, il titolo non chiede piu' il prelievo (#31)
Con un asset BLIND e nessun ALERT, severity restava None e il titolo del
runner cadeva sul default piu' forte ("PRIMO PASSO: prelievo di prova") per
un episodio che e' "non vedo", non "stress misurato". run_once ora assegna
severity="blind" quando c'e' un BLIND senza ALERT (ALERT resta piu' forte, P9);
_titolo distingue il caso con "venue_watch CIECO — referenze non leggibili,
nessun giudizio sul venue". La ripetizione oraria di BLIND non e' toccata.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:38:35 +00:00
Adriano dda5d41f38 fee_watch: save_state solo se l'invio necessario e' riuscito (#29 B8)
save_state girava sempre dopo l'eventuale notify, anche quando l'invio
falliva: il giro dopo diff_vs confrontava lo stato nuovo con se stesso e il
cambiamento (o il livello AZIONE) spariva senza essere mai stato detto. Ora
lo stato si salva solo se non serviva un invio, o se l'invio e' riuscito.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:38:28 +00:00
Adriano f0193f013d usde_convert: cancella i residui GTC delle proprie label, nel ciclo e all'avvio (#26)
Il gateway cerbero-mcp non accetta time_in_force (PlaceOrderReq non ha il
campo): un limit riempito solo in parte restava APERTO per sempre e si
accumulava a ogni giro. cancella_residui() pulisce lo spot USDE_USDC dai
residui con label "usde-quota-*" prima del ciclo; nel ciclo, un ordine con
filled < amt viene cancellato subito dopo, e una cancellazione fallita ferma
il ciclo (mai un secondo ordine con un residuo vivo).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:38:20 +00:00
Adriano 0c19c804d1 analista: --secco non scrive piu' nel DB (#34)
scrivi() chiamava J.salva() prima del controllo su --secco: un giro "a secco" scriveva
comunque le sezioni misurate nel giornale. Ora salva() (e scrivi_file, che era gia' dopo
il return) girano solo quando non e' secco; rendi_markdown() tollera l'assenza della riga
in DB (nota/analisi vuote, verificato).

Test nuovo in tests/test_analista.py (non c'e' un test_analista_u4.py: l'analisi indicava
i due file journal/tradesdb, questo fix e' su analista.py e segue la convenzione un
file-di-test-per-modulo del resto della suite).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:38:10 +00:00
Adriano 2bf4f9cceb live/deribit: position_usd legge il segno da direction, non dal solo size (#17)
Il gateway manda size/size_currency in assoluto e il segno a parte in direction:
letta com'era, uno short risultava un long e close()/ensure_disaster_sl decidevano
lato ordine e prezzo dello stop dal segno sbagliato.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:37:36 +00:00
Adriano b8c2bba320 tradesdb: lotti con segno (short) e fill a qty<=0 fuori dal FIFO (#32 C2, C10)
C2: fifo_roundtrips ora apre un lotto SHORT quando un sell non trova lotti long da chiudere
(prima il resto spariva in silenzio), chiude prima il lato opposto e apre l'eccedenza nel
segno del fill — anche a meta' dello stesso fill (inversione long<->short). stato_aperto e
report() portano la direzione del lotto residuo.
C10: un fill "NON VERIFICATO" a qty 0 (place_order error) non entra piu' nel FIFO ne' in
stato_aperto (WHERE qty > 0 in rebuild_roundtrips/stato_aperto); resta nel DB marcato
(verified=0), non e' scomparso.

test_fifo_non_mescola_gli_asset aggiornato: una vendita ETH senza lotti long ora apre uno
short invece di sparire (era il comportamento che C2 corregge). Test nuovi in
tests/test_tradesdb_u4.py.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:37:20 +00:00
Adriano ac21e1c97d journal: dichiarati nello stesso intervallo si sommano, giro corrente, finestra 7gg, DD netto (#27, #35)
#27: due movimenti dichiarati nello stesso intervallo si sommavano al posto di sovrascriversi
(l'aggancio "dichiarato+rilevato" ora cerca solo fonte=="rilevato").
#35 C9: salute() non conta piu' il giro dell'ora corrente prima che scatti (minuto :47 +
margine, MINUTO_GIRO costante di modulo).
#35 C15: la finestra "ultimi 7 giorni" della concentrazione ora copre 7 giorni di calendario,
non 8 (baseline = ultima lettura al o prima di giorno-7 fine giornata).
#35 C7: il drawdown si calcola sulla serie equity al netto dei movimenti di capitale certi,
cosi' un prelievo non si legge come perdita di trading e un versamento non alza il picco.

Test nuovi in tests/test_journal_u4.py; tests/test_journal.py aggiornato (l'orologio del
test su salute() era reale e non deterministico, ora e' fissato).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:35:08 +00:00
Adriano cfc42653cc shadow: USDE illeggibile -> equity IGNOTA non 0; online richiede tutti i mark mainnet (#20, #25)
Un'eccezione sulla lettura del conto USDE valeva 0 USDE: se il conto ne aveva davvero, l'equity
totale risultava sottostimata senza che nulla lo dicesse. Ora _collaterale_usde ritorna None +
la nota dell'eccezione, e _equity propaga l'ignoto (real_eq None -> eq_fallback, non un numero
falso). shadow_report.online guardava solo il mark di BTC: con ETH in fallback il giro si
considerava comunque online. Ora richiede TUTTI i mark da mainnet.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-27 13:33:48 +00:00
Adriano 1a7f670966 sei sorveglianti registrano i giri e stanno in monitor_health (Fixes #16)
src/live/giri.registra_giro: una riga jsonl {ts ms, campi} dopo una misura completata,
mai un'eccezione. edge_watch, fee_watch, scale_watch, vrp_f_watch, venue_news (cron_daily)
e venue_watch (cron_book, orario) scrivono data/<dir>/runs.jsonl; niente riga senza misura.
monitor_health: sei MonitorSpec (30h i giornalieri, 3h venue_watch), open_labeled=False.
Stessa riparazione di cc01 (#10, #12), generalizzata. Primo giro notturno: NUOVO, non allerta.
Test: incrocio P1 percorso/RUNS, misura -> una riga, non-misura -> nessuna. Suite: 1098 passed.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-21 08:48:07 +00:00
Adriano e4efdaaa53 analista: niente capitale cablato nelle istruzioni, round-trip = lotto FIFO (Fixes #13)
ISTRUZIONI diceva «capitale ~$635» (equity reale ~$4.5k dal 04/09): valore ridichiarato,
forma di P1, e fuori pagina per la regola 1 delle istruzioni stesse. Ora il capitale e'
l'equity in pagina. Aggiunto che fifo_roundtrips chiude un round-trip per lotto: piu'
round-trip che fill nello stesso giorno e' atteso (l'analista lo segnalava come anomalia).
Test: nessun importo in ISTRUZIONI; FIFO e lotto nominati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-21 08:48:07 +00:00
Adriano b46041d11d CLAUDE.md: §1 tetto allerta USDE 0,85 e frase ricucita, garanzia dell'ombra anche per permesso; §4 soglie STATARB verbatim (Fixes #14, Fixes #15)
- §1: «tetto ALLERTA quota 50%» contro config usde.quota_max_frac 0.85 (dal 06/09;
  0.50 resta default di codice in src/live/usde.py). Frase «dopo un bonifico si» troncata
  dal 10/09 (37d1565), ricucita.
- §1 OMBRA: dal 21/09 il token dell'ombra e' a scope di sola lettura (Adriano/TradingBook#19),
  misura del 21/09 riportata; il segreto resta pieno, la chiave read-only la crea l'operatore.
- §4 STATARB: regola del 24/07 copiata verbatim da scripts/research/r0724_statarb_deploy_gate.py
  (esiti, guardie, addendum 25/07 non binding). Nessun verdetto anticipato.
Autorizzato da Adriano il 21/09 dopo la revisione settimanale.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-21 08:48:07 +00:00
Adriano 4b04831352 giornali 17-20/09 (cron_daily 00:30Z) e revisione settimanale 21/09 — solo dati
Commit di soli dati dalla produzione: le pagine le scrive cron_daily e la
revisione cron_review, nessun cron le committa (commit a mano da sempre).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-21 08:25:38 +00:00
Adriano 8007158eb5 giornale 2026-09-16 (cron_daily 00:30Z)
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-17 05:31:42 +00:00
Adriano 31f5915a41 ombra di TradingBook documentata al §1; cc01_regime_watch registra i giri e sta in monitor_health (Fixes #11, Fixes #12)
- CLAUDE.md §1 OMBRA: cron :44 sulla stessa crontab, legge il conto con la STESSA chiave live di
  cerbero-mcp (verificato per hash), scrive solo nel suo albero (3 giri misurati, nessun file di
  data/ o logs/ di qui cambiato), non invia per assenza di codice e non per permesso. §12 rimanda.
- cc01: ogni giro con entrambi gli asset misurati scrive data/cc01_regime/runs.jsonl (ts ms,
  stato, funding 30g/7g); se non vede, non scrive e lo dice. monitor_health: MonitorSpec
  giornaliera, max_age 30h, percorso incrociato con cc01.RUNS da un test (P1).
- tests/test_cc01_regime_watch.py (4, rossi prima). Suite completa: 1074 passed.
Autorizzato da Adriano il 16/09 dopo la revisione settimanale.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-16 21:10:12 +00:00
Adriano e42ab5369f giornali 10-15/09 e revisioni 14/09 (NON eseguita, limite Fable) e 16/09 (rilancio a mano, esito sospetta)
Solo documenti generati da cron_daily e revisione.py, nessun codice. Su richiesta di Adriano 16/09.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-16 19:46:36 +00:00
Adriano a6a49d9c65 cc01_regime_watch: ROOT in sys.path, moriva ogni notte dal 03/09 su from src.live.cli (Fixes #10)
Eccezione alla regola «PG non si tocca» autorizzata da Adriano il 16/09, solo questo file.
Verificato: --help exit 0, giro completo QUIET (BTC 30g +9,0%, ETH +9,4%), test_cli_flag 55 passed.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-16 19:36:33 +00:00
Adriano Dal Pastro a4e942c8bb r0910: risk-off ±2h intorno a FOMC/CPI su TP01 REFUTED 0/3 (ΔSh −0,097, −1,24%/anno; le ore dei dati sono fra le migliori)
Calendario letto dal web (Fed 61 riunioni + BLS 88 release CPI, 2019-2026), TP01 orario dalla stessa
held di sleeves, null location-matched 1000 estrazioni (Δ vero al 4,2° pctl), per anno 2/8.
Registro §78, memoria 20-ondate (D-bis), diario 2026-09-10b.

Fixes #9

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016kqvff47UBGeYfj1QeN4zE
2026-09-10 14:56:29 +00:00
Adriano Dal Pastro 5b72a4b188 §3: quota USDE 0,64 derivata dal cuscino e' decisione vincolante dell'operatore (10/09)
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016kqvff47UBGeYfj1QeN4zE
2026-09-10 14:19:31 +00:00
Adriano Dal Pastro a2b03aa2b6 USDE allineato a quota 0,64 su ordine dell'operatore (238 USDE venduti, slack +$266 = OK)
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016kqvff47UBGeYfj1QeN4zE
2026-09-10 14:17:43 +00:00
Adriano Dal Pastro 37d1565a1e cuscino_watch: riacquisto automatico di USDE con isteresi (ECCEDENTE), bande in config, escape HTML nel sink di notify
Decisione dell'operatore 10/09 («riportarla a quota in autonomia»). Verificato da revisione fable
(10 segnalazioni, 9 applicate; loop numerico su usde_convert.piano: nessuna sequenza vendita→acquisto).

- quarto stato ECCEDENTE: slack > cuscino_riacquisto_frac (0,40) x cuscino => acquisto di USDE fino
  allo stesso bersaglio della vendita, q* = 1 - 0,30 x (1 + cuscino_margine_frac 0,20) = 0,64.
  Isteresi [0 ; 0,40] x cuscino con bersaglio unico 0,20: per oscillare servono +-8,6% di equity
  USDC (~$380); un bonifico alza lo slack di 0,7 x importo e sopra ~9% dell'equity ricompra da solo.
- le tre frazioni (preavviso/margine/riacquisto) in config/live.json sezione usde, lette da
  usde.bande_cuscino() che verifica l'ordine; quota_target 0,70 TOLTO (slack zero per costruzione).
- notifier.notify: html.escape su titolo e valori — la prima allerta vera (13:53Z) era andata persa
  per un '<' nudo; allerta_errore registrato nel record (P3).
- da ECCEDENTE un fallimento si ritenta ogni 24h (non 4 Telegram/giorno per sempre); bande fuori
  ordine => BLIND con motivo, non un traceback ingoiato dal cron.
- CLAUDE.md §1/§4/§5.17, config _nota_usde/_nota_cuscino, diario. 0,64 e' una DERIVAZIONE
  dell'autore, non la quota decisa il 30/08 (0,70): dichiarato, da confermare.
- test: 1070 (+8 netti).

Fixes #7

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016kqvff47UBGeYfj1QeN4zE
2026-09-10 14:14:29 +00:00
Adriano Dal Pastro f82f685528 cinque punti della revisione 09/09: usde_watch a 1000 trade + finestra 24h, cuscino_watch (equity USDC, riconverte da solo), PREVDAY-01 kill/veto cablati, SCALA-01 al 2027-02-28, versamento 04/09 dichiarato
Decisi dall'operatore il 2026-09-10, verificati da revisione fable (15 segnalazioni, 12 applicate).

- usde_watch: TRADE_LIMIT 1000 (count max Deribit) e trade_copertura(): lista troncata o ultima
  lettura oltre la finestra di 24h del gateway => somma NON leggibile, reward non attribuito (P12).
  Riga del 07/09 corretta nel log con campo `correzione` (400 USDE erano acquisti, non reward).
- cuscino_watch.py (cron :53, monitor_health): equity USDC contro cuscino derivato da
  usde.cuscino_richiesto_usd (formula spostata in src/live/usde.py, usde_convert la importa);
  OK/PREAVVISO/SCOPERTO/BLIND; sotto zero lancia usde_convert --quota quota_ripristino(0.20)=0.64
  --esegui con guardie (execution_enabled, depeg_warn, 1 tentativo/6h). Primo giro: PREAVVISO, +$26.
- usde_convert: il tetto del venue vale solo in ACQUISTO (bloccava la vendita).
- paper_prevday: GATE PREVDAY-01 cablato (2027-06-21, kill Sharpe giornaliero < -0,50 su >=180 g
  attivi, veto >=80% barre ricostruibili + divergenze non crescenti con soglia materiale).
  Oggi: +0,95 su 81 g, 1942/1943 ricostruibili, kill NON MATURO.
- CLAUDE.md: arming 20/06 (TP01) / 23/06 (BOOK); piano EUR 5.000 chiuso col versamento 04/09
  ($2.414,68 dal balance, dichiarato); SCALA-01 non prima del 2027-02-28 (A2 dal 01/09);
  PREVDAY-01 con data, kill, veto; §5.17 riparato con i limiti dichiarati (ratchet, slack zero a 0,70).
- test: 1062 (+31): test_cuscino_watch (16), test_paper_prevday_gate (8), test_usde_watch (+5).

Fixes #2
Fixes #3
Fixes #4
Fixes #5
Fixes #6

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016kqvff47UBGeYfj1QeN4zE
2026-09-10 13:24:28 +00:00
Adriano Dal Pastro 79afe41ec2 giornale 2026-09-09 (cron_daily 00:30Z)
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Bjj5vPEBoAJrB23P6RjKzs
2026-09-10 04:32:48 +00:00
Adriano Dal Pastro 8f2e6c5c2c revisione settimanale in sola lettura: revisore fable, rapporto firmato + Telegram, lunedi' 06:15 UTC
- src/live/revisione.py: materiale (CLAUDE.md, config, crontab, git, monitor_health, stati dei
  sorveglianti, 7 g di giornale e diari, ~195k caratteri), prompt con dieci regole (sola lettura, fonte
  per ogni segnalazione, solo numeri del materiale, §3 non si ripropone, idee nuove solo citando la
  memoria, gate con data e criterio), guardia sui numeri, rapporto firmato (P13), Telegram = Sintesi
  con taglio dichiarato; modello muto o risposta senza titoli -> rapporto «NON eseguita» + 🚨 (P5).
- scripts/live/revisione.py (guardia cli.valida, --secco/--no-telegram/--quiet/--giorno/--modello),
  scripts/cron_review.sh, crontab `15 6 * * 1`.
- primo giro reale: il prompt su argv moriva con `Argument list too long` senza rapporto ne' allerta ->
  prompt su stdin, ogni eccezione diventa errore dichiarato; `analista.pulisci` toglieva i titoli.
  Secondo giro: docs/revisioni/2026-09-09.md, stato sospetta (cifre in formato italiano), nessun URGENTE.
- scartati con la memoria: autoregolazione dei parametri, generazione automatica di strategie, macro
  da internet (diario 2026-09-09c, memoria 40).
- test: tests/test_revisione.py (18) + 2 in test_cli_flag; suite 1031/1031.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Bjj5vPEBoAJrB23P6RjKzs
2026-09-09 22:07:50 +00:00
Adriano Dal Pastro 0a2f780d3c cblib causale: spot +1h e DVOL +1 giorno (debito §5.18); §11 rimisurato 0,714 → 0,712, verdetti invariati
- cblib.causale(s, cadenza): spot_series e dvol_series escono causali (asof = ultima chiusura NOTA);
  il DVOL giornaliero era una seconda serie con lo stesso difetto (fino a 24h avanti), verificato contro
  l'API pubblica a 1h. Regolamento ST alle 08:00 invece delle 09:00.
- §11 riprodotto al millesimo su worktree HEAD (0,714 [0,690-0,779], n=19, flag --al) e rimisurato:
  0,712 [0,664-0,732]; solo spot 0,721, solo DVOL 0,693, DVOL orario di controllo 0,717. Mediana onesta
  BTC 1,45 → 2,12, fee 1,51x/1,87x. r0730: 0,73 → 0,71. §75: ETH pre 0,76, BTC durante 0,89 (orario 0,83).
  skew panel ≤0,005. vrp_f_watch: f canonico 0,732 → 0,706, differenza +0,097 [+0,042, +0,140].
- r0909 senza doppio shift, contesto sul DVOL del giorno; r0822 regime su date di calendario; r0901
  join riallineato (bit-exact). Aperti con costo: DVOL orario (−0,04/+0,06 nel crollo), spot 5m (≤25 min).
- test: +3 causalita' in test_cb_chain_vrp, anti-doppio-shift in test_r0909; suite 1011/1011.
- revisione fable: 16 segnalazioni, tutte applicate (fra cui un «−1,8% in un'ora» che era +3,9%).

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Bjj5vPEBoAJrB23P6RjKzs
2026-09-09 21:41:23 +00:00
Adriano Dal Pastro bb40e87d13 crolli: il libro perde nel giorno e chiude > 0 in 8/8 finestre dal 2022 (SKH01 short); crollo catturato a vol bassa, XRP diluisce come SOL
Quattro misure (r0909_*), nessun cambio a libro/pesi/config:
- libro nei crolli: −0,48%/g nei 160 giorni ≤ −5%, positivo per finestra dal 2022
  per la gamba short di SKH01 (108% dei guadagni); beta 0,0769 riprodotto (§46);
  il peso di SKH01 resta chiuso dal gate (in-sample).
- crollo catturato 1-5/06/2026 a quote vere: f_net 0,74 = rally; put δ−0,10
  1,92× il modello; a vol bassa e fuori dal gate di VRP01 → §3 non si riapre.
- XRP terza gamba (harness r0822_sol_leg): hold-out −0,169 in 0/24, un anno buono.
- universo Deribit: liquidi solo BTC/ETH/XRP/SOL; XS01 13/19; BTCDVOL future
  non negoziabile; PAXG non misurato.
Revisione fable: due conclusioni smontate (MTM 2,6× era un artefatto di quote;
«8/12 guadagna» era l'ordine delle classi). Debito §5.18: cblib.spot_series
+ asof guarda un'ora avanti (feed 1h etichettato all'apertura).
Test Opus: 92 nuovi, suite 1008/1008; due difetti del verdetto XRP corretti.
Docs: diario, RESULTS §74-77, CLAUDE.md, memoria 20/50, README; journal 07-08/09.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017zJjHUS7mf4pnGE6pq9RTt
2026-09-09 16:33:54 +00:00
Adriano Dal Pastro 9f55652d99 usde al 68,7%: il tetto del venue del 30-31/08 non c'era piu'; il versamento di prova del 25/08 dichiarato, TWR +7,83%
Su autorizzazione dell'operatore («usa piu' USDE», «cerca % massima raggiungibile»):
- usde_convert al 31,8% (774 USDE), poi sonda a saldo crescente r0906_usde_tetto_sonda.py
  (passi 100->20->4->1, doppio rifiuto prima di scendere, conferma a saldo neutro): da 31,8%
  a 68,7% in 39 ordini @ 1,0005, ZERO rifiuti. Fermata dal cuscino di regolamento (70%,
  derivato da config), non dal venue. «Il 70% non e' raggiungibile ne' ora ne' mai» (31/08)
  e' falsificato: il tetto e' sparito, non scalato. Non spiegato, puo' tornare.
- config: venue_cap_frac -> null (misura in venue_cap_misurato), quota_max_frac 0,50 -> 0,85
  (il valore scelto dall'operatore il 30/08 per questo scenario).
- debito §5.17: nessuno sorveglia il cuscino USDC (slack $58; una perdita del libro lo consuma
  da sola).

Versamento di prova di EUR 25 il 25/08 08:00Z (dichiarato dall'operatore): +3,3% su $647, sotto
la soglia del 10% del rilevatore, contato per 12 giorni come trading.
- data/live/movimenti_dichiarati.jsonl (append-only, nel backup) letto da
  journal.movimenti_dichiarati; movimenti_capitale lo fonde coi rilevati (fonte dichiarato,
  importo dell'operatore, dopo = prima + importo; dichiarato+rilevato se coincide; fuori
  letture o riga rotta -> avvisi). Report e nota di giornale lo dicono.
- trading da arming +87,35 -> +62,45; TWR +11,98% -> +7,83%. CLAUDE.md §2 aggiornato.
- tests: +6 in test_journal (conftest isola il file). Suite 916 verdi.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01KSnordG9FT4q8M4MVm85GQ
2026-09-07 05:49:15 +00:00
Adriano Dal Pastro 95424f0755 docs: il README era fermo a 15 giorni PRIMA del reset — riscritto contro lo stato vero
Ultimo commit del README: 2026-06-04. Reset v2.0.0: 2026-06-19. Per 75 giorni la prima pagina
del repo ha pubblicato la libreria pre-reset (FADE/HONEST/PAIRS/TSMOM/SHAPE, PORT01-06) con
Sharpe 7,84/10,06 e CAGR ~79% come risultati correnti — cioe' esattamente i numeri che §2
elenca sotto "non citare", dalla libreria che il reset aveva dichiarato artefatto. Meta' dei
file citati non esiste piu' (strategies.yml, portfolios.yml, scripts/waste, scripts/portfolios,
src/live/multi_runner.py), e l'esecuzione descritta era su TESTNET, che e' la causa del reset.

- README riscritto (423 -> 152 righe): cosa gira adesso (TP01+SKH01 75/25, ~$2.050, cadenza
  oraria :47), i numeri nella lente di §2 (TWR +10,6%, non la crescita del conto), la riga che
  ordina il piano, il metodo e i suoi sei requisiti, il dato, la struttura VERIFICATA file per
  file, i comandi, i gate con le loro date, l'obiettivo con la sua onesta'.
- CLAUDE.md §0 e memoria 40: registrato il difetto e la lezione — un reset invalida anche i
  documenti che nessuno rilegge; l'inventario di cosa cita numeri morti va fatto il giorno del
  reset, non 75 giorni dopo per caso.
- Diario 02/09c: sezione col confronto riga per riga; coda dichiarata (l'inventario completo
  degli altri documenti pre-reset non e' stato fatto).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XDJsH3iDSaBns3ccpPBwiu
2026-09-02 15:53:42 +00:00
Adriano Dal Pastro de83909db9 un flag sconosciuto non e' l'azione di default: guardia su 18 script, indice USDE orario, pulizia
MISURATO oggi durante la revisione: `trades_db.py --help` non stampava l'uso, cadeva in sync()
e riscriveva meta.ultimo_sync. Nessuno dei 18 script di scripts/live/ usava argparse: un flag
sbagliato era il ramo else. Su journal.py avrebbe scritto pagina e riga di DB, su analista.py
avrebbe speso una chiamata al modello e mandato un Telegram.

- src/live/cli.valida: prima istruzione di ogni __main__, prima di connect()/sync/rete.
  --help -> 0 con l'uso; flag ignoto, valore mancante o posizionale -> 2 con l'elenco dei
  previsti (P4). NIENTE argparse: cambierebbe messaggi, codici d'uscita e --help di script
  che il cron gia' chiama.
- 18 script cablati (i 3 che scrivono + 14 + cc01), flag invariati.
- tests/test_cli_flag.py (30): elenco DERIVATO dalla cartella (P1), valida come prima
  istruzione, uso che documenta i flag, e i flag che il CRON usa davvero restano accettati
  (P15/P16); end-to-end su --help e flag ignoto con trades.db non toccato (M15).
  Verificato a mano: monitor_health --quiet, trades_db --sync --quiet, book_execute dry-run.

Debito §5.15, primo passo: balance_watch (orario) registra `usde_usdc` a ogni campione — None
con la ragione se illeggibile, mai 1,0. Il cablaggio nel bound quando la serie ha storia.

Pulizia dalla revisione: tests/helpers.carica_script al posto della 15a copia del loader
importlib (5 file del libro live); il fill di prova via upsert_fills invece di un INSERT che
lasciava verified NULL; asserzioni non ancorate al padding; movimenti_capitale accetta le
righe gia' lette (una SELECT invece di due ai due lati di una scrittura del cron).

Test 910 verdi (+52). Diario 2026-09-02c.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XDJsH3iDSaBns3ccpPBwiu
2026-09-02 15:49:40 +00:00
Adriano Dal Pastro 1279ea605a revisione 02/09, seconda tornata: il classificatore dei movimenti era cieco ~23 ore al giorno
Il feed 1h certificato si ferma alle 00:00: per le letture successive `asof` dava la stessa
barra a t0 e t1, mercato "fermo" = 0, e qualunque calo >=10% del giorno sarebbe stato un
"movimento" scorporato come prelievo (giornale dal 25/08, report da oggi). Con feed assente
tutto era "ambiguo" e il report stampava e1/e0-1 sotto l'etichetta TWR.

- journal.movimenti_capitale: stato "mercato non misurabile" (feed fermo/assente/barra
  mancante) => ambiguo con la ragione; leva_tetto = min(frac x n x scala, LEVA_LORDA_MAX) (P1).
- journal.rendimento_twr: salto non classificabile => twr E trading None con motivo.
- journal.pnl_giorno CHIAMA rendimento_twr (prima rifaceva cum - certi: "entrambi la chiamano"
  era falso); la pagina stampa il TWR; analista qualifica il cumulato "di cui versati".
- trades_db --report: la classe di ogni salto con la sua misura (mercato max a leva piena).
- book_execute docstring: banda dello stop -33,5%/-26,5% (era invertita), "non costa ordini"
  -> micro-ordini di ri-taglia (22/48, C2), latenza <=1h solo con feed fresca, conteggi di
  r0823 al posto di "raddoppia" (2 contro 1 e' rotolante vs pavimento sulla riga 4h; la
  peggiore misurata e' 24h).
- test_book_cadenza: LTF_MIN importato da skyhook; tutte le righe attive della crontab (una
  sola); tre stati dello skip (col progetto ma senza cron_book => ROSSO); slot di release
  testato con venue_probe (il :07 come controllo positivo); parser regolare, passo > 0.
- r0823_sl_anchor: guardia sul :47 (era sul vecchio :07), prosa al passato; cron_chain.sh idem.
- CLAUDE.md: §5.7 frase invertita corretta, §5.14 limite vero (non l'artefatto della fixture),
  §2 ora della LETTURA (13:47Z), nuovo debito §5.15 (USDE fuori dal bound di mercato).
- diari: tempi "scritto" corretti coi commit; sezione "Seconda tornata".

Test +11 (858 verdi).

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XDJsH3iDSaBns3ccpPBwiu
2026-09-02 15:33:13 +00:00
Adriano Dal Pastro 835e0c8666 revisione 02/09: il rotolante si CONTROLLA ogni ora (non "si ri-ancora"), TWR con limiti dichiarati e tre stati
Quattro segnalazioni della revisione sui commit di oggi, tutte verificate e riparate.

1. book_execute.py (+ CLAUDE.md §5.7, memoria 40): «il disaster-SL rotolante si ri-ancora ogni
   ora» era falso — ensure_disaster_sl lascia il bracket finche' lo stop e' entro il 5% e la
   taglia entro il 10%; il giro orario CONTROLLA, ri-ancora oltre la tolleranza (mark
   +5,263%/-4,762%). Lo stop siede fra -26,3% e -33,3% dal mark corrente.
2. journal.rendimento_twr: limite dichiarato (D5) — l'intervallo che contiene un movimento
   certo esce intero dal rendimento, il suo P&L di mercato va in `certi`; errore massimo meta'
   del movimento per costruzione (25/08: ~$0,5). Non si stima (P12). Segmenti a lunghezza zero
   non prodotti; nessun tempo a mercato -> 0,0 dichiarato numero.
3. base di equity zero: `twr` E `trading` None con motivo (il salto 0->X e' invisibile al
   classificatore, `trading` valeva l'intero conto); il report stampa n/d.
4. test_book_cadenza: la guardia estrae ogni prescrizione «ogni/every N unita'» e pretende 60
   minuti, con controllo positivo (M15); limite P13 dichiarato.

Test +5 (847 verdi). Diari 02/09 e 02/09b con la sezione "Revisione".

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01RziUCB336YPUUyDJ29x4Ke
2026-09-02 15:17:05 +00:00
Adriano Dal Pastro 861cc7fc27 debito 7: la cadenza del libro e' ORARIA — docstring riscritto, tre fonti tenute d'accordo da un test
Il docstring di book_execute.py prescriveva «ogni ~230 minuti» mentre il cron gira ogni ora
(47 * * * *). Era il docstring a sbagliare: sulla riga 4h BTC raddoppia gli scatti del
disaster-SL rotolante (r0823_sl_anchor.py), e chi avesse "corretto" il cron verso il
docstring avrebbe spostato il libro sulla riga peggiore.

- scripts/live/book_execute.py: CADENZA: ORARIA, la riga di crontab, la ragione (giro
  idempotente, latenza SKH01 <=1h, ri-ancoraggio orario) e il divieto esplicito con la data.
- tests/test_book_cadenza.py (10): deriva e confronta docstring, intestazione di
  cron_book.sh e crontab installata (crontab -l; SALTATO se illeggibile, non verde);
  parser a 5 campi solo per cadenze regolari; 60 < 230 < 240; minuto != :00.
- docs: CLAUDE.md §5.7 chiuso, §13 conteggio 842; memoria 40; diario 02/09b.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01RziUCB336YPUUyDJ29x4Ke
2026-09-02 14:38:53 +00:00
Adriano Dal Pastro 2f701b8469 debito 14: il report stampa il TWR (+10,61%), non il bonifico (+243%)
`trades_db.py --report` calcolava e1/e0-1 sulla serie grezza di equity: il 96,3% del
numero era il versamento di $1.399,39 del 25/08. La riparazione (journal.movimenti_capitale)
esisteva e non aveva attraversato il confine fra i due lettori della stessa serie (P1).

- src/live/journal.py: `rendimento_twr` — funzione unica, spezza la serie sui movimenti
  CERTI e moltiplica i segmenti; gli ambigui restano dentro, dichiarati (P12); tre stati.
- scripts/live/trades_db.py: report() la chiama; stampa TWR con segmenti datati, movimenti
  elencati, trading al netto, delta $ etichettato "movimenti INCLUSI"; il % grezzo sparisce.
- test: +5 in test_journal.py (incl. riproduzione del +10,80% del diario 01/09, M23),
  +2 in test_trades_report.py sul testo stampato con connect() deviato in tmp. 832 verdi.
- docs: CLAUDE.md §5.14 chiuso, §2 e §13 aggiornati; memoria 40; diario 02/09.

Limite ereditato e dichiarato (D5): +10% di trading fra due letture consecutive tocca la
soglia del rilevatore e a mercato fermo verrebbe classificato movimento.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01RziUCB336YPUUyDJ29x4Ke
2026-09-02 14:22:50 +00:00
Adriano Dal Pastro bc43218a12 docs: soldi fermi §73 — l'operatore sceglie di versare (piano 27/07: €5k dentro, ~€1k fuori)
Conclusione dell'operatore (02/09): "mettere gli XEON su Deribit col
sistema attivo". Si', ed e' cio' che la memoria aveva scritto il 27/07.
Tre precisazioni, tutte gia' misurate e ora registrate:
- €5.000, non €6.043: la protezione venue satura a qualunque quota > 0,
  l'ultimo migliaio dentro compra ~€100/anno e butta via l'assicurazione;
- il "~€600" e' un'attesa a banda larga, non un tasso (libro a mercato il
  22% dei giorni, TWR +10,8% in 70g, hold-out TP01 ~+0,05, fisco −30%/10a);
- fondo d'emergenza da dichiarare.
Nessuna azione di config (cap dinamico, rilevatore collaudato il 25/08).
In attesa di importo e data; al deposito una riga di giornale, scritta
prima e non ricostruita dopo. N9: le opzioni sicure (+€52-62/anno) sono
state viste e messe da parte con motivo.

- CLAUDE.md §1: riga "soldi fermi" + indice §1-73
- RESULTS §73 + riga d'indice
- memoria 30-piano-capitale-fisco: voce
- diario 2026-09-01d: §7 la conclusione dell'operatore
- docs/journal/2026-09-01.md (voce del cron, non era committata)

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-02 06:06:15 +00:00
Adriano Dal Pastro d95fabf060 soldi fermi: i modi esistono e valgono €5/mese — BOT/conto deposito +€52-62/anno, sUSDe distrugge lo split
On-venue chiuso con l'elenco intero: 4/50 valute remunerate = le 4 gia'
chiuse il 31/08. L'USDC su Deribit non e' fermo (base di sizing + cuscino).
I €6k in XEON sono lo split-cassa. Tassi dal web con fonte (BOT 2,768%
asta 08/2026, DFR 2,25%, conti deposito 3,25-3,50%, sUSDe ~9%). In euro
netti su €6k: XEON 81, BOT 133, conto deposito 143, sUSDe 350 (ma stesso
emittente dell'USDE: split distrutto), libro ~600 (trading, split
distrutto). Miglior guadagno sicuro: +€62/anno. €100/mese di bonifico =
+4,07%/anno di drift. Non sono pareri fiscali. Nessun ordine.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-01 21:21:14 +00:00
Adriano Dal Pastro 1c0549080c PAVIMENTO-LEVA (§72): il pavimento non licenzia taglia, 0/16 — e corregge §71
Domanda dell'operatore: "possiamo usare quanto conosciamo del pavimento per
studiare una strategia". L'inverso di COLLAR01: non "quanto DD mi risparmia
il pavimento a taglia fissa" (perdeva contro il de-levering) ma "quanta
TAGLIA mi autorizza a DD fisso" — l'unica cosa che il de-levering non puo'
comprare (cambia la FORMA, non la proporzione), e la grandezza su cui vive
il tetto di leva del progetto (n·frac·scala·sl <= 0,50 => 1,67x).

RISULTATO: 0/16. La sola put a premio reale PEGGIORA il maxDD in 16/16 celle
(FORTE 51,83% -> 55,4-75,8%; LARGO 71,94% -> 74,8-81,7%), quindi k_f = 1,000
ovunque: niente da licenziare. Monotono nella protezione: piu' la put e'
vicina, peggio va — il bleed del premio E' il drawdown.

🚨 CORREGGE §71 (stesso giorno). Stamattina A1 diceva "il pavimento funziona
davvero". E' il COLLAR a ridurre il DD, non il pavimento: a premio zero la
put lo riduce (51,83 -> 36,76, il controllo), a premio reale lo peggiora =>
tutto il beneficio e' mangiato dal premio, e oltre. Nel collar la riduzione
viene dal TETTO: il suo premio compensa il bleed, e cappare l'upside abbassa
il picco da cui il DD si misura — un picco piu' basso, non protezione.
Premio di pareggio: 36-79% del reale; il DVOL sta 1,32x sopra la RV, quindi
un prezzo equo (~76%) sfiora il pareggio nelle celle migliori e lo manca
nelle altre. Il motivo di §46 (beta) non si applica — a beta 1,0 la put
paga davvero — ma il verdetto di §46, "il maxDD SALE", si riproduce per un
motivo diverso. Corretti il diario di §71 (titolo e A1), RESULTS, memoria.

IL MECCANISMO (B2), trasferibile: i drawdown di BTC sono GRIND. maxDD FORTE
2021-07-20 -> 2022-05-06 = 290 giorni; LARGO fino al 2023-10-16 = 818. Una
put a 7-14g copre UNA finestra; il DD che conta dura 20-60 finestre; la put
scade OTM ogni settimana (para nel 0-9% dei cicli) mentre il premio sanguina.
Non protegge nemmeno la finestra peggiore: 14g FORTE -22,9% nudo -> -23,6%
col pavimento. Su BTC il pavimento compra protezione contro la cosa sbagliata.

LA LICENZA DEL DISASTER-SL E' DI CARTA (B3), scritto prima che sia comodo:
con la put a 5d/14g a 21,9% dallo spot, sostituire sl con quella distanza
darebbe 2,28x. Ma l'invariante limita UN episodio, la put limita UNA
finestra, e il massimo su finestre consecutive non e' limitato da nulla:
1 finestra -23,6% (coperta), 8 finestre -33,6% (non coperte) => a 2,28x un
grind di 112 giorni costerebbe il 77% dell'equity. disaster_sl_pct NON si
sostituisce con la distanza di un pavimento. Aggiunto a CLAUDE.md §3.

GATED SULL'IV (B4) — la copertura dinamica che §46 non aveva provato: put
ON solo sotto il 25°/50° pctl di DVOL/RV. Migliora molto (FORTE +3,8% ->
+8,4%) ma resta sotto la base (+10,04%) e il DD resta >=. L'incollatura
ignora lo spread delle transizioni A FAVORE del gated: perde a maggior ragione.

Quattro attese a priori (B1-B4) scritte prima, tutte confermate.

NON MISURATO, dichiarato: nessun DSR (cade al primo gate); nessuna lente
reale; nessun pavimento a scadenza lunga (30-90g, che coprirebbe piu'
finestre di grind) perche' l'operatore ha vincolato a <=15 giorni — e'
l'unica variante che B2 lascia aperta, e sta fuori dal vincolo.

Libro, pesi, cron, config INVARIATI. Nessun ordine. Test 25/25 sui filoni.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-01 20:45:02 +00:00
Adriano Dal Pastro ec8478308f GATE SCALA-01: la chiave di scala esiste, ed e' INERTE (SPEC §8 punti 1-4)
Chiude il debito che CLAUDE.md dichiarava da settimane: la regola "ogni cambio
di scala passa dal cap di config, non da target_vol" NON era implementabile
perche' una chiave di scala non esisteva — qualunque cambio sarebbe finito su
WEIGHT/W_TP01/W_SKH, cioe' codice su un percorso con soldi veri e per giunta
nel posto sbagliato (W_TP01/W_SKH sono il RAPPORTO 75/25, non la taglia).

Specifica gia' scritta in docs/research/SPEC-scale-key.md (618 righe, 9
condizioni di gate, prototipo). Non ho progettato: ho eseguito i punti 1-4.

🚨 config/live.json NON E' STATO TOCCATO. La chiave e' assente, vale 1,00, e
T7 dimostra bit-exact che il libro e' quello di ieri (max|diff| = 0.0).
Verificato anche a runtime: book_execute in dry-run da' gli stessi target del
cron delle 15:47 (BTC $+355, ETH $+214).

LE QUATTRO DECISIONI CHE NON SONO DI COMODO
- La scala si applica DOPO il clamp. Prima, il cap se la mangerebbe proprio
  nei giorni di massima convinzione (a tp=1/sg=+1 il grezzo vale esattamente
  cap => k_eff tornerebbe a 1,00 a ogni k): sarebbe un cambio di FORMA
  travestito da cambio di taglia, e la curva g(k) con cui il gradino viene
  autorizzato non descriverebbe quel libro. Prezzo dichiarato: il cap diventa
  il tetto del libro UNITARIO, e la guardia sulla leva lorda va ricostruita.
- Il tetto e' sul PRODOTTO e sta nel CODICE. Sulla sola chiave lascerebbe
  aperta la porta accanto (frac 0,625 x scala 1,25 = 1,562x); in config
  sarebbe un lucchetto con la chiave attaccata. LEVA_LORDA_MAX 1,25 in
  src/live/book.py => il gradino a 1,50 richiede codice, quindi review.
- Fuori scaletta o fuori tetto = STOP, non clamp. book_execute si ferma, non
  invia, allerta (ScalaNonAutorizzata). E SCALA_LADDER (1,00 · 1,25) rende
  INESPRIMIBILE "solo un po'": 1,05 non e' prudente, e' fuori scaletta.
- La scala vive solo sul percorso fidato (equity illeggibile => 1,00), cosi'
  "il fallback non e' piu' permissivo" e' vero per costruzione. Ma la
  VALIDAZIONE avviene sempre: una config rotta non si nasconde dietro un giro
  in cui l'equity non era leggibile.

LA GUARDIA CHE MORDE PER PRIMA non e' il peggior giorno (k <= 3,49x) ma il
COSTO di un disaster-SL (k <= 1,67x, 2,1x piu' stringente): l'invariante
n_asset x frac x scala x disaster_sl_pct <= 0,50 scatta anche se qualcuno
allarga lo stop invece di alzare la scala.

TEST T1-T11 (tests/test_book_scale.py, 18 verdi). Il piu' importante e' T1b:
a k=1 l'implementazione simmetrica e quella asimmetrica danno lo STESSO
numero, quindi un test di simmetria scritto sul caso di default ha potenza
ZERO. T1b verifica che le due coincidano a k=1 (il rischio e' reale) e che
fuori da k=1 l'asserzione le SEPARI, con un'implementazione asimmetrica
scritta nel test apposta perche' fallisca.

SORVEGLIANTE scale_watch (cron_daily, 3 domande / 3 azioni / 3 stati, una
allerta per streak, marcatore scritto solo dopo invio riuscito — debito #2).
Riporta la frequenza del ramo di fallback, che sopra il 2% in 90 giorni
invaliderebbe la regola: misurata 0/1.676, coi 19 giri "paper capital"
(pre-finanziamento, dove il libro non invia) contati e dichiarati a parte.
Non puo' impedire la modifica: la rende visibile entro 24h e attribuibile.

CHIUDE il debito #5 di §5: T2/T3 sostituiscono il vecchio
test_leva_massima_da_config (che misurava frac x n_asset mentre la grandezza
vera e' frac x n_asset x scala), e T11 verifica che sia rimasto cancellato.

NON FATTO, deliberato: la chiave in config (punto 2 lo vieta), GATE SCALA-01
(A2 richiede >=30 giorni a 1,00 col sorvegliante attivo — "l'unico modo di
scoprire che il sorvegliante e' rotto mentre la leva e' ancora 1,00"),
r0726_fee_sensitivity rifatto (A7: serve solo al gradino; a 1,25x una
liquidazione costerebbe 1,25% non 1,00%, e ereditarlo sarebbe l'errore).

Nessun ordine. Suite: 825 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-01 17:44:02 +00:00
Adriano Dal Pastro 05816c49f9 COLLAR01 (§71): il pavimento funziona, il tetto lo paga troppo — e cio' che vince e' VRP01
Chiesto dall'operatore in quattro battute: hold BTC long o short coperto in
opzioni, scadenza <=15gg, "ridurre la vincita ma bloccare la perdita" (=>
collar, non put protettiva), entrata gated da indicatori ("forte bull"), e
uscita dalle opzioni fra il 50% e il 75% del tempo.

PERCHE' SI POTEVA RIAPRIRE DOPO §46. §46 (tail-hedge) fu refutato sul beta
+0,076 del libro — "non si assicura un libro che nei crash e' gia' quasi
piatto". Qui il sottostante e' un hold di BTC, beta 1,0: quel motivo non si
applica. E §46 dichiarava non provata proprio la copertura gated su regime.

L'entrata non aggiunge un solo parametro: tsmom_blend media tre np.sign() su
(30,90,180) => valori in {-1,-1/3,+1/3,+1}, quindi "forte bull" = |blend|==1
(52,5% dei giorni) contro il confronto dichiarato |blend|>=1/3 (97,1%).

RISULTATI (lente lunga 2021-03 -> 2026-09, 5,44 anni; griglia 48 celle
dichiarata prima + 36 di estensione dichiarata):
- A1 CONFERMATA: il pavimento FUNZIONA, maxDD scende in 36/48 (§46: saliva
  in 162/162). La meta' della domanda ha risposta positiva.
- A3 CONFERMATA: il de-levering lo fa meglio in 45/48. Δdrift/ΔmaxDD 7,90
  (gate forte) / 1,98 (largo): 2-8 punti di drift per punto di DD.
- C9 in forma pura: il tetto taglia il 46,2% dei cicli VINCENTI, il pavimento
  para il 6,7% dei PERDENTI — 7x piu' spesso sui vincenti: troncatura.
- M1: collar Sharpe 0,508 vs TP01 0,852; TP01+10% => +0,000 di Sharpe e
  +2,32pp di maxDD.

IL FATTO CHE VALE PIU' DEL VERDETTO. Le 3 celle vincenti stavano tutte sul
BORDO; estesa la famiglia vince 35/36 nell'ANGOLO (dput 0,02 / dcall 0,50,
Sharpe 1,471) — e il limite di quell'angolo e' una COVERED CALL: la pendenza
porta fuori dalla domanda posta e dentro lo short-vol. E quel 1,471 e' il
prezzatore che si paga da solo: DVOL/RV-forward 1,320 a 7g (sopra nel 76,9%
dei giorni) => riprezzato alla vol vera l'angolo cade a 0,511, che e' VRP01
(0,47). Non una scoperta: VRP01 per una strada piu' lunga. §3 lo blocca.

USCITA ANTICIPATA: implementata (exit_frac) e COSTA. Cella onesta gate forte:
drift +9,48% (scadenza) -> +3,84% (50%), esito da VINCE a perde sotto 0,75.
Il meccanismo previsto c'e' (VRP residuo +3,38 -> +1,27pp) ma lo spread lo
travolge. Corregge l'applicazione di §46: "un roll anticipato non paga f"
vale per una copertura solo LONG; in un collar la gamba venduta va
RICOMPRATA, quindi si paga f sulla parte che a scadenza si regolava gratis.
L'asimmetria si INVERTE quando la struttura ha una gamba corta.

CONTROLLI DELL'APPARATO 3/3 (M15): pranzo gratis riconosciuto (maxDD
51,83%->36,76%, drift +10,04%->+35,69%), premio x10 rifiutato, zero-cost
finito. Cinque difetti miei catturati dai controlli, non a occhio: bisezione
zero-cost invertita (dava Sharpe -3,9), dcall=NaN nella cassa, C9 non
consapevole della direzione (S1>S0 non e' "vincente" per uno short), e due di
contabilita' che avrebbero ADULATO il collar (base che rollava lo spot
pagando ~3,6%/a di fee inesistenti; roll che chiudeva lo spot senza motivo).

Corregge anche un muro di §46: il tick da 5 USDC e' della famiglia USDC; la
catena che raccogliamo e' 100% inverse, quindi li' non si applica.

Regole nuove in CLAUDE.md: M29 (un edge da opzioni prezzate a modello si
riprezza alla vol REALIZZATA prima di crederci), M8 esteso (un argmax sul
BORDO e' una pendenza, non una cella), C4 esteso (il segno dell'asimmetria di
f dipende dal verso della gamba).

Libro, pesi, cron, config INVARIATI. Nessun ordine. Suite: 807 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-01 17:30:18 +00:00
Adriano Dal Pastro 5bcf212923 stato trades: il "+243%" del report e' per il 96,3% un bonifico — TWR +10,80%
`trades_db.py --report` stampa `$598,06 -> $2.051,84 (+243,08%)` accanto a
`netto +40,77`. La serie di 1.657 letture orarie contiene UN SOLO salto: il
versamento di $1.399,39 del 25/08 11:47Z. Confermato dal classificatore
ufficiale del progetto (`journal.movimenti_capitale`: certi 1399.39,
ambigui 0.0, classe `movimento`).

Al netto: TWR +10,80% spezzato sul versamento (+11,61% fino al 25/08,
-0,73% dopo), equity +$54,39 in 69 giorni. Il giornale, che lo scorporo lo
fa gia', concorda: $+62,00 al 31/08, -7,61 di marcatura fino a oggi.

Il difetto non e' nuovo — e' la stessa riparazione che NON ha attraversato
il confine. `journal.py:121` porta il caso d'origine nel docstring (la voce
del 25/08 che dichiarava «+$1.414,57» di giornata); `trades_db.py:83`
calcola `100*(e1/e0-1)` sulla serie grezza e non chiama
`movimenti_capitale()`, che e' a un import di distanza. Variante di P1: non
un sorvegliante che ridichiara il bersaglio, ma una riparazione che non si
e' propagata al secondo lettore della stessa serie. Danno sui soldi nessuno
(sola lettura); danno di citazione si', ed e' l'unico numero fuorviante che
il progetto produce su richiesta di un comando pubblicato in §13.

Codice NON toccato: sta su uno script che legge il libro vivo. Debito #14.

Stato del libro al 01/09 16:47Z, per il resto invariato: 45 fill (ultimo
31/08 15:47), 29 round-trip (21 in utile, netto +40,77), posizioni BTC
0,0045 @ $79.208,11 e ETH 0,0872 @ $2.473,04, non realizzato -$11,72, leva
lorda 0,27x. Nessun fill da 25 ore = banda morta del min_order_usd $5, non
un blocco (il cron logga «gia' al target» a ogni giro). monitor_health 8/8
OK, riconcilio 44/45 con 0 prezzi divergenti (l'unica coppia scoperta e' il
difetto noto dei sei giorni fra log e jsonl sullo stesso fill).

- CLAUDE.md §2: riga nella tabella dei numeri da non citare
- CLAUDE.md §5: debito #14
- docs/diary/2026-09-01-stato-trades.md
- docs/journal/2026-08-31.md (voce del cron, non era committata)

Suite: 800 passati, 0 falliti.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-01 16:52:48 +00:00
Adriano Dal Pastro 8d391ed29a margini: la pagina si ricostruisce dal gateway — e l'"IM %" non e' il margine delle posizioni
L'operatore ha incollato la riga CROSS col modello ATTIVO invece che proiettato:
Available $2.010,81 · IM 2,15% · MM 0,37%. Il gateway, letto allo stesso minuto, dice
available_funds = 2010,82299383. Scarto $0,01.

(a) LO SCREENSHOT NON SERVE PIU'. La riga CROSS della pagina E' `available_funds`, che
leggiamo da soli a ogni giro. Ieri quella schermata era l'UNICA fonte per l'haircut e per il
modello attivo, e per averla e' servito un passaggio dall'operatore e da Wasabi.
r0831_margini_conto.live() la ricostruisce.

(b) TERZA CONFERMA DEL 5%, E LA PRIMA ESATTA:
    1.400,71 + 0,95x654,176 + 0,20 dust - 11,553 IM = $2.010,82   contro pagina $2.010,81
Scarto $0,007. Il 10% della vecchia config non e' improbabile: invertendo la stessa riga da'
IM = -$21,16, aritmeticamente impossibile. Tre strade indipendenti, stesso numero.

(c) MIA LETTURA SBAGLIATA, CORRETTA. L'"IM %" della pagina e'
(margin_balance - available)/margin_balance, non il margine delle posizioni:
    haircut USDE  $32,71 = 1,592%   +   IM vera  $11,55 = 0,562%   =  2,153%
Il 74% di quella percentuale e' HAIRCUT. E' salita da 2,13% a 2,15% perche' abbiamo comprato
collaterale a rendimento — letta come rischio direbbe che ieri sera abbiamo alzato la leva
comprando USDE, l'opposto di quello che e' successo. La MM invece e' pulita ($7,60) e non puo'
contenere l'haircut, che da solo la renderebbe negativa: le due colonne hanno basi DIVERSE e la
pagina non lo dice. Regola: una percentuale letta da una schermata va INVERTITA nella sua
definizione prima di essere confrontata (P7 su superficie nuova).

(d) LA BOCCIATURA DI X:PM ESCE RAFFORZATA. La KB da' USDe al 5% sotto entrambi i modelli:
l'haircut si cancella e l'inversa da' il margine di POSIZIONE sulle stesse due posizioni,
stesso istante — X:SM $11,64 contro X:PM $88,23, 7,6x, e 9,3x la MM. Due misure pulite,
stesso verso. E la riga X:SM era una PROIEZIONE di un modello inattivo che oggi si riproduce
al centesimo: anche la riga X:PM era affidabile, quindi decidere senza provare era corretto.
Ora si sa perche', non solo che.

Suite: 800 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01BmkQty4a99pVmvwGfxAMQ9
2026-08-31 08:39:45 +00:00
Adriano Dal Pastro 62025e7840 docs: X:SM ri-sondato e X:PM scartato — il modello di margine entra nel tetto ma non lo spiega
Le due misure di ieri sera vivevano solo in chat. Ora sono nei documenti, con i numeri
e con cio' che le riapre.

X:SM vs S:SM, stessa notte, stesso conto:
  S:SM  tetto [643,18 - 644,18)  equity $2.055,56  ->  31,29% - 31,34%
  X:SM  tetto [654,18 - 655,18)  equity $2.054,90  ->  31,84% - 31,88%
+0,55pp = +11 USDE ~ $11. L'ipotesi "il tetto dipende dal modello di margine" e' VERA e
INUTILE: per arrivare al 70% mancano ~38 punti, un fattore 2,2x. Un'ipotesi confermata al
terzo decimale e falsa all'ordine di grandezza si archivia come falsa — il tetto resta
misurato e non spiegato.

La lezione di metodo vale piu' del risultato: il primo probe fu un BUY 20, RIFIUTATO, e da
solo avrebbe chiuso la questione con "tetto invariato". Falso: il tetto si era mosso di 11,
cioe' MENO della taglia del probe. Un probe unico di taglia sbagliata produce un falso
negativo che si legge come risultato — la taglia si sceglie sulla risoluzione dell'effetto
che si cerca (M13 in veste nuova).

X:PM valutato e SCARTATO senza provarlo: la pagina margini lo dice gia'. Available Balance
$1.935,14 contro $2.011,73 (-$76,59), MM 3,43% contro 0,37% (~9x). Il PM e' basato su
scenari e premia il rischio che si compensa; due long direzionali nudi sono il suo caso
peggiore. La MM e' la riga che decide: non morde a 0,28x ma sposta il punto di liquidazione.
NON "PM e' peggio" ma "PM e' peggio PER QUESTO portafoglio" — cosa lo riapre: il deploy di
VRP01 o di un altro sleeve di opzioni, che fa compensare il rischio e cambia il segno del
confronto.

Registrato anche il prezzo del cross, che non e' zero: sotto segregato l'USDE era ring-fenced
dalle perdite del libro, sotto cross risponde l'intero conto. Non morde oggi (perdita massima
plausibile ~$617, dentro il solo USDC), ma il verso e' cambiato e tornare a S:SM lo ri-recinta.

Suite: 800 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01BmkQty4a99pVmvwGfxAMQ9
2026-08-31 08:30:51 +00:00
Adriano Dal Pastro 4705d71ceb tetto ri-sondato sotto X:SM: il modello entra ma non spiega — +11 USDE
L'operatore e' passato a Cross: Standard Margin. Verificato dal gateway:
available_funds USDC da ~$1.400 a $2.011,09 contro $2.010,90 attesi con haircut
5% (scarto $0,19) — seconda conferma indipendente del 5%, da una lettura
completamente diversa dallo screenshot.

RI-SONDATO il tetto a saldo neutro, stesso metodo del 31/08:
  SEGREGATO S:SM  [643,18 - 644,18)  equity $2.055,56  = 31,29-31,34%
  CROSS     X:SM  [654,18 - 655,18)  equity $2.054,90  = 31,84-31,88%
Il modello ENTRA nel tetto ma NON lo spiega: +0,55pp = +11 USDE (~$11), non le
centinaia che servirebbero per il 70% (manca ancora un fattore ~2,2x).
L'ipotesi "il tetto dipende dal modello segregato" e' quantitativamente demolita
come spiegazione, pur essendo tecnicamente non nulla.

Nota di metodo: il primo probe (BUY 20) era stato rifiutato e avrebbe fatto
concludere "tetto invariato". Era solo troppo grosso: il test a saldo neutro con
passi piccoli ha mostrato che il tetto si era mosso di 11. Un probe unico di
taglia sbagliata produce un falso negativo che si legge come risultato.

config: venue_cap_frac 0.312 -> 0.318 (bordo basso del bracket CROSS, che e' il
modello attivo; se si torna a S:SM va rimesso a 0.312).

E il costo del passaggio, che va detto: sotto SEGREGATO l'USDE era RING-FENCED
dalle perdite del libro (solo il silo USDC rispondeva); sotto CROSS risponde
l'intero conto. Non morde oggi (perdita massima plausibile ~$617 col disaster-SL,
dentro il solo USDC) ma il rischio strutturale ha cambiato verso. Il cross ha
comprato $611 di margine utilizzabile — inutile a 0,28x, serve sopra ~1,4x che
non e' autorizzata — piu' $11 di capienza.

Suite: 800 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 08:12:31 +00:00
Adriano Dal Pastro fd7595e819 margini: haircut 5% (la config aveva torto) — e il conto NON e' cross-collateral
Lo screenshot della pagina margini era su Wasabi (rclone remote wasabi:, bucket
adp-work, cartella _scambio), non sulla VPS: per questo il percorso non esisteva.
Riconciliazione riproducibile in scripts/research/r0831_margini_conto.py (N11).

(a) HAIRCUT = 5%. La pagina non lo espone come numero: si ricava per differenza,
perche' il CROSS conta l'USDE scontato e il SEGREGATO non lo conta affatto.
  S:SM (attivo)  USDC Available 1.400,86  vs  equity 1.412,28 - IM 11,55 = 1.400,73
  X:SM           CROSS Available 2.011,73
  contributo USDE al cross = $610,81 su $643,05  ->  5,0137%
    5% (KB)     atteso $610,89  scarto $ 0,09  TORNA
   10% (nostra) atteso $578,74  scarto $32,06  NON torna
config/live.json: haircut 0.10 -> 0.05. Il 26/08 il 10% fu registrato come
"verificato sul venue" senza traccia di COME, e non lo era.

(b) 🚨 IL CONTO NON E' CROSS-COLLATERAL: modello attivo "Segregated: Standard
Margin" (S:SM). Nella tabella del modello attivo l'USDE NON COMPARE: non fa
margine per i perp USDC-settled del book, e l'haircut oggi non si applica. Il che
spiega a posteriori perche' la misura di stamattina trovava $0,0000 accantonati:
non stavo guardando nel secchio sbagliato, cercavo un parametro che sul nostro
conto non e' in vigore.

NON MORDE: al massimo lordo del libro (1,0x = ~$2.056 di nozionale) l'IM sarebbe
~$41 contro $1.400 di USDC disponibile, 34x di copertura. Nessuna decisione
operativa cambia oggi.

Ma la premessa in CLAUDE.md era falsa, e il modo in cui lo era e' istruttivo:
"l'equity del book e' il TOTALE cross-collateral" metteva due cose sotto un nome
solo. Come RICCHEZZA sommare USDC+USDE e' giusto ed era il punto della riparazione
del 26/08 (evito' il falso "USCITA DI FONDI -24%"); come CAPACITA' DI MARGINE e'
sbagliato, perche' nel modello attivo l'USDE vale zero. Finche' il margine non
morde le due coincidono nell'uso, e infatti non era mai emerso.

Corretta anche la riga di usde_watch che stampava "margine utilizzabile ~$2.013
(haircut 10%)": era falsa due volte insieme. Ora stampa il solo silo USDC e,
accanto, cosa darebbe il cross.

La quota USDE non e' "collaterale diversificato": e' cassa a rendimento FUORI dal
sistema di margine. Passare a X:SM aggiungerebbe $610,87 di margine utilizzabile
ma porta la meccanica cross (collateral fee 0,05%/giorno sul saldo negativo,
ribilanciamento automatico): decisione dell'operatore, oggi non serve.

Ipotesi nuova e non verificata: il tetto del ~31,2% potrebbe dipendere proprio dal
modello segregato. Si saprebbe passando a X:SM e ri-sondando.

Suite: 800 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 08:01:21 +00:00
Adriano Dal Pastro c8be83ef6e haircut: la divergenza non si chiude dal gateway — misurato perche', non supposto
Richiesta: leggere la pagina margini del conto per chiudere il 5% (KB) vs 10%
(nostra config). NON E' RAGGIUNGIBILE da qui: account_summary per la valuta USD
da' "Invalid currency", il parametro `extended` viene ignorato, e il gateway
filtra a 8 campi senza initial_margin/maintenance_margin (debito #11).

E non e' che si sia guardato nel secchio sbagliato: la contabilita' TORNA ESATTA
senza alcun termine di haircut.
  USDC equity 1412.281074  available 1400.728093  riservato 11.5530
  USDE equity  643.175691  available  643.175691  riservato  0.0000
  posizioni lorde $577.65 -> IM al 2% = $11.5530 -> RESIDUO -$0.0000
Un haircut al 5% chiederebbe $32,16 accantonati, al 10% $64,32: non ci sono.
=> L'haircut non e' osservabile in ALCUN campo esposto. O e' applicato solo nella
vista cross/USD che il gateway filtra, o non e' applicato al nostro conto: da qui
le due cose non si distinguono, e non le si sceglie tirando a indovinare.

La divergenza resta APERTA, ma con la ragione MISURATA invece che supposta. La
chiudono 30 secondi sulla web UI o delle chiavi API Deribit (la decisione gia'
dichiarata nel debito #11, non un refactor). Nel frattempo non morde nulla di
osservabile: l'IM e' il 2% del nozionale e l'USDE resta interamente disponibile,
quindi 5% o 10% non cambia una cifra operativa.

L'operatore ha dichiarato che il conto e' STANDARD MARGIN. Aggancia due cose:
  - la colonna da leggere e' Haircut (X:SM), che per USDe dice 5% come la PM:
    ora si sa con certezza quale numero ufficiale contraddice il nostro;
  - spiega perche' l'IM misurata e' esattamente 1/50: il nuovo modello di margine
    del 05/08 si applica ai "standard margin accounts", tier 1 C1=50. Un fatto
    dichiarato dall'operatore e una misura fatta senza conoscerlo si confermano
    a vicenda — ed e' la PRIMA affermazione del venue che il conto conferma questa
    settimana, dopo l'APR USDC e "all users can buy BUIDL".

Lo screenshot non e' arrivato: il percorso sta sul desktop dell'operatore, non
sulla VPS.

Suite: 800 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 07:53:26 +00:00
Adriano Dal Pastro 30286ea033 venue_news: sorvegliare cosa il venue ANNUNCIA — e due correzioni dalla KB
Nasce dall'annuncio sulla fine della Proof of Reserves. La notizia in se' vale
poco: si perde un segnale ad alta frequenza e DEBOLE (una PoR auto-pubblicata
prova che gli attivi esistono in un istante, non che coprano le passivita') e si
guadagna un audit annuale indipendente sotto VARA piu' il 90% degli attivi presso
Coinbase come custode. E non l'abbiamo mai sorvegliata: zero occorrenze nel
codice. Rinunciato di proposito a catturare l'ultimo dato — uno snapshot singolo
auto-riportato non regge lo standard di prova e non permetterebbe di stimare `p`.

CONSEGUENZA VERA: la decisione "100% Deribit fino a $20k" ha fra i suoi riapritori
"`p` che diventa stimabile invece che assunto". Dal 1/9 il segnale pubblico passa
da quotidiano ad ANNUALE: da una serie si stima, da un punto all'anno no. Quel
riapritore diventa praticamente irraggiungibile => la decisione e' ora gated SOLO
dal capitale.

TROVATO CERCANDO: esiste un feed RSS degli exchange-update, e conteneva quattro
annunci materiali che nessuno leggeva. Il caso che decide: le specifiche dei perp
USDC sono cambiate il 18/08, ANNUNCIATE IL 14/08. check_specs() e' nato da quella
svista e gira ogni ora, ma rileva la deriva DOPO; il feed l'avrebbe detta quattro
giorni PRIMA. La prima volta e' andata bene solo perche' i cambi erano RIDUZIONI.

Costruito scripts/live/venue_news.py (in cron_daily accanto a fee_watch):
  - NON interpreta: dice "e' uscito questo, guardalo". Nessun automatismo su un
    testo di marketing (P13). Classifica solo l'urgenza.
  - parole-chiave DERIVATE da deribit._CONTRACT e config/live.json, non
    ridichiarate (P1): chi aggiunge un asset allarga la sorveglianza da solo, ed
    e' il test che lo blinda.
  - primo giro semina senza allertare (P9); feed illeggibile -> exit 2, mai
    silenzio implicito (P5).
Debito #8 si RESTRINGE, non si chiude: il Rulebook non ha un feed.

Confermato due volte lo zero USDC: l'espansione del 31/07 non contiene l'Italia
ne' alcun paese UE, mentre San Marino e Citta' del Vaticano SONO idonei. Non
asserisco una causa (ci sono anche Canada e Giappone).

DUE CORREZIONI dalla KB "Cross collateral specifications":
(a) Il saldo negativo costa una collateral fee dello 0,05% AL GIORNO = 18,25%/anno,
    al secondo — 4,3x la resa USDE. Il 30/08 avevo scritto "lo finanzia a
    interesse" SENZA il numero: giusto e vuoto. Col numero, il criterio del
    cuscino di regolamento diventa aritmetica (-14 punti). E il ribilanciamento
    automatico non salva: scatta a $1M assoluti o al 100% della cross equity,
    irraggiungibili a $2k. Non veniamo ribilanciati: sanguiniamo la fee.
(b) L'haircut USDe ufficiale e' 5%, noi abbiamo 0.10 registrato come "verificato
    sul venue" il 26/08 senza traccia di come. NON riparato (P12/M28): si tiene
    0.10 perche' e' il lato conservativo, non e' sul percorso soldi e non morde
    fino al 90% di quota. Divergenza dichiarata in config.
Di lato: BUIDL haircut 2% (sarebbe stato il miglior collaterale del listino, se
si potesse comprare), stETH 7,5% (terza ragione indipendente per lasciarlo stare).
Nessuna fonte documenta un tetto sulle QUANTITA': il ~31,2% resta misurato e non
spiegato — e ora si sa che non e' una svista di lettura.

Suite: 800 passati (5 nuovi su venue_news).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 07:47:15 +00:00
Adriano Dal Pastro 41f83b5dd8 BUIDL-01 CHIUSO: non entrabile — e la frase pubblicata da Deribit e' falsa per noi
Esito del test pre-registrato dieci minuti prima (7b8e356). Si chiude con un esito
che NON era fra i due previsti: i criteri contemplavano ">=1 reward -> IDONEO" e
"zero reward -> NON IDONEO", ma non si riesce a comprare BUIDL affatto, quindi la
domanda sull'eligibilita' ai reward e' priva di oggetto. Un gate puo' fallire sulla
sua PRECONDIZIONE invece che sul suo criterio, e va scritto cosi'.

Undici ordini rifiutati con not_enough_funds_in_currency, fino a 1 unita' a limite
1,0100 contro ask 1,0004 con 10.730 di profondita', tenendo ZERO BUIDL e avendo
$1.412 disponibili per comprarne $1. Esclusi uno per uno tutti i sospetti che
sull'USDE avevano portato fuori strada: prezzo (incrocia di 96 bps), liquidita',
taglia (il minimo dello strumento), fondi, tetto sul livello (teniamo zero), wallet
(account_summary risponde). Costo del test: $0, nessun fill.

🚨 "All Deribit users are permitted to buy and sell BUIDL tokens in the spot markets
on Deribit, with no extra requirements" — insights.deribit.com. NON per noi.
Motivo plausibile e non verificato: BUIDL e' un titolo (fondo BlackRock via
Securitize), distribuzione ristretta a monte dell'exchange. Il fatto misurato e' il
rifiuto, non il suo motivo.

REGOLA (due affermazioni pubblicate smentite dal conto in due giorni — APR USDC
3,40% e "all users can buy BUIDL"): una capacita' PUBBLICATA dal venue non e' una
capacita' del CONTO. Si verifica sul conto, prima che entri in un piano, e costa un
ordine da $1. E' N10 un passo piu' in la': non basta il sito, non basta il venue,
serve il conto.

SOTTOPRODOTTO che vale piu' del test: not_enough_funds_in_currency e' il messaggio
GENERICO di Deribit per "non puoi acquisire altra di questa valuta" — permesso
(BUIDL, zero in mano) o tetto (USDE, ~31,2% dell'equity), mai i fondi. Chi lo
incontra salti subito alla domanda giusta invece di inseguire taglia, cadenza e
prezzo come e' successo il 30/08.

=> L'USDE resta l'unico collaterale a rendimento che il conto puo' usare, ed e' al
suo tetto; i $1.412 di USDC continuano a rendere zero. Non per mancanza di
alternative: le tre alternative sono chiuse per giurisdizione (USDC), per permesso
(BUIDL) e perche' non e' un dollaro (stETH).

balance_watch esteso a BUIDL: se l'accesso si aprisse, un balance non nullo lo
direbbe da solo. Suite: 795 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 07:35:32 +00:00
Adriano Dal Pastro 7b8e35633d BUIDL-01: criteri pre-registrati PRIMA dell'esecuzione e dell'esito
Test di eligibilita' sul collaterale BlackRock (Treasury USA tokenizzati), taglia
500 BUIDL come il test USDE del 26/08. Nasce dalla domanda su stETH: stETH rende
2,22% (meta' dell'USDE) ed e' ETH, non un dollaro — coprirlo e' CC01, gia'
parcheggiato a scala 20k+. I custodi sono istituzionali e comunque nessuna via
custodiale restituisce i reward USDC (esclusione italiana per giurisdizione).

BUIDL invece e' comprabile, liquido, in cross-collateral, e soprattutto e' un
emittente DIVERSO: oggi il conto ha $1.412 di USDC che rendono zero e il rischio
emittente concentrato al 100% su Ethena.

Criteri dichiarati adesso, esito da leggere il 2026-09-04:
  ELIGIBILITA': >=1 reward entro le 23:00 UTC del 03/09 -> IDONEO; zero -> NON
  IDONEO, si riconverte e la pista si chiude. Tre finestre feriali piene.
  TETTO: sondato a saldo neutro, registrato col suo bracket E l'equity del
  momento (sull'USDE il tetto e' una frazione, non un livello).
  HAIRCUT: dichiarato NON misurabile a questa taglia, e non vincolante.

Committato PRIMA dell'esecuzione: l'ordine dei fatti sta in git.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 07:30:40 +00:00
Adriano Dal Pastro f151316bdf usde: il tetto e' una FRAZIONE dell'equity (~31,2%), non un livello — e ora e' in config
Fonte: articolo ufficiale Deribit "Yield/reward bearing coins" (WebFetch lo prende
403, si legge dall'API Help Center in JSON). Tre correzioni alle conclusioni di
ieri.

1) L'ITALIA e' nella lista delle giurisdizioni escluse dai reward USDC. Lo zero
misurato e' confermato dalla fonte, ma la mia ipotesi MiCA era SBAGLIATA: la
lista contiene Canada e Giappone, non e' il perimetro MiCA. E' policy di
giurisdizione Deribit. M27: una fonte normativa si verifica, non si deduce.

2) La finestra di pagamento USDC e' di DUE SETTIMANE ("within the first two
weeks of the following month"), non tre giorni. Avevo verificato su 8/14 e 3/14
giorni. Rifatto sulle finestre vere: LUGLIO conclusivo (atteso $1,72 contro
un'escursione TOTALE dell'equity di $0,48 in 1-16/08, zero scalini compatibili),
GIUGNO no (il libro opera da meta' mese, rumore della taglia del segnale). La
conclusione non cambia, ma l'evidenza e' UNA finestra piu' la lista ufficiale,
non due: il "172x" del 30/08 era sovra-affermato.

3) IL TETTO NON E' UN LIVELLO, E' UNA FRAZIONE. L'articolo documenta un Cap
ETHENA che diluisce il TASSO a livello di exchange e nessun limite sulle
quantita' detenibili: il muro non aveva base documentale e andava ri-sondato.
Fatto il 31/08 (giorno UTC nuovo -> non e' un limite giornaliero): ieri si
tornava a 644,18, oggi no, con l'equity scesa di $8.
    30/08  tetto [644,18 · 645,18)  equity $2.063,79  = 31,21-31,26%
    31/08  tetto [643,18 · 644,18)  equity $2.055,56  = 31,29-31,34%
0,05pp di scarto, dentro il rumore dell'equity (+-$2-8/ora). Candidato pulito
5/16 = 31,25%, ma a questa risoluzione non si distingue da una regola sul
collaterale scontato dell'haircut (~29%): si cita la banda (M25).
=> Il tetto SCALA col conto: la quota resta ~31%, il valore in dollari cresce
col capitale, il 70% non e' raggiungibile ne' ora ne' mai. E, essendo pinnati
al tetto, il rischio emittente resta una frazione COSTANTE del conto.

Cablato (rispondeva a "dove e' scritto il valore del tetto": in tre note di
testo e in nessun posto che il codice leggesse, tanto che usde_convert --quota
0.70 dichiarava "piano valido" per un ordine che il venue rifiuta):
  - config/live.json usde.venue_cap_frac 0.312 + venue_cap_misurato
  - src/live/usde.py lo porta nei default (unica autorita', P1)
  - usde_convert.piano() rifiuta il bersaglio sopra il tetto PRIMA di sparare
    e stampa il massimo raggiungibile. Verificato su entrambi i rami.

Anche: l'USDe ha un fee Deribit del 5% mai nominato prima. Il nostro misurato
(~4,5%/anno) e' gia' netto: e' l'unico numero da citare.

Stato: USDE 643,175691 (31,29%, al tetto), USDC $1.412,40, totale $2.055,57.
Suite: 795 passati.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-31 07:27:23 +00:00
Adriano Dal Pastro c250c04371 usde: l'USDC NON frutta sul nostro conto — misurato, e §6 di stasera era sbagliata
Domanda dell'operatore: "verifica se l'USDC frutta davvero sul nostro conto".

Sembrava dover aspettare: il gateway non espone il Transaction Log
(get_transaction_log, get_settlement_history, get_deposits, get_transfers,
get_interest_history: tutti 404 — debito #11) e l'unica serie storica e'
trades.db.equity, oraria ma arrotondata a 2 decimali e sporcata dal P&L non
realizzato (+-$2-8/ora a posizioni aperte), dove $0,13/giorno sparisce.

La fonte ufficiale Deribit ha spostato il problema dal rumore al calendario: i
reward USDC si pagano UNA VOLTA AL MESE ("paid out as a single monthly payment
early in the following month"), accrual alle 00:00 UTC sulla minima equity —
non ogni giorno come l'USDE. Ecco perche' una sorveglianza giornaliera non
poteva vederli. E un accredito mensile da qualche dollaro si vede benissimo
anche a 2 decimali, purche' il libro sia FLAT: allora equity == balance == USDC
e ogni scalino e' un accredito.

MISURA, due confini di mese entrambi a libro flat:
  29/06 -> 08/07  equity 598,06 costante, 237/237 ore ferme, 0 scalini  (attesi $0,45)
  31/07 -> 03/08  equity 596,92 costante per 4 giorni pieni             (attesi $1,72)
Il secondo e' decisivo: $1,72 contro una risoluzione di $0,01, 172x. Zero
MISURATO, non zero sotto soglia.

=> La premessa originale del gate USDE-01 e' RESTAURATA: il guadagno di tenere
USDE e' il tasso pieno ~4,1%, non lo spread 0,71 punti che avevo scritto poche
ore fa. Sui $644: ~$26/anno, non ~$4,6.

Cosa avevo sbagliato: ho letto `apr: 3.4` in public/get_currencies e l'ho
trattato come una proprieta' del NOSTRO CONTO. Era un listino del VENUE. La
"conferma indiretta" che invocavo provava che il listino e' reale per l'USDE e
non diceva nulla sull'idoneita' dell'USDC. Un tasso pubblicato non e' un tasso
incassato: si verifica sul conto — ed e' costato una query su una serie che
avevamo gia'.

Esclusione plausibile ma NON verificata: MiCA (USDC e' e-money token, USDe no);
Deribit dice solo "eligibility is based on their location". Il fatto misurato
e' lo zero, non il suo motivo.

Nuovo: scripts/live/balance_watch.py + scripts/cron_balance.sh (orario al
minuto :42, libero fra :25/:35/:47, sola lettura). Registra il BALANCE a 8
decimali per valuta — la serie che mancava — col conteggio dei fill dall'ultimo
campione e il nozionale lordo, cosi' una finestra sporca si riconosce invece di
essere mediata dentro. Etichetta PULITA le finestre a 0 fill e libro flat, dove
il delta USDC E' l'interesse, e ne stampa l'APR implicita.

Suite: 795 passati. L'ERROR di teardown e' il falso positivo dichiarato dalla
guardia stessa: il cron :47 ha scritto un fill reale (ETH BUY $+9, 23:47:19)
mentre la suite girava.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-30 23:48:52 +00:00
Adriano Dal Pastro a45794d2cb usde: il venue mette un TETTO al 31,21% — e l'USDC paga gia' 3,40%
Richiesta dell'operatore: "porta in usde tutto il capitale che non viene
usato". Il margine consuma $11 su $2.063 e l'USDE e' cross-collateral: preso
alla lettera vale una quota ~99%, cioe' il 100% che il gate esclude. Portata
all'operatore con le cifre, ha scelto 70%.

Il 70% non e' un argmax (M8): e' il massimo compatibile col CUSCINO DI
REGOLAMENTO, il vincolo che r0830_usde_quota non aveva guardato. P&L e funding
dei perp USDC-lineari si regolano in USDC, non nel collaterale, quindi la
quota non la limita l'haircut ma il saldo USDC che deve reggere il disaster-SL
sulla massima esposizione: 2 x 0,5 x 0,30 = 30% dell'equity, che lascia il 70%.

ESEGUITO +144 USDE (500,1757 -> 644,175691), quota 24,24% -> 31,21%, fee 0.
Poi il muro.

(a) TETTO DEL VENUE, misurato e non documentato da nessuna parte. Provato a
saldo neutro: BUY 20 rifiutato, SELL 20 OK, BUY 20 OK, BUY 5 rifiutato, con
$1.408 disponibili. E' un tetto sul LIVELLO. Il messaggio del venue
(not_enough_funds_in_currency) e' fuorviante e ha fatto inseguire tre ipotesi
sbagliate: taglia (falso, ma min_trade_amount=1 e' vero), rate-limit (falso),
prezzo (vero in parte: il book REST pubblico e' in ritardo sul matching engine
e prezzavo l'ordine sull'INDICE invece che sul BOOK — l'indice marca il
collaterale, il book prezza lo scambio). La cronaca resta nel diario: chi
rilegge non deve rifare il giro.

(b) L'USDC PAGA 3,40%. public/get_currencies: USDE 4,1071%, USDC 3,4000%, e i
nostri reward USDE misurati (~4,5%/anno) confermano che quelle APR sono reali.
Il guadagno non e' il tasso, e' lo SPREAD: 0,71 punti, ~$4,6/anno sui $644 che
teniamo, non i $21 che il gate implicava. Il gate ha misurato il reward
dell'USDE e non ha mai chiesto cosa facesse l'USDC fermo: manca il
controfattuale, M1 in un'altra veste. NON dimostrato che sia accreditato sul
nostro conto — da verificare su un giorno senza trade.

Nuovo attrezzo scripts/live/usde_convert.py: dry-run di default, banda prezzo,
tetto hard di quota, cuscino di regolamento derivato da config. NON passa da
execution.ALLOWED, che resta ai soli due perp.

config: quota_target 0.70 registrato; quota_max_frac alzato a 0.85 e RIMESSO a
0.50 nella stessa sessione — la soglia larga presupponeva un 70% che non
esiste, e lasciarla avrebbe disarmato la guardia per uno scenario che non si e'
verificato.

Suite: 795 passati, 0 falliti.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-30 20:18:31 +00:00
Adriano Dal Pastro 3cf884fa39 CLAUDE.md: la riga USDE-01 cita il tasso con la sua banda — 3,26% [1,13-4,51], n=4
Citava "3,80% su UNA finestra, 1,90% su DUE": due letture di n=1 e n=2, senza banda,
cioe' esattamente cio' che la §2 vieta. A quattro finestre il numero e' 3,26% annuo
con banda bootstrap [1,13% - 4,51%], e la larghezza (3,4 punti su un livello di 3,2%)
E' il risultato: a n=4 il tasso non e' misurato.

Aggiunto il risultato che governa la decisione di domani: l'EV e' lineare in q, quindi
non puo' scegliere una quota interna. E i tre numeri che la incorniciano: il margine
non e' il vincolo (l'haircut non morde fino al 90% di quota, nemmeno a leva 1,50x con
USDE marcato alla soglia critica 0,95 — 29x di cuscino), la resa vale $16/anno cioe'
meno di un mese di versamento, e aspettare quattro settimane costa $1,33 per 8x le
finestre.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01E1gJmWPA4rEhmc6CQQuNZw
2026-08-30 17:41:14 +00:00
Adriano Dal Pastro 035bd086a2 usde: l'EV non puo' scegliere la quota — e aspettare 4 settimane costa $1,33
La decisione di quota e' dovuta lunedi' 31/08. Il risultato strutturale, dichiarato
prima di guardare i numeri: l'EV e' LINEARE in q, quindi il suo argmax e' sempre un
angolo (0% o 100%) e non puo' produrre una quota interna. Ogni quota intermedia nasce
da un criterio sulla CODA, che va dichiarato e non ottimizzato (M8). Lo script quindi
non sceglie: mette il prezzo accanto a ogni criterio candidato.

Misure:
- rendimento 3,26% annuo su n=4 finestre (3 pagate), banda bootstrap 95%
  [1,13% - 4,51%] su 200.000 ricampionamenti. Larga 3,4 punti su un livello di 3,2%:
  a n=4 il tasso non e' misurato, e' abbozzato. Il punto stimato si DERIVA da
  usde_watch.rendimento() invece di essere ridichiarato (P1), e la divergenza fra i
  due denominatori (0,06 punti) e' stampata, non appianata (P12).
- l'hazard annuo di pareggio E' l'APR: la quota e' EV-positiva se e solo se si crede
  che Ethena stia sotto il 3,3%/anno di evento catastrofico. Numero ASSUNTO, non
  stimato, come il p di Deribit del 26/07 — il cui framework P=1-(1-p)^20 lo script
  riproduce prima di usarlo (10/18/33/64% contro 10/18/34/64% registrati).
- il haircut 10% NON morde a nessuna quota testata, fino al 90%: il libro gira al
  2,00% di margine ($11,37 su $568,64), tre ordini di grandezza sotto il collaterale.
  Il vincolo non e' il margine (D5: buco quantificato e innocuo).
- il churn da depeg critico vale ~$52 di nozionale a quota 50%: secondo ordine.

Il numero che decide (N10 — una data si giustifica col COSTO della misura): la
conversione e' fee 0 e ~3 bps di spread, quindi la decisione e' reversibile a
~6 bps. Alzare a 50% fra quattro settimane invece che domani costa $1,33 di resa non
incassata e porta il campione da 4 a 32 finestre, stringendo la banda da ~3,4 punti
a ~1,2.

Due letture del rischio che non si annullano (M28): l'USDE fa perdere soldi solo nel
mondo in cui Ethena salta E Deribit sopravvive, quindi il rischio aggiunto e' di
secondo ordine — ma e' un terzo strato sullo stesso conto, e N4 dice che un rischio
di venue si compra con un secondo CONTO. La prima dice che costa poco, la seconda
che non e' li' che si compra sicurezza.

Verdetto a runtime: risoluzione insufficiente per alzare · nessun vincolo operativo ·
scala (la resa di oggi vale $16/anno, meno di UN mese di versamento: la leva binding
resta il bonifico) · asimmetria (gia' a 24,2% l'evento emittente vale 3,1x il maxDD
dell'intero libro) · reversibile e quasi gratis da rimandare.

La scelta resta dell'operatore: lo script mette i prezzi, non ne sceglie uno (N4).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01E1gJmWPA4rEhmc6CQQuNZw
2026-08-30 17:38:35 +00:00
Adriano Dal Pastro fc24ee5f52 journal: voce COMPLETA del 29/08 sostituisce la parziale — 24/24 giri
Il cron notturno (00:37Z del 30/08) ha riscritto la pagina come annunciato
dalla versione parziale. I numeri di GIORNO passano dalla frazione di 7 giri
al giorno intero: equity $2,056.87 (era $2,051.29), P&L giorno +$4.51 (era
-$1.07), trading cumulato +$59.42, DD dal picco -0.81%.

Implicita ancora sotto la realizzata su entrambe le gambe (BTC 37.4 vs 44.0,
ETH 51.1 vs 68.9), DVOL al 19° e 18° percentile dell'anno: VRP01 resta fermo
per costruzione, IV-rank 0.07 e 0.12 sotto la soglia 0.30 del gate.

Aggiunta la sezione Analisi (agente), assente nella parziale. Salute pulita:
24/24 giri di book_execute, feed SKH a 0 min.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01E1gJmWPA4rEhmc6CQQuNZw
2026-08-30 13:11:48 +00:00
Adriano Dal Pastro bb33df472f journal: voce PARZIALE del 29/08 — implicita al 24° e 17° percentile, VRP01 resta fermo
Scritta a mano alle 06:49Z, quindi marcata PARZIALE: copre 7 giri su 24 e non si
aggiorna da sola. Il cron la riscrive completa dopo le 00:30 di domani.

Equity $2.051,29, nozionale $555, leva 0.27x. Giornata -$1,07 su 7 letture, 1 fill
e 1 round-trip (+$0,02 netto). Cumulato dall'arming +$1.453,23, di cui $1.399,39
versati -> trading +$53,84. Entrambe le gambe a target, SKH01 flat su tutte e due:
il rischio resta interamente TP01.

Due cose che la Lettura tira fuori:
- l'implicita e' crollata in un giorno — DVOL BTC dal 47° al 24° percentile di un
  anno, ETH dal 45° al 17° — MENTRE la realizzata 30g saliva (44,1% e 68,9%). E'
  lo spread in cui vivrebbe VRP01, ma il suo gate guarda l'IV-rank espandente
  (0,09 e 0,12 contro una soglia di 0,30) e tiene lo sleeve fermo: dice di no
  esattamente dove l'occhio direbbe di si', ed e' per questo che esiste.
- prima comparsa della riga [drawdown]: -1,08% dal picco di $2.073,59, con la sua
  avvertenza attaccata (letture ORARIE, non minimo intra-giorno: e' un pavimento).

Campo `nota` lasciato vuoto: e' dell'operatore.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-29 06:51:22 +00:00
Adriano Dal Pastro 993d17556a usde: gate CHIUSO IDONEO, quota rinviata a lunedi' — l'APR si legge col suo n
Il 2026-08-28 12:35Z `usde_watch` ha rilevato il primo reward (+0.052055 USDE su
500), e la regola pre-registrata il 26/08 PRIMA dell'esito ha chiuso il gate
USDE-01 su IDONEO. Si apre la decisione di QUOTA, che e' dell'operatore.

DECISIONE DELL'OPERATORE (29/08): la quota si decide lunedi' 31/08, su tre-quattro
finestre invece che su una. Il motivo e' un numero: sul solo pagamento il tasso
implicito e' 3,80% annuo, su DUE finestre — il 27/08 aveva pagato ZERO — e' 1,90%.
Fra i due c'e' tutta la decisione, e il campione e' UN pagamento.

`rendimento()`: APR sulle finestre OSSERVATE, col denominatore sul TEMPO VERO e
non sul numero di finestre pagate — cosi' una finestra che non paga ABBASSA la
stima invece di sparire (P5: quel silenzio e' uno zero). Le letture con trade nel
mezzo si escludono, non si riparano in silenzio (P12). L'APR si stampa sempre col
suo `n`, e sotto 4 finestre la riga dice «un pagamento non e' un tasso». Sulle
letture vere: 1,97% annuo su 1,9 giorni, 1/2 finestre pagate.

`quota_da_decidere()`: vera SOLO se IDONEO E il rinvio e' scaduto. Da lunedi' il
watch manda il 📌 OGNI giorno — quota attuale, tetto di allerta, APR osservato —
finche' non si decide (N9: una decisione rinviata senza promemoria e' rinviata per
sempre). Stesso schema della soglia $15k di GTAA01, con la data al posto del
capitale. Si smette togliendo `DECISIONE_QUOTA_DAL`.

6 test nuovi, incluso il controllo positivo — «la finestra sola darebbe il doppio»
— che e' esattamente la ragione per cui l'APR non si cita senza il suo n.

CONFERMATO il fix IB di ieri: il giro delle 00:30 ha 0 righe
`orders request timed out` (erano 2 per giro, 63 su 63) e tutti e sei gli ETF
scaricati. E una conferma involontaria del debito §5.13: SPY e' passato da
1996-09-04 a 1996-09-05 — la finestra rotolante ha perso un altro giorno in una
notte, come misurato.

Diario: docs/diary/2026-08-29-usde-idoneo-e-ib.md
Suite: 795 passati, 0 falliti.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-29 06:45:47 +00:00
Adriano Dal Pastro 2beb11b764 fetch IB: client in readonly — via due righe d'errore da 63 notti su 63
`fetch_ib_equities.py` si connetteva senza `readonly`, e ogni notte il log del
cron si prendeva

    open orders request timed out
    completed orders request timed out

126 righe in 63 giri. Due errori innocui ripetuti per sempre sono il modo in cui
un errore VERO smette di farsi notare (P14): su `cron_daily.log`, 126 dei 146
match di "error" erano questi.

CAUSA, letta nel sorgente di ib_async e non indovinata: in `IB.connectAsync` le
richieste "open orders" e "completed orders" esistono SOLO se il client non e'
readonly (`if not readonly: reqs[...]`), e sul gateway paper non rispondono.
Questo client scarica storico e non manda ordini mai: `readonly=True` e' insieme
la cura del rumore e la dichiarazione corretta di cosa fa. Tolta la CAUSA, non
filtrato il messaggio — filtrarlo avrebbe nascosto anche il giorno in cui quel
timeout significasse qualcosa.

VERIFICATO con un A/B sul solo flag, contro il gateway vero:
  · readonly=False -> le due righe compaiono, e si apre sul gateway il dialogo
    modale "API client needs write access action confirmation" (visto nei log del
    container, resta su ~75s);
  · readonly=True  -> nessuna delle due righe, nessun dialogo.

⚠️ CIO' CHE NON E' STATO VERIFICATO, e va detto: in nessuna delle quattro prove
fra le 13:05 e le 15:35 UTC il gateway ha servito storico — 0 barre con ENTRAMBI
i flag, quindi la causa non e' questa modifica, ma non ho potuto confermare
end-to-end che il fetch continui a riportare barre. La conferma e' il log del
cron di stanotte: se SPY/QQQ/IWM/TLT/GLD/HYG tornano con le loro barre e senza
le due righe di timeout, e' a posto; se tornano tutti a 0, si revoca il flag.
Il fallimento e' comunque innocuo: con 0 barre lo script NON sovrascrive i
parquet (verificato: eq_spy/eq_qqq intatti dopo i tentativi falliti).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 13:31:22 +00:00
Adriano Dal Pastro 32e1649dcb test: la suite non parla piu' al canale di allarme vero
Difetto trovato addosso: `uv run pytest` mandava messaggi Telegram VERI sul
canale dell'operatore — cinque per giro, col testo delle fixture («Analisi di
ieri.», «rete KO», «Testo dell'agente.») sotto l'intestazione di una voce di
giornale del 21/08. Colpevoli i cinque test di `analista.CLI.scrivi()`, che non
passavano `telegram=False` e percorrevano `invia()` fino a `notifier.send()`.
`_cfg()` legge il token da `.env.mainnet`/`.env`: il fatto che non fosse
nell'ambiente non proteggeva niente.

NON E' COSMETICO. E' P9 al contrario — allarmi finti spesi su un canale che
deve restare credibile il giorno che l'allarme e' vero. Chi riceve cinque
messaggi identici a ogni giro di test impara a non aprirli, ed e' l'unico
canale da cui passano disaster-SL, uscita di fondi e venue giu'.

RIPARAZIONE STRUTTURALE, stessa lezione del watermark (§5.12): si blocca la
RETE in una fixture autouse, non si chiede a ogni autore di ricordarsi un
parametro. Un test che vuole davvero esercitare `send()` continua a funzionare
— patcha `urlopen` nel proprio corpo e vince su questo.

In piu' una guardia di sessione: bloccare non basta, un tentativo va TROVATO e
reso esplicito, o resta li' pronto a tornare vero il giorno che qualcuno cambia
il boundary. Validata su controllo positivo (M15): un test che chiama
`notifier.send()` fa fallire la sessione.

⚠️ E un difetto fatto e corretto nello stesso giro: la prima versione registrava
l'URL, che contiene il BOT TOKEN in chiaro — e quella lista finisce nel
messaggio di un assert, cioe' nell'output della suite e nei log. Ora si registra
solo "telegram sendMessage": serve sapere CHE si e' tentato, non VERSO DOVE.
Il token e' stato esposto una volta nell'output di quella verifica: va ruotato.

Suite: 789 passati, 0 falliti.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 13:04:19 +00:00
Adriano Dal Pastro 418f523be7 gtaa: la decisione tenere/bloccare va a $15k — gate (A) ritirato, soglia sorvegliata
Decisione dell'operatore: GTAA01 NON si blocca oggi, si decide quando il book
arriva a $15k. Il motivo registrato non e' «non contribuisce» — la misura dice
il contrario (+0,095/+0,124 di Sharpe a iso-rischio secondo la fase, positivo in
tutte e cinque, hold-out +0,247, 6 anni su 8, correlazione col resto +0,087).
Il motivo e' che sotto $15k di book lo sleeve NON E' ACCENDIBILE:
GTAA_MIN_CAPITAL e' $3.000 allocati, che al peso 20% fa $15.000 contro i $2.068
attuali. Finora era manutenzione senza beneficio incassabile.

Registrate anche le due ragioni contro il blocco, che restano valide: N7 (uno
sleeve difensivo si giudica sul sinistro, e questa finestra non lo contiene) e
N4 (togliendolo il portafoglio di ricerca diventa 100% cripto su un venue solo).
E il costo che sarebbe andato pagato: GTAA01 e' uno dei quattro nomi di
W_DEPLOY, da cui escono i $313k del muro.

PERCHE' LA DECISIONE NON SI DIMENTICHI (N9). Una decisione parcheggiata su un
numero che nessuno sorveglia e' parcheggiata per sempre. `journal.SOGLIE_CAPITALE`
legge l'equity ogni giorno — il giornale lo fa comunque — e il giorno che supera
la soglia la voce dice quale decisione si sblocca e perche'. Seconda riga: $20k,
dove si riapre «100% Deribit fino a $20k». Una riga si TOGLIE quando la decisione
e' presa. 5 test, incluso «equity non leggibile non e' una soglia superata» (P5).

GATE (A) RITIRATO come pass/fail, congelando il MOTIVO e non l'esito — come il
07/08 col confronto fra ranghi, e per la stessa ragione: il criterio decide su un
margine piu' piccolo del rumore che lo scuote. In piu' una guardia sulla CAUSA
(`test_la_fase_di_ribilanciamento_e_ancora_ancorata_alla_POSIZIONE`) che si rompe
il giorno che qualcuno ancorasse la fase al calendario: quel giorno il gate
potrebbe tornare decidibile, ed e' un fatto da guardare, non da ignorare.
Il test sul margine assoluto si e' auto-ritirato: diceva «se scendesse sotto un
centesimo questo criterio smetterebbe di essere una misura», ed e' sceso a 0,0074.

CLAUDE.md: §3 nuova riga · §5.2 RISOLTO (trasporto allarmi) · §5.4 riscritto (la
domanda fiscale (a) ha una risposta alla fonte: derivati in c-quater al 26%, non
c-sexies al 33% — Circolare AdE 30/E del 27/10/2023, citata verbatim) · §5.13
nuovo debito, la fase che ruota — quantificata e dichiarata INNOCUA oggi (D5):
0,029 di Sharpe a livello di portafoglio, dentro la banda [1,81-2,12].

Diario: docs/diary/2026-08-28-gtaa-fase-e-allarmi.md
Suite: 789 passati, 0 falliti.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 12:54:08 +00:00
Adriano Dal Pastro 21fe289383 research(gtaa): cosa cambia togliendo GTAA01 — +0.11 di Sharpe a iso-rischio, sul filo
Misura chiesta prima di decidere del gate (A): se togliere lo sleeve non
cambiasse niente, la domanda sul gate sarebbe accademica. Portafoglio di
RICERCA a 5 sleeve (33/15/12/20/20), NON il book live (dove GTAA01 non c'e').

Due lenti, ed e' la seconda che decide (M6: un diversificatore a basso CAGR si
giudica a iso-rischio, mai a iso-nozionale; M5: "meno drawdown" si testa a
iso-rischio o si sta comprando de-levering):
  · iso-nozionale: CON Sh 2.28 CAGR +19.2% DD 6.1% vol 7.8%
                   SENZA Sh 2.16 CAGR +23.8% DD 7.8% vol 10.1%
    -> togliendolo si guadagna DRIFT e si compra VOLATILITA'.
  · iso-rischio (×0.77): SENZA Sh 2.16 CAGR +18.0% DD 6.0%
    -> Δ Sharpe +0.121, Δ maxDD +0.02pp.
Hold-out 2025+: Δ +0.247. Per anno: GTAA01 aiuta in 6/8. Correlazione col resto
del portafoglio +0.087 — e' davvero altro. Standalone Sh 1.06, CAGR +5.8%.

⚠️ E LA BANDA DI FASE, che e' la ragione per cui questo numero va citato con la
sua incertezza: il Δ sulle 5 fasi va da +0.095 a +0.124 e supera la soglia
dichiarata (0.12) in 2 fasi su 5. Il SEGNO e' stabile — GTAA01 aiuta in ogni
fase — ma il verdetto BINARIO dipende dalla notte in cui lo si legge. Sanity:
la fase 0 riproduce lo sleeve di produzione bit-exact (max|Δ| = 0.00e+00).

Lettura: il contributo e' reale e sempre positivo, e vale ~+0.11 di Sharpe, cioe'
ESATTAMENTE quanto lo spread fra le tre baseline che il progetto gia' si porta
dietro (0.12, §2). Non e' "GTAA01 e' inutile": e' "sta al limite di cio' che
questi dati risolvono".

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 12:34:44 +00:00
Adriano Dal Pastro 801bd13f10 allarmi: il marcatore "gia' detto" si scrive DOPO l'invio, non prima
Debito §5.2 chiuso su decisione dell'operatore. `run_once` salvava lo stato coi
marcatori `alerted` gia' a True e l'invio lo faceva il chiamante DOPO: col 6,9%
di invii falliti misurato (2 su 29), un 🚨 perso restava perso per l'EPISODIO
INTERO — l'ora dopo lo stato diceva "gia' detto" e usciva WATCH/MUTO. Gli
episodi storici durano 200-2.324 ore, quindi il buco non era teorico.

- `run_once(state_path, sender=None)`: il sender e' INIETTATO, non importato —
  e' cio' che tiene la funzione testabile senza rete d'uscita, che era la
  ragione del disegno precedente. Senza sender il comportamento resta quello di
  prima e il report lo DICE (`invio`), invece di lasciar credere che qualcosa
  sia partito.
- Su invio fallito si disfano SOLO i marcatori "gia' detto", non le misure:
  · asset in ALERT -> alerted=False, l'ora dopo ri-allerta;
  · lock MAINT/ALERT -> alerted_soft/hard=False ma le ORE restano a correre,
    cosi' una manutenzione che sfora la grazia sale ad ALERT anche col trasporto
    giu' (disfare anche le ore congelerebbe l'escalation proprio mentre non si
    riesce a parlare);
  · lock RIENTRATO -> si ripristina l'intero LockState, perche' il rientro si
    annuncia una volta sola e senza le ore non ci sarebbe piu' niente da dire.
- `notify(..., tentativi=)`: il retry esisteva in `send` e non arrivava qui.
  venue_watch ora manda con 3 tentativi.
- L'esito dell'invio finisce nel log del cron invece di sparire.

5 test nuovi. Il primo e' quello che conta — dopo un invio fallito, l'ora dopo
ri-allerta — col suo controllo positivo (un invio riuscito consuma l'allarme
UNA volta sola), senza il quale "ri-allerta sempre" passerebbe.

Suite: 782 passati, 2 falliti (i due del gate GTAA, non toccati qui).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 12:34:44 +00:00
Adriano Dal Pastro c21a0d4058 research(gtaa): criterio (C) — la mediana delle 5 fasi regge come strumento, e sceglie il 60%
Analisi richiesta prima di decidere che fare del gate (A). Il criterio: a cadenza
di produzione, la banda si sceglie sulla MEDIANA delle 5 fasi di ribilanciamento
invece che sulla fase capitata (M7: su ancore appaiate la statistica e' la
mediana). Toglie la componente di FASE; resta quella di DATO.

⚠️ DICHIARATO IN TESTA ALLO SCRIPT: (C) e' stato scelto DOPO aver visto la
tabella delle fasi di r0828_gtaa_band_phase. Sceglierne uno nuovo guardando
l'esito del vecchio e' selezione. Quindi (C) misura lo STRUMENTO — risoluzione
e potenza — e NON valida la proposta del 27/07. Pavimento tenuto a 0.01, quello
che il test si diede il 07/08: il metro non si ritocca sul risultato.

ESITO, coi tre criteri calcolati a runtime:
  (i)   scelta stabile su 10 notti : SI — ['60%'] in tutte e dieci
  (ii)  margine sempre >= 0.01     : SI — minimo 0.0197 (fase singola: 0.0026,
        e sotto il pavimento in 4 notti su 10)
  (iii) potenza (in-sample ≠ hold-out) : SI — al buio 60%, sull'hold-out 40%
Lo strumento funziona: l'escursione dello Sharpe in-sample su 10 notti cala del
74-99% per ogni banda (60%: da 0.1120 a 0.0006).

MA LA CELLA CHE SCEGLIE NON E' LA PROPOSTA. Al buio esce il **60%**; il 25%
vince **0 notti su 10**. Da tenere accanto: sull'hold-out il 60% e' penultimo
(0.7430 contro 0.9315 del 40%), coerente con lo Spearman IS/OOS ~0 misurato il
07/08 — la scelta in-sample non predice, e non va letta come "la banda giusta".

CONTORNO che vale piu' del verdetto: le 5 serie di fase correlano **0.988**,
quindi N_eff = 1.01. La mediana di 5 fasi e' UNA osservazione: toglie
l'artefatto, non compra precisione. Va citata come robustezza alla fase, mai
come campione (§2: «positivo in N/N ancore NON e' N osservazioni»).

Nessuna decisione presa qui: il gate (A) non e' toccato e i due test restano
rossi in attesa della scelta dell'operatore.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 08:51:43 +00:00
Adriano Dal Pastro 31f82e1730 research(gtaa): il gate (A) della banda e' una moneta — la finestra "congelata" rotola ogni notte
Il 28/08 falliscono `test_la_banda_proposta_e_quella_scelta_al_buio` e
`test_il_margine_del_blind_non_e_un_arrotondamento`, a codice fermo dal 07/08
(nessun commit su src/portfolio/gtaa.py ne' su r0727_gtaa_band_gate.py). Al buio
esce il 60% invece del 25%, con margine 0.0074 — sotto il pavimento di 0.01 che
il test si era dato. Questo script chiede, per la terza volta sullo stesso
parametro, se il criterio misura cio' che dichiara. Replica bit-exact della
produzione verificata a fase 0 / taglio 0 (max|Δ| = 0.00e+00 su 7.544 barre).

(0) LA FINESTRA IN-SAMPLE NON E' FERMA. IB serve una finestra ROTOLANTE di 30
    anni. SPY e' l'unica gamba al muro (30.0 anni), e nel cron log la sua data
    d'inizio avanza di un giorno di borsa ogni notte: 1996-07-02 il 24/06,
    1996-09-04 oggi. Il pre-2015, che tutto il progetto tratta come finestra
    congelata, perde il giorno piu' vecchio ogni notte. QQQ e IWM arriveranno
    allo stesso muro fra 2,5 e 3,7 anni.

(1) L'AMPLIFICATORE E' LA FASE. `_gated_returns` ribilancia su `i % every == 0`,
    indice di POSIZIONE nell'array: se la prima barra scivola, si ri-fasa ogni
    decisione di trent'anni. Il progetto sapeva che la fase conta
    (`r0726_loo_deluck.gtaa01_at(ph)`, 5 ancore) ma la assumeva fissa alla
    canonica 0. Non lo e': la fase canonica cambia da sola ogni notte.

MISURE. Sulla finestra CHIUSA pre-2015, che non puo' acquisire dati nuovi, lo
Sharpe si e' mosso fino a 0.0760 fra il 07/08 e oggi. Su 10 notti consecutive
la banda scelta al buio e' 25% / 40% / 60% — la proposta vince il 40% delle
notti — e il margine sta sotto il pavimento in 4 notti su 10 (minimo 0.0026).
A dato FISSO, muovendo la sola fase, il verdetto cambia lo stesso (25% su 3
fasi, 60% su 2): l'imputato e' la fase, non le barre perse.

VERDETTO calcolato a runtime coi criteri dichiarati in testa (M13): il gate (A)
NON ha risoluzione. Il verdetto non e' una proprieta' della banda, e' una
proprieta' della notte in cui lo si legge. La banda al 25% non e' ne' confermata
ne' smentita: non e' decidibile cosi'.

Lo script misura e basta. Ritirare il criterio, come si fece il 07/08 col
confronto fra ranghi, e' una decisione dell'operatore e non e' presa qui.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 08:44:25 +00:00
Adriano Dal Pastro cb40ab3e20 journal: recuperata l'analisi del 27/08, saltata dal guasto di autenticazione
Rigenerata con `analista.py --giorno 2026-08-27 --no-telegram`. Le sezioni
misurate escono IDENTICHE (ricostruzione deterministica da trades.db e dal
feed): cambiano solo l'ora di scrittura in testata e la sezione `Analisi`,
che ora c'e'. Controllo sui numeri: ok.

`--no-telegram` di proposito: la notifica delle 00:37:02Z era partita e diceva
«analisi non disponibile (errore)». Quel record e' la prova che l'allarme del
guasto e' uscito, e riscriverlo con un invio di oggi la cancellerebbe.

L'analisi legge lo storico com'e' OGGI, non com'era stanotte: la testata porta
l'ora vera di scrittura (08:29:00Z), quindi la pagina non si spaccia per una
scritta a ridosso del giorno chiuso.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 08:32:41 +00:00
Adriano Dal Pastro 05a698a83e analista: il motivo di un guasto si prende da stdout E da stderr, o si perde
Il 2026-08-28 alle 00:37:00Z la CLI `claude` e' uscita 1 scrivendo
«Failed to authenticate: OAuth session expired and could not be refreshed»
su STDOUT, con stderr VUOTO. `interroga()` componeva il motivo dal solo
stderr, quindi nel DB e' finito `analisi_stato='errore'`,
`analisi_motivi='uscita 1: '` — e su Telegram e' partito
«analisi non disponibile (errore): uscita 1:».

La meccanica ha retto (nessuna analisi di ieri spacciata per quella di oggi,
esito registrato, notifica partita): a mancare era solo il PERCHE'. P4 —
un'allerta risponde a due domande, e con la prima sola la causa si ricostruisce
aprendo a mano il transcript della sessione headless. P3 — quando la diagnosi
serve, il guasto e' gia' rientrato: il motivo si cattura li' o mai.

- `motivo_uscita(returncode, stdout, stderr)`: unisce i due canali (stderr per
  primo), tronca a 300 caratteri.
- Silenzio totale su entrambi i canali -> lo DICE, invece di lasciare i due
  punti a vuoto: «la CLI non ha detto perche'» e «il perche' l'abbiamo perso
  noi» sono guasti diversi e finora si scrivevano uguali.
- 4 test nuovi, fra cui la regressione col messaggio testuale del 28/08.

NON risolve la causa a monte: perche' quella refresh sia fallita non sta in
nessun log locale. Il refresh token era valido (rinnovo automatico riuscito
alle 08:03:35Z dello stesso giorno, scadenza 2026-09-25) e la stessa chiamata
rifatta a mano esce 0 -> guasto transitorio, unico su 24 sessioni locali.
Da qui in avanti, se ricapita, il motivo si legge dalla notifica.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 08:32:41 +00:00
Adriano Dal Pastro a6b5756cc0 journal: voci automatiche del 26-27/08 — rischio tutto su TP01, SKH01 flat
Due voci scritte dal cron delle 00:37Z (27/08 e 28/08). Numeri come registrati,
nessuna riscrittura a mano.

- 26/08: equity $2.065,45, giorno $+8,86, 4 fill / 2 round-trip, 24/24 giri.
  L'analisi dell'agente segnala il denominatore cambiato il 25/08 (conversione
  USDE): stessa esposizione ($582 lordi), leva 0,28x non confrontabile coi
  giorni precedenti.
- 27/08: equity $2.070,23, giorno $+4,78, 1 fill / 1 round-trip, 24/24 giri.
  Manca la sezione "Analisi (agente)" — il passo dell'analista nel cron e'
  a `|| true`, quindi un suo fallimento non lascia traccia nella voce.

Cumulato dall'arming $+1.472,17 di equity, di cui $+1.399,39 versati:
trading **$+72,78** su 65 giorni e 23 round-trip — taglia a cui il P&L non
distingue l'edge dalla fortuna, e con l'82% del cumulato negli ultimi 7 giorni
(la settimana in cui BTC ha fatto +9,94% e il libro era lungo su entrambe le
gambe).

SKH01 flat su BTC e ETH in entrambe le voci: l'esposizione e' interamente TP01.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-28 08:19:09 +00:00
Adriano Dal Pastro e5052a690f usde: da patch d'emergenza a struttura — config, modulo unico, sorveglianza
- config/live.json sezione `usde` (unica autorita', P1): indice, haircut 10%,
  tetto allerta quota 50%, soglie depeg 0.99/0.95 coi criteri dichiarati (P6)
- src/live/usde.py: config + catena di prezzo (indice pubblico -> ticker ->
  1.0 dichiarato) + valutazione PURA; shadow._collaterale_usde ora deriva da qui
- scripts/live/usde_watch.py + cron_usde.sh (12:35 UTC, dopo la finestra reward):
  reward per delta netto trade (P12: senza inventare attribuzioni), depeg
  (crit ripetuto, resto a transizione, P9), quota anche per deriva passiva (N4);
  applica il verdetto di eligibilita' pre-registrato (>=1 reward entro 29/08)
- serie data/live/usde_watch.jsonl sotto monitor_health (max 30h, P5: un watch
  fermo non deve leggersi come "va tutto bene"); baseline 14:17Z registrata
- GATE USDE-01 in CLAUDE.md §4; test 775 (+17 in tests/test_usde_watch.py)

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 15:11:44 +00:00
Adriano Dal Pastro 631e854b29 live: l'equity del book e' il TOTALE cross-collateral — USDE valutato all'indice pubblico
Trovato eseguendo il test di eligibilita' USDE ($500 convertiti alle 13:04Z,
fill 1.0003 fee 0): shadow._equity leggeva solo il conto USDC -> il giro
successivo avrebbe visto -24,3%, mandato un falso "USCITA DI FONDI" e venduto
~$140 di posizioni. Riparato prima del giro delle 13:47: _collaterale_usde()
valuta l'USDE all'indice pubblico usde_usdc (mediana multi-exchange, lezione
Binance 10/10/2025), depeg passa nel sizing, clamp a 1.0 sopra la pari,
fallback 1.0 dichiarato (mai 0: il fallback si sceglie sul danno, P5).
6 test nuovi in tests/test_shadow_usde.py.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 13:07:29 +00:00
Adriano Dal Pastro 562e95338b ricerca: USDE come collaterale a rendimento — analisi da candidato + test di eligibilita' pre-registrato
Verificato sul venue: apr 4.0 (netto fee), spot USDE_USDC spread ~3bps fee zero,
haircut 10% (non morde al nostro profilo di leva), indice usde_usd multi-exchange
con mediana+clamp (la differenza strutturale dal caso Binance 10/10/2025).
Rischi dichiarati R1-R4, p non stimabile -> la leva di controllo e' la QUOTA (N4).
Aritmetica: a $5k/quota 50% ~$101/anno; -100% = 25 anni di resa, non si recupera.
Pre-registrato il test di eligibilita' (~$500, 3 giorni, regola dichiarata prima).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 11:44:58 +00:00
Adriano Dal Pastro c4c82a8fbd diario: USDC rewards — verdetto: Italia esclusa per MiCA, pista chiusa + episodio scam in chat
Coinbase (chi paga i reward del programma Deribit) ha cessato i reward USDC
nell'EEA dal 2024-12-01 per il divieto MiCA di remunerare gli EMT; l'espansione
Deribit del 2026-08-01 aggiunge 80 paesi, nessuno EEA. Nessun ticket necessario.
Registrato l'episodio dei finti agenti in chat ("Yes, Italy is supported" =
falso) con la regola permanente sul canale di supporto.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 11:37:30 +00:00
Adriano Dal Pastro e7a5fee2fd diario: USDC Rewards Deribit — prodotto verificato sul venue (apr 3.4), il conto NON li riceve
Verifica empirica sulla serie equity oraria: nelle finestre di pagamento
(1-14 lug, 1-14 ago) il libro era flat e nessun accredito da ~$0,65-2,00
compare (0-1 salti >=$0,40, tutti spiegati dai fill). Resta il ticket al
supporto sull'idoneita' dell'Italia. Vale ~$170/anno a $5k.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 11:15:47 +00:00
Adriano Dal Pastro 3034bfdc58 gate XSR01: riscrittura DICHIARATA (opzione A dell'operatore) + haircut con script
Decisione operatore 26/08, a 58 giorni dall'esito, in direzione che stringe:
(1) capitale deploy $5k -> $20k — riconcilia il gate (25/07) con la decisione
vincolante "100% Deribit fino a $20k" (26/07), posteriore, che governa (M28);
deploy XSR01 e scelta del venue ora coincidono in un punto solo.
(2) gamba haircut: numero decisivo da r0826_xsr_haircut.py (N11) a pavimento
$10 (il vero, HL-EXEC), citato con la frazione di ordini eseguiti (P7).
Misurato: FULL 968 barre floor $10 -> haircut -1,1% con 22% di eseguiti (la
guardia da sola era vacua: un libro fermo ha haircut piccolo); ticket mediano
$3,34/gamba, 84% sotto $10 — sostituisce il "$14,41" senza script.
(3) contesto 1.82 -> 1.79 (lente dei gate). Soglie numeriche INVARIATE.

Chiude il debito S5.3. Diario 2026-08-26-xsr01-gate-riscritto.md.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 11:04:57 +00:00
Adriano Dal Pastro d597fc64e8 monitor: advance() consuma solo barre CHIUSE — serie rigenerate, guardia PREMATURO, 4 debiti chiusi
S5.1 RIPARATO E RIGENERATO. Filtro condiviso src/live/paper_guard.py (barra
open-labeled chiusa = ts + cadenza <= adesso) importato da tutti e 6 i monitor;
serie rigenerate dallo stesso start_ts con scripts/live/paper_regen.py (evidenza
in *.pre_regen_20260826.*): statarb +1,95 -> -1,61 (il ribaltamento del gate
27/09 previsto dall'audit), dvolspread -14,73 -> -4,41, xsr -4,98 -> -2,72,
prevday invariato. Nessuna data di gate si sposta. Guardia cablata in
monitor_health: stato PREMATURO (ultima barra che chiude dopo l'mtime, grazia
5 min, open_labeled=False per collect_chain) — sul dato vivo segnala i 5 rotti
e tace sui 2 sani; dopo la rigenerazione 7/7 OK. paper_portfolio non rigenerato
(GTAA su ADJUSTED_LAST: replay != serie registrata, P12), tolta la coda non
chiusa. D6 pagata di nuovo nel fix: asi8 in pandas 3 e' in us, non ns —
blindata con test su tre risoluzioni.

S5.12 ESTESO: conftest devia anche trades.db (wrapper su connect: il default
e' catturato alla definizione) e docs/journal/; book_executions.jsonl
sorvegliato con impronta inizio/fine suite.

S5.5 FATTO: test_leva_massima cancellato con nota (misurava frac*n_asset:
con una chiave di scala avrebbe continuato a passare smettendo di controllare).

S5.9 INDAGATO E RIPARATO (r0826_skh_band_drift): il dato regge (taglio 02/07
riproduce l'audit 1,6376, in-sample identico su ogni taglio); la deriva era la
finestra hold-out — e la sola settimana 15-22/08 vale +0,35 di Sharpe hold-out.
Il test ora taglia il feed al 02/07 e verifica la riproduzione stretta.

Suite: 751 passati, 0 falliti.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 10:12:23 +00:00
Adriano Dal Pastro a51844875b journal: i versamenti non sono piu' P&L — movimenti di capitale scorporati dal trading
Il P&L di giornale era un delta di equity: la voce del 25/08 dichiarava +$1.414,57
di "giorno" quando $1.399,39 erano il deposito USDC, e il cumulato dall'arming
avrebbe mentito per sempre. Nuova `movimenti_capitale()`:
- soglia IMPORTATA da book.EQUITY_JUMP_ALERT, non ridichiarata (P1);
- "movimento" solo se il salto supera di >2x il massimo che il mercato MISURATO
  (feed certificato, tetto di leva da config) poteva produrre fra le due letture;
- altrimenti AMBIGUO: dichiarato con attenzione e NON scorporato (P12 -- un crash
  vero a tutta leva non deve diventare "prelievo"); idem a feed illeggibile (P5).
Scansione dell'intera storia: 1 evento, esattamente il deposito (+209,6% contro
mercato max 0,22%), zero falsi positivi. `concentrazione` ora lavora sul cumulato
di TRADING; le regole sui movimenti stanno sopra l'early-return "nessun giro".
Limite dichiarato (D5): un movimento sotto il 10% dell'equity resta nel P&L.
7 prove nuove (31 -> 37), incluso il controllo M15 al contrario. Voce del 25/08
rigenerata: giorno -> trading +$15,18; cumulato -> trading +$59,14.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 07:35:15 +00:00
Adriano Dal Pastro f10d847816 ricerca: XSR01 sotto la lente RENDITA (filone 70) + cosa compra un versamento da $3k
XSR-RENDITA (r0825_xsr_rendita.py): prima valutazione di XSR01 sul criterio della
perpetua. A iso-nozionale alza il muro; a iso-rischio lo abbassa del 20,6% MA il null
mostra che il meccanismo vale 0,8% (mescolare i rendimenti non cambia nulla) e un
conto remunerato allo stesso tasso lo eguaglia a vol zero senza secondo venue.
A drift zero il muro SALE: si compra un drift scorrelato, non la scorrelazione.
L'haircut non pareggia un conto al 4% nemmeno a zero. Vincolo binding: capitale
($60k per un 25% sopra C*). Corretta in CLAUDE.md la riga Sharpe 1,82 (terza lente;
la lente dei gate da' 1,79 alla scoperta / 1,56-1,63 a oggi).

VERSAMENTO-3K (r0825_versamento_3k.py): $2.065 -> $5.065 appaiato sugli stessi path
del piano = 5,5 mesi di versamenti anticipati; 10a $114.929 -> $122.491 (+6,6%);
$15k in 1,3a e $20k in 1,9a. P(cap >= $5k al gate XSR01 del 23/10): 0% -> 100% --
il lump rende il gate leggibile senza rendere XSR01 comprabile: la decisione sulle
soglie (S5.3) va presa PRIMA che il lump atterri.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 06:56:40 +00:00
Adriano Dal Pastro 4f91b25b72 journal: voce automatica completa del 25/08 (riscritta dal cron delle 00:37Z)
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-26 06:56:40 +00:00
Adriano Dal Pastro ee5c6ed539 ricerca: il piano a 10 anni dal conto vero, l'ETF-quando-flat SCARTATO, slippage rifatto
Giornata partita da "stato trades" e finita sul disegno del sistema. Versamento di
1.400 USDC atterrato alle 11:03:35Z (equity $667,88 -> $2.066,88); il giro delle 11:47
ha ribilanciato correttamente e ha ripiazzato i disaster-SL alla taglia nuova -- prima
volta che il ramo riparato stamattina gira sul serio.

(1) PIANO A 10 ANNI DAL CONTO VERO -- r0825_piano_10a_500.py (nuovo)
Le tabelle pubblicate partono da $600/$635: rifatte su $2.067, lente L3 CONGIUNTA.
Replica superata: chiede EUR 1.718/m dove la tabella da $635 chiedeva EUR 1.733.
EUR 500/mese per 10 anni -> mediana $114.934, rendita 18,35 EUR/g, P(>=50 EUR/g) = 0,0%
su 3.000 traiettorie. Il bersaglio con EUR 500/m arriva al 17o anno.

  L'EQUIVALENZA CHE ORDINA IL PIANO: EUR 100/mese in piu' == +4,07%/anno di drift,
  cioe' +27% su TUTTO il drift del libro. A 10 anni i bonifici fanno il 59%.
  Tutta la leva autorizzabile vale quanto EUR 100-150/mese: k=1,25 (+15,6%) vale MENO
  di EUR 100/mese in piu' (+19,1%), e si porta dietro il peggior giorno al 21,48%.

  E il libro a k=1 rende MENO dell'S&P (15,19% vs 17,40%): il vantaggio sta nello
  Sharpe (1,35 vs 0,89) e senza leva NON si converte in rendimento. Senza leva il libro
  non si giustifica come veicolo di ACCUMULO -- si giustifica come veicolo di RENDITA,
  dove serve 2,5x meno capitale ($254k contro $646k) perche' la perpetua vive sul DD.

(2) "ETF QUANDO IL LIBRO E' FLAT" -- SCARTATO, r0825_capitale_fermo.py (nuovo)
Il libro e' flat il 28,0% dei giorni (2,7% nel 2021, 77,0% nel 2022, 75,6% nel 2026);
live, esposto 14 giorni su 64, leva lorda mediana 0,00x e max 0,52x su un tetto di 1,0x
-- il cap non ha mai morso, il vincolo e' il segnale.
A ISO-RISCHIO il dinamico PERDE: Sharpe 1,01 contro 1,40 del 50/50 e 1,35 del libro. E
il null a maschera casuale (400 estrazioni, stessa quota, blocchi 20g) lo mette al 30o
percentile: fa PEGGIO di commutare a caso.
A iso-nozionale sembrava vincere (drift 17,09%, il piu' alto) perche' aveva la vol piu'
alta: e' la trappola di M6, il de-levering e' il PRIMO test.

  E IL MECCANISMO CHE SEMBRAVA OVVIO NON ESISTE. Aggregato: SPY 4,91% nei giorni flat
  contro 21,48% negli altri (-16,57%), e la storia si scrive da sola. FALSA: scomposta
  per anno il segno ALTERNA (3 su, 4 giu') e il 2022 -- l'anno che doveva reggerla --
  ha il segno OPPOSTO. Artefatto di composizione: i giorni flat stanno negli ANNI brutti
  per l'azionario, non nei GIORNI brutti. M9 ha fatto il suo lavoro su di me.

(3) SLIPPAGE RIFATTO ALLA TAGLIA VERA -- r0822_slip_audit.py riparato
26 fill (erano 18), $6-$319. I due piu' grandi mai eseguiti sono di oggi e hanno preso
1,01% e 0,54% della loro barra 5m, con il print a meta' del range (q=0,50). Il caso
peggiore resta un fill da $74 del 18/07 al 21,9%: un sabato, nastro inesistente.
L'attrito non e' funzione della TAGLIA ma di taglia/volume-della-barra -- l'estrapolazione
lineare che prevedeva ~71% a questo capitale e' refutata dalla misura diretta.
NB non e' "assente", e' "non ancora testato": manca un fill grande in una barra sottile,
e il weekend e' dove TP01 fa il 38% del proprio gross.

  DIFETTO P1 RIPARATO: l'equity era CABLATA a 636.0 con un commento che diceva di
  leggerla dal watermark. Il giorno del versamento avrebbe stampato $636 sbagliando di
  3,3x proprio la sezione che esiste per dire QUANDO la misura scade. Riparata leggendo
  il watermark -- e poi riparata di nuovo, perche' i fill del campione sono stati
  eseguiti a conti diversi ($597-$2.067) e una base sola e' sbagliata comunque la si
  scelga. Ora la normalizzazione e' PER FILL, e a $600 riproduce il 22,0% originale.

DUE ERRORI MIEI, CATTURATI PRIMA DI PUBBLICARLI
- maschera VUOTA vestita da risultato: la prima stesura di r0825_capitale_fermo prendeva
  i giorni flat dalla serie DE-LUCKATA, ma `deluck` sottrae una costante e lo zero esatto
  sparisce -> maschera vuota, dinamico identico al book, e lo script ha stampato tabelle
  piene e un p-value. Lo ha rivelato solo la riga "0 = 0.0%".
  REGOLA: stampare la CARDINALITA' di una maschera prima di usarla.
- il meccanismo falso della (2), demolito dalla scomposizione per anno.

Suite: 730 passati, 1 fallito -- quello gia' noto di 5.9 (deriva dati, non codice).
Watermark del libro live sopravvissuto intatto alla suite (fixture autouse di stamattina).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-25 18:13:15 +00:00
Adriano Dal Pastro 14e1567125 docs: il cap per-asset non ha tetto assoluto — CLAUDE.md dichiarava la formula del fallback
CLAUDE.md 1 descriveva il guardrail live come `min($3.000, equity_osservata x 0.5)`.
Il codice dice altro (src/live/book._cap):

    if trusted:                      # equity reale leggibile
        return float(equity) * float(frac)          # <-- nessun min() con `fixed`
    return min(fixed, wm * float(frac)) ...         # <-- il $3.000 vive SOLO qui

Cioe' `max_notional_per_asset_usd` NON morde mai sul percorso normale: e' il tetto del
ramo di FALLBACK (equity illeggibile), e la riga lo spacciava per quello vivo. Stessa
classe del difetto 5.7 — una descrizione puntata su una configurazione diversa da quella
che gira.

Conseguenza da sapere, emersa da "cosa succede se arrivo a 3.000 USDC": nessun livello
di capitale cambia il profilo di rischio RELATIVO. Il book scala indefinitamente a leva
lorda massima 1,0x (0,40x al segnale corrente), e $3.000 non e' una soglia — il numero
compare in tre posti del progetto e nessuno scatta li':
  - max_notional_per_asset_usd: cap sul nozionale, non soglia di equity, non morde;
  - "la soglia $3k" di 3: decisione CHIUSA il 26/07, si riapre a $20k;
  - C* ~$3.000 del monitor XSR01: difetto noto (5.3), il pavimento vero e' $15-20k.

CODICE NON TOCCATO: il comportamento e' intenzionale e documentato nel docstring di
_cap (la "frontiera" del 03/07 esiste apposta perche' un deposito non resti strozzato).
Era sbagliata la descrizione, non la scelta. Verificato anche che il tetto sul PRODOTTO
del GATE SCALA-01 (n_asset x frac x scala x disaster_sl_pct = 0,30 <= 0,50) non dipende
dall'equity, quindi regge identico a ogni capitale.

Contesto: versamento di 1.400 USDC atterrato alle 11:03:35Z, equity $667,88 -> $2.066,96.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-25 11:07:11 +00:00
Adriano Dal Pastro 426735448e live: diagnosi del guasto venue, disaster-SL scoperto, isolamento per asset, cron :47
Nato da "stato trades" durante una manutenzione Deribit (system_maintenance 11051,
08:57-09:20 UTC). Contati i log invece che ricordarli: 1.499 giri dal 23/06, 3 con
manutenzione, 5 traceback duri — e 4 dei 5 sono il NOSTRO gateway, non il venue.
Le release Deribit escono il martedi' alle 09:00 UTC: il cron al :07 ci cadeva dentro
per costruzione (21/07, 11/08, 18/08, 25/08).

DIAGNOSI (src/live/venue_probe.py, nuovo)
Sonda l'API PUBBLICA Deribit senza gateway e senza credenziali, e classifica il guasto:
VENUE_MANUTENZIONE / VENUE_GIU / GATEWAY / IGNOTO. Prima ogni causa stampava la stessa
riga ("conto non leggibile (offline)") con nota di diagnosi CABLATA — P4 violata, e il
18/08 il codice 11051 era gia' dentro il processo senza arrivare a chi decideva la
gravita'. Parte solo dopo un guasto: sul percorso sano costa zero. P1 rispettata: la
firma 11051 si importa da venue_watch.is_maintenance, non si ridichiara.

P9: la manutenzione dentro lo slot declassa il titolo a info, ma solo su EVIDENZA della
sonda (mai sull'orologio) e solo dentro la durata annunciata — oltre, RIALZA. Un gateway
rotto di martedi' mattina resta al massimo.

DISASTER-SL SCOPERTO (src/live/execution.py)
ensure_disaster_sl cancella i bracket incoerenti PRIMA di ripiazzarne uno: fra le due
chiamate la posizione e' senza stop. Se il ripiazzamento sollevava, l'eccezione risaliva
a main() e il guasto peggiore aveva la faccia di un errore qualunque. Ora: due tentativi,
poi stato `naked`, distinto da `place-failed` (P5). Non e' "non sono riuscito a
proteggere": e' "ho tolto la protezione e non sono riuscito a rimetterla" -> allarme
massimo, mai declassato. La SEQUENZA non e' stata invertita: piazza-poi-cancella sembra
piu' sicuro ma "sembra" non basta con soldi veri senza misurarlo.

ISOLAMENTO PER ASSET (scripts/live/book_execute.py)
Il 21/07 un 502 dentro ensure_disaster_sl su BTC ha ucciso il giro intero: nel log ETH
non compare — ne' ribilanciato ne' verificato nella protezione. Ora un asset che esplode
non ferma il ciclo, e il giro degradato esce con codice 2.

CRON :07 -> :47
Il vincolo vero non era ":07" ma "fuori dai ~26s del minuto tondo" (rate-limit per-IP
auto-saturato dal collettore catena, misura del 30/07). Il :47 lo soddisfa e in piu' sta
fuori dallo slot di release. PREVISIONE DICHIARATA (M12): 3 delle 4 finestre osservate
sono rientrate entro l'ora -> il :47 ne avrebbe scavalcate 3 su 4; se martedi' prossimo
becca comunque la manutenzione, la previsione e' sbagliata.

WATERMARK AVVELENATO DAI TEST (tests/conftest.py, nuovo)
Trovato addosso: lanciando la suite, data/live/equity_seen.json passava a $5.000 e il giro
successivo mandava un allarme Telegram FALSO ("USCITA DI FONDI -86,6%"). Non cosmetico:
cap_fallback = min(cap_config, watermark x frac) sarebbe passato da $334 a $2.500/asset,
~7,5x di leva su un conto da $668, sul ramo eq_fallback che allerta e NON blocca — cioe'
i test potevano armare il pericolo che il watermark esiste per impedire. Riparato con una
fixture AUTOUSE, non per-test: chiedere a ogni autore di ricordarsene ha gia' perso il
26/07 e il 21/08. Resta esposto lo stesso errore su trades.db e book_executions.jsonl.

BLOCCATO, NON RINVIATO
Il fallback diretto ai privati Deribit richiede chiavi API create dall'operatore: in
locale esiste solo CERBERO_TOKEN. Il gateway resta un punto singolo di guasto non
aggirabile (CLAUDE.md 5.11). La sonda dice di chi e' il guasto, non lo aggira.

Test: 20 nuovi, nessuno tocca la rete; controllo positivo fatto (5 su 7 falliscono contro
il codice vecchio). Suite 730 passati, 1 fallito — quello gia' noto di 5.9 (deriva dati).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01B9UyJLHzR7EJzxR3iQ3RN1
2026-08-25 10:27:36 +00:00
Adriano Dal Pastro 2751a7efd0 journal: la voce del giorno IN CORSO non si presenta piu' come una giornata
cron_daily (00:30 UTC) faceva DUE chiamate al giornale: chiudeva IERI (giusto)
e apriva OGGI. La pagina di oggi nasceva con ~30 minuti dentro e nessuno la
aggiornava fino alla notte dopo.

Il difetto non era il dato mancante: era che la pagina non lo diceva dove si
legge. Aveva TUTTE le sezioni di una chiusa -> passava ogni controllo di
completezza e freschezza, e la parzialita' stava solo in §Salute, quinta
sezione su otto. Stessa famiglia di "una barra presente non e' una giornata
presente", in veste nuova: la pagina e' presente, il giorno no.

Taglia misurata sul caso reale di oggi: la pagina congelata alle 00:37 diceva
"giorno: $+0.54 (1 letture)" e la regola [pnl] chiosava "senza operare". Alle
08:54 il libro aveva fatto 3 fill, 2 round-trip e +$25.86 ($642.56 -> $667.88).
Avrebbe raccontato una giornata ferma per tutta una giornata operativa.

Riparato in due pezzi indipendenti:
  1. la pagina dichiara la parzialita' nel TITOLO e nella prima riga —
     "PARZIALE (giorno in corso)", copertura esplicita (N giri su 24), il fatto
     che non si aggiorna da sola, e quali numeri sono di quella frazione;
  2. tolta la seconda chiamata dal cron. In docs/journal/ restano solo giorni
     chiusi; lo stato corrente si prende da journal.py a mano (pagina marcata)
     o da trades.db, che cron_book sincronizza ogni ora.

Scelta dichiarata: NON si rigenera ogni ora. Costerebbe una riga in cron_book
ma riscriverebbe un file tracciato da git 24 volte al giorno per un consumatore
che non esiste (l'analista legge il giorno chiuso). Se un domani servisse, la
strada e' RIGENERARLA, non congelarla: e' scritto nel commento del cron.

Prove (test_journal 28 -> 31): una accende la marcatura, una la tiene spenta su
un giorno chiuso (una marcatura sempre accesa non si legge), una e' guardia sul
SORGENTE di cron_daily.sh — ogni chiamata a journal.py deve avere --giorno
esplicito, perche' senza argomenti scrive OGGI.

Regolare docs/journal/2026-08-25.md rigenerato: ora si dichiara PARZIALE (9/24).

NON riparato, e registrato come debito aperto in CLAUDE.md §5:
test_wave_0726::test_t1_canonical_riproduce_il_backtest_ufficiale fallisce, e
falliva gia' prima di questa modifica (verificato con git stash sull'albero
pulito). Sharpe hold-out SKH01 canonical 1,9223 contro la banda cablata
1.3 < h < 1.9: il codice non e' cambiato, sono cambiati i dati (data/raw e'
gitignored, il cron lo ricostruisce ogni notte). La banda NON e' stata
allargata — lezione 07/08. Suite: 710 passati, 1 fallito.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-25 08:59:42 +00:00
Adriano Dal Pastro 11a2370027 journal: voci automatiche del 23-25/08
Giri notturni del cron. Il 23/08 e' stato rigenerato alle 00:36 del 24 col
giorno COMPLETO (24 giri invece di 20, equity $637.58, cumulato $+39.52):
la voce precedente era stata scritta alle 19:44 a giornata in corso.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-25 08:50:02 +00:00
Adriano Dal Pastro b237ad2e8b docs: compattazione di CLAUDE.md — 3458 -> 424 righe, memoria in docs/memory/
CLAUDE.md era arrivato a 310 KB (~80k token caricati a OGNI sessione) e la
sua funzione si era sdoppiata: era insieme il manuale operativo e l'archivio
di 69 filoni di ricerca. Le due cose hanno lettori diversi.

I 65 bullet-blocco sono stati spostati VERBATIM in docs/memory/ (nulla
riscritto). Verifica meccanica riga per riga prima del commit: 3272 righe
non vuote, 0 mancanti, 0 aggiunte, zero buchi e zero sovrapposizioni nella
copertura delle regioni estratte.

  10-sleeve-e-candidati.md    30 KB  TP01 XS01 VRP01 SKH01 GTAA01 XSR01
  20-ondate-e-scartati.md    126 KB  69 filoni, ogni scartato col suo perche'
  30-piano-capitale-fisco.md  59 KB  muri, versamenti, venue risk, fisco, prop
  40-produzione-e-deploy.md   66 KB  esecutore, tripwire, monitor, PRIIPs/UCITS
  50-dati-e-feed.md           14 KB  difetti del dato, catena opzioni
  60-metodo-e-gate.md          4 KB  i gate di altlib.py

In CLAUDE.md resta solo cio' che serve a non sbagliare una decisione: stato,
book live vs book di ricerca, i numeri da citare e quelli da NON citare,
7 decisioni vincolanti dell'operatore con "cosa le riapre", 6 gate
pre-registrati con la data, 9 debiti aperti non riparati, le regole di
prim'ordine (D/M/C/P/N, distillate dalle 113 righe che contenevano REGOLA),
IL DATO, metodologia, stack/struttura/comandi.

Tre fatti che erano sepolti in 3400 righe e ora stanno in testa: le TRE
baseline diverse che girano sotto il nome "libro 75/25" (spread piu' grande
di quasi tutti gli effetti misurati), il funding non modellato in nessun
backtest (-2,16%/anno), e che «N/N ancore» vale ~2 osservazioni.

Verificato prima del commit: 36/36 percorsi citati esistono su disco,
708 test collezionati, code fence bilanciati. Nessun file di codice toccato.

Convenzione aggiunta (§14) perche' il file non torni a crescere: quando un
risultato CAMBIA UNA DECISIONE si aggiorna CLAUDE.md; quando aggiunge
racconto, va in docs/memory/.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-25 08:50:02 +00:00
Adriano Dal Pastro 214599e0a8 docs: libro di bordo in CLAUDE.md + diario del 23/08
CLAUDE.md: bullet del libro di bordo (il difetto dell'ora dei fill, il DB a
tre fonti incrociate, i quattro livelli della pagina, l'analista e i suoi
limiti, le due riparazioni al notifier), piu' i file nuovi nella Struttura e
i quattro comandi nella sezione Comandi.

Diario `2026-08-23-libro-di-bordo.md`: la storia per esteso, i numeri del
libro live dall'arming (+$37,50 in 64 giorni, ma l'80% delle giornate a
equity invariata e tutto il P&L in sei giorni), i cinque difetti trovati dai
test e il ciclo di retroazione dell'agente.

Le due cose che un lettore futuro deve trovare scritte: che l'analisi in
prosa NON e' parte del registro (una guardia sui numeri non copre il
ragionamento — due errori su due giri con sonnet-5, nessuno con una cifra
nuova), e che il modello e' stato cambiato su un campione di due
osservazioni, quindi e' un tentativo di abbassare un tasso e non una
garanzia.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 19:50:56 +00:00
Adriano Dal Pastro 12dc04c969 analista: modello di default a opus-5
Sonnet-5 ha prodotto due errori di ragionamento in due giri: una frase su un
merge di cui nessuno gli aveva parlato, e un round-trip corretto sulla pagina
dichiarato inesistente, con una spiegazione inventata per il proprio dubbio.
Nessuno dei due contiene una cifra nuova, quindi numeri_non_supportati() non
li vede: e' il buco dichiarato quando la guardia e' stata scritta.

Primo giro con opus-5 sulla stessa giornata: nessuna affermazione inventata,
e le affermazioni numeriche verificate a mano contro il DB tornano tutte
(fill 1 contro 2/5/4/3 dei giorni precedenti, equity ferma a $597.12 dal 13
al 18/08, target BTC 189 -> 115). Resta un'imprecisione di nome: chiama
"target" un valore che nella fonte era la POSIZIONE. Il numero e' della
fonte, la classe di errore e' cambiata.

E ha prodotto una riformulazione che le regole non possono dare: la
concentrazione del P&L in 7 giorni ha una lettura alternativa altrettanto
compatibile — quei sette giorni sono anche gli UNICI in cui il libro e'
stato a mercato, quindi la finestra non separa l'edge dal beta a un rialzo
del 22-29%.

⚠️ Il campione e' di due osservazioni contro una: e' un tentativo di
abbassare un tasso, non una garanzia, ed e' scritto cosi' nel sorgente.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 19:47:11 +00:00
Adriano Dal Pastro 782c0ce4bc analista: manda l'analisi giornaliera su Telegram, con l'esito registrato
La notifica porta una testata coi numeri che si leggono senza aprire nulla
(equity, delta del giorno, cumulato, posizioni, leva, fill e round-trip) e
sotto l'analisi del modello.

Il trasporto Telegram e' pero' il punto singolo di guasto gia' misurato in
questo progetto: un tentativo, nessun retry, esito mai registrato, 6,9% di
invii persi (2/29). Su un messaggio al giorno sono ~25 messaggi persi
all'anno, quindi qui sono state fatte due delle tre riparazioni dichiarate
il 2026-08-23 e mai eseguite:

(a) `send(text, tentativi=1)` — retry OPZIONALE con backoff. Il default resta
    1, cosi' il comportamento e' invariato per tutti i chiamanti esistenti:
    alzarlo per tutti cambierebbe la latenza degli allarmi di venue_watch e
    book_execute su un percorso con soldi veri, e non e' una modifica da fare
    di straforo dentro un'altra funzionalita'. L'analista chiede 3.
(b) `ultimo_errore()` — il motivo si registra nel punto in cui l'eccezione
    veniva ingoiata, e NON sopravvive a un invio riuscito. Regola gia'
    codificata il 29/07 su un altro percorso e mai applicata al notifier.

La terza (marcare `alerted=True` solo a invio riuscito in venue_watch) cambia
il comportamento degli allarmi e resta una decisione dell'operatore.

L'esito finisce nel DB in tre stati: inviata / non configurato / FALLITA col
motivo. Un invio perso che non lascia traccia, il giorno dopo, non si
distingue da "non e' successo niente".

E se l'analisi manca, il messaggio parte lo stesso dicendo PERCHE': senza
quel ramo un guasto del modello si leggerebbe come una giornata senza nulla
da dire. Taglio a 4096 caratteri dichiarato, mai silenzioso; HTML del modello
neutralizzato.

708 test passano. Strategia, pesi, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 19:40:56 +00:00
Adriano Dal Pastro 7456be1ce5 merge: ondata di ricerca 0822 + libro di bordo del book live
114 commit. Due cose diverse dentro lo stesso ramo.

RICERCA (scripts/research/, docs/) — sei ondate, §21-69, 0 candidati promossi.
Il valore e' difensivo e reale: quattro monitor forward rotti che avrebbero
fatto decidere un gate al contrario, un costo gia' in essere mai contato (il
funding dei perpetual, -2,16%/anno di drift), un punto singolo di guasto nel
trasporto degli allarmi, quattro soglie pubblicate falsificate. Il finding di
prim'ordine e' §58: l'obiettivo del progetto ha DUE definizioni operative in
uso che danno 33,9% contro 0,33% sulla stessa domanda.

PRODUZIONE (src/live/, scripts/live/, cron) — il libro di bordo:
- data/live/trades.db, i trade allineati col tempo. Erano salvati ma datati
  alla BARRA DI SEGNALE: 19 righe su 19 a 00:00:00, e un trade registrato sei
  giorni prima di essere eseguito. L'ora vera viveva solo in cron_book.log,
  gitignored e fuori dal backup.
- book_execute.py: ts_utc = ora vera del fill, bar_ts = barra, con test di
  regressione sulla sorgente.
- docs/journal/: una voce al giorno, quattro livelli separati per
  provenienza — numeri misurati, Lettura a regole tracciabili, Analisi di un
  modello, Nota dell'operatore.
- sync orario in cron_book, giornale e analista in cron_daily.

Strategia, pesi e config del libro INVARIATI su tutto il ramo. Nessun ordine.
695 test passano.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 17:48:24 +00:00
Adriano Dal Pastro f5d9409213 analista di bordo: un modello scrive la prosa del giorno, in un campo suo
Aggiunto il quarto livello della pagina, tenuto separato dagli altri tre:
  numeri   -> misurati dal feed e dal DB
  Lettura  -> regole deterministiche, ognuna col suo id
  Analisi  -> questo: prosa di un modello, che puo' sbagliare
  Nota     -> l'operatore

NON scrive dentro `nota`, che era la richiesta letterale: quel campo e'
dell'operatore, ed e' cio' che a rileggere il giornale fra sei mesi permette
di sapere chi ha scritto cosa. L'agente ha `analisi`, marcato col modello,
con l'ora e con l'esito del controllo sui numeri.

Gira via `claude -p` (verificato con env -i che risponda nell'ambiente nudo
di cron), una chiamata al giorno sul giorno CHIUSO, tolte le tool.

Tre guardie, una per ogni modo in cui una prosa generata rovina un registro:
- NUMERO INVENTATO: numeri_non_supportati() estrae ogni cifra dall'analisi e
  verifica che compaia in cio' che il modello ha ricevuto. Oltre tre numeri
  liberi l'analisi e' RIFIUTATA e la pagina resta senza. E' un controllo
  debole per costruzione, e lo dichiara: prende l'invenzione, non il
  ragionamento sbagliato.
- COMMENTO DI SE': senza_analisi() toglie dalla pagina la sezione dell'agente
  prima di dargliela. Al primo giro reale il modello aveva letto la propria
  uscita precedente e prodotto un paragrafo sull'avviso che si era preso il
  giorno prima — un ciclo di retroazione che in poche settimane avrebbe
  riempito il giornale di meta-commento, e che nessun controllo automatico
  puo' distinguere da prosa valida.
- ANALISI DI IERI SPACCIATA PER OGGI: se il modello non risponde, la pagina
  resta VUOTA e il perche' viene registrato (stato + motivo). Il silenzio non
  diventa continuita'.

Corretto anche un falso positivo mio: il tripwire validava sulla sola pagina
mentre il prompt include anche il blocco storico, quindi bocciava un'equity
vera. Una guardia piu' stretta del contratto produce allarmi che si impara a
ignorare.

Ogni guardia ha un test in entrambe le direzioni. 695 test passano.
Strategia, pesi, config INVARIATI. Nessun ordine.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 17:46:29 +00:00
Adriano Dal Pastro 1803e0ac9f giornale: lettura ragionata a regole dichiarate e tracciabili
Non prosa libera: dodici regole, ognuna con un id stampato accanto alla riga
che ha prodotto. Combinano solo numeri gia' presenti nella pagina, tacciono
sul non misurato e non prevedono niente. Il campo `nota` resta l'unico posto
dove puo' finire un giudizio umano.

Le regole: stato del libro e PERCHE' e' flat (componente per componente),
disaccordo fra orizzonti del trend contro esposizione TP01, incoerenza
(trend su ma libro fuori), leva contro il tetto, P&L del giorno, costo che
supera il movimento, concentrazione del cumulato, drawdown dal picco,
implicita contro realizzata col gate IV-rank di VRP01, giornata oltre 2
deviazioni, giri mancanti e feed vecchio, e la taglia del campione.

Ogni regola ha DUE test: uno che la accende e uno che la tiene spenta. Una
regola che si accende sempre non sta leggendo niente, una che non si accende
mai e' indistinguibile da una rotta.

Tre difetti corretti prima di pubblicare, tutti trovati scrivendo i test:
- il tetto di leva era RIDICHIARATO (0.5 cablato) invece che letto da
  config/live.json — quinta occorrenza dello schema che il progetto paga da
  luglio: un sorvegliante che ridichiara il proprio bersaglio continua a
  passare il giorno che il bersaglio cambia. Ora deriva, e se il config non
  si legge lo dice invece di inventare un tetto.
- l'IV-rank era il percentile a UN ANNO etichettato col nome del gate di
  VRP01, che usa un percentile ESPANDENTE. Due statistiche diverse, e oggi
  danno il verdetto OPPOSTO: 0.52 (sopra la soglia, "il sleeve venderebbe")
  contro 0.18 (sotto, sleeve fermo). Il valore giusto combacia con quanto
  gia' misurato il 30/07: 0/8 settimane passano il gate.
- la concentrazione si accendeva su $2,08 di cumulato: vera e inutile. Ora
  ha una soglia di rilevanza, o e' una riga che insegna a saltare la sezione.

62 voci rigenerate. Strategia, pesi, config INVARIATI. 675 test passano.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 13:36:05 +00:00
Adriano Dal Pastro 10c373075c libro di bordo: DB dei trade allineato col tempo + giornale giornaliero
I trade erano salvati, ma non allineati col tempo: book_execute.py scriveva
ts_utc = pd.Timestamp(r['last_data']), cioe' la data della BARRA DI SEGNALE.
19 righe su 19 a 00:00:00, e un trade (ETH 0.04 @ 1869.74) registrato SEI
GIORNI prima di essere eseguito — fill vero 2026-07-14T14:00, scritto 08/07.
L'ora vera esisteva solo in logs/cron_book.log, che e' gitignored, fuori dal
backup e ruotabile: la cronologia reale del libro live viveva in un file che
una rotazione avrebbe cancellato senza che nessuno se ne accorgesse.

- src/live/tradesdb.py: parser del cron log (ora vera + contesto del segnale),
  FIFO con fee pro-quota, riconciliazione a tre fonti, sqlite in data/live/
  (dentro il perimetro del backup). Le tre fonti si INCROCIANO e non si
  sovrascrivono: reconcile() riporta le divergenze e non ripara niente da solo.
  Il venue e' autorevole ma TRONCA (1 trade su BTC, 0 su ETH): dichiarato.
- scripts/live/trades_db.py: --sync (idempotente, in cron_book ogni ora),
  --report, --reconcile.
- src/live/journal.py + scripts/live/journal.py: una voce al giorno in
  docs/journal/YYYY-MM-DD.md — mercato (ritorni, RV30, TSMOM sugli orizzonti
  di produzione, DVOL con eta'), libro (TP01/SKH01, target, posizione, leva),
  P&L (equity del venue come autorita', scomposizione locale), salute.
  NIENTE narrativa automatica: il campo `nota` e' l'unico posto per il testo
  libero ed e' dell'operatore, mai riscritto da un ricalcolo.
- book_execute.py: ts_utc = ora vera del fill, bar_ts = barra. Test di
  regressione sulla sorgente: se qualcuno rimette last_data, il test lo dice.
- 62 voci di giornale ricostruite dall'arming a oggi.

Tre difetti trovati dai test mentre scrivevo, non a occhio: il renderer cadeva
in KeyError se mancava il blocco mercato (un giornale che non si scrive non e'
un giornale); "24 giri attesi" su un giorno IN CORSO produceva un allarme a
ogni esecuzione; e libro e P&L leggevano due istanti diversi, quindi la stessa
pagina mostrava due equity.

Strategia, pesi, config INVARIATI. Nessun ordine. 659 test passano.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 13:13:02 +00:00
Adriano Dal Pastro 0cd0747e95 CLAUDE.md: bullet della sesta ondata (§58-69) + tre correzioni inline
0 candidati su 69 filoni cumulativi. Il finding di prim'ordine e' §58:
l'obiettivo del progetto ha DUE definizioni operative in uso (flusso e
ricchezza sostenibile) che danno 33,9% contro 0,33% sulla stessa domanda, e
per cinque ondate i due corpi di lavoro sono stati confrontati come se
parlassero della stessa cosa.

Tre marcatori inline dove l'ondata contraddice numeri gia' scritti, perche'
questa memoria non deve contraddirsi da sola:
- il vincitore MISTO del 25/07 e' superato da MISTO-A (§60)
- il gate XSR01 del 23/10 legge un monitor tarato sul pavimento del venue
  sbagliato (§67); soglie NON toccate, decisione dell'operatore
- la ragione per raccogliere la catena USDC e' caduta: le due superfici sono
  la stessa superficie a strike appaiati (§64)

Registrata anche la provenienza anomala dei verdetti (riesecuzione degli
script, non messaggi degli agenti) e la previsione verificabile che la 70a
ondata dara' la stessa risposta.

Libro, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 12:51:58 +00:00
Adriano Dal Pastro 8c0b5f97ee registro: chiusi §58-69 — dodici verdetti, 0 candidati, e due appoggi tolti a decisioni gia' prese
I dodici filoni della sesta ondata erano rimasti `_in corso_`: la sessione si e'
chiusa dopo che gli agenti avevano scritto gli script e prima che i verdetti
fossero consolidati, e i loro messaggi finali sono persi. I numeri qui NON
vengono da quei messaggi: vengono dalla riesecuzione dei dodici script
(07:38-08:06 UTC, sequenziale, log in logs/r0823b/ che e' gitignored).
E' il motivo per cui l'ondata non e' andata persa: ogni script calcola il
proprio verdetto a runtime.

Cosa tocca decisioni gia' prese:
- §67 il gate pre-registrato XSR01 del 23/10 legge un monitor tarato sul
  pavimento del venue sbagliato (C* $15-20k, non ~$3k)
- §64 la raccomandazione di §51 (raccogliere la catena USDC) non e'
  giustificata dalla ragione che porta: le due superfici sono la stessa
- §60 la politica MISTO scelta il 25/07 non e' piu' l'ottimo (oggi MISTO-A)
- §63 domanda fiscale NUOVA, diversa da quella aperta il 07/08

Il risultato piu' grande e' di §58: l'obiettivo del progetto ha DUE definizioni
operative in uso che danno 33,9% contro 0,33% sulla stessa domanda, e non era
mai stato detto quale si stesse ottimizzando.

r0823b_quasi_passati.py (§68) terminava con IndexError: Griglia.combo()
indicizzava con self.idx (2720 giorni) un sottoinsieme di 958 righe. Corretto
col parametro idx esplicito piu' un controllo di lunghezza; la
rinormalizzazione e' riga per riga, quindi i valori sono quelli dell'intento
dell'autore. La correzione e' del coordinatore, non dell'autore, ed e'
dichiarata nel registro.

Libro, pesi, cron, config INVARIATI. Nessun ordine.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-23 12:40:30 +00:00
Adriano Dal Pastro cdec81c5bc registro: aperti §58-69 — sei filoni sulla conversione del libro in 50 EUR/g, cinque sullo spazio-strategie non toccato, uno scettico 2026-08-23 04:24:59 +00:00
Adriano Dal Pastro e48de7fcc7 CLAUDE.md: rimando al diario di chiusura 2026-08-23 04:17:25 +00:00
Adriano Dal Pastro 273a43ad6a diario 23/08: ondate 7-8 e critico di chiusura — 17 filoni, 0 candidati, 3 numeri di testa riscritti e 5 errori miei 2026-08-23 04:17:12 +00:00
Adriano Dal Pastro ab4590c326 CLAUDE.md: bullet della quinta ondata (§46-57) — 0 candidati su 57 filoni, PREVDAY girava senza gate, 1,50x bocciato, e la somma di tutti i lead vale +0,036 EUR/giorno 2026-08-23 04:12:06 +00:00
Adriano Dal Pastro 80ca982f64 CLAUDE.md: correzioni del critico — il muro e' una mediana con banda esplosiva, «N/N ancore» vale ~2 osservazioni, il 1,50x e' bocciato, il soffitto ~1,3 e' refutato due volte, i bonifici fanno il 61% non il 73% 2026-08-23 04:10:34 +00:00
Adriano Dal Pastro 00f55fd753 registro §57: il critico di chiusura — repliche 6/6, ma il muro e' una mediana con banda esplosiva e «N/N ancore» vale ~2 osservazioni; somma di tutti i lead = +0,036 EUR/giorno 2026-08-23 04:09:26 +00:00
Adriano Dal Pastro 37c83c11c9 critico di chiusura: il muro $313k e' una mediana con banda [$187k, $1,14M], e «N/N ancore» vale ~2 osservazioni
Ultimo agente dell'ondata 2026-08-22/23. Sola lettura, nessun file di produzione toccato.
Attese a priori dichiarate nel docstring: A1/A4/A5/A6 confermate, A2 e A3 REFUTATE.

REPLICHE (prima di ogni accusa, tutte riuscite):
  - libro 75/25 path live: drift 19,23%/17,07%, Sharpe 1,692/1,513, funding -2,1597%/anno
  - i quattro muri L0/L1/L2/L3 riprodotti al dollaro: $278.033 / $264.373 / $327.617 /
    $313.143, e il muro E' esattamente `prelievo / perpetua`
  - §42 dShFULL(floor=-1) all'ancora 0 = -0,4502 (pubblicato -0,450)
  - TP01 canonico ShFULL 1,305; XS01 fase 0 == sleeve di produzione a max|diff| 0,0
  - funding ri-misurato da implementazione indipendente: TP01 2,138%/anno, rapporto
    condizionale 1,93x (BTC) / 2,58x (ETH) contro il pubblicato 1,86-2,55x

TROVATO:
1. Il muro $313k non ha mai avuto una banda. Propagando SOLO la SE del drift (5,151%/anno,
   block bootstrap; §53 la misura 5,09 su altra lente) va da $204k (+1 SE) a $707k (-1 SE),
   p10-p90 [$187k, $1,14M], e a -2 SE il traguardo NON esiste a nessun capitale. La riga
   «EUR500/mese -> P(20a) 85%» diventa ~0% a -1 SE. L'ondata ha pubblicato la risoluzione
   Monte Carlo del muro (0,7%) e mai quella del suo input, che e' 100x piu' grande.
2. «positivo in N/N ancore/fasi» non e' N osservazioni: N_eff misurato 1,6-2,1 (24 ancore
   TP01, corr 0,63) e 1,2-1,5 (10 fasi XS01, corr 0,79), con controllo positivo 24,5 / 1,00.
   La componente comune NON si cancella nella differenza appaiata (corr 0,59) -> A3 refutata.
   E la banda d'ancora non e' un IC: per la stessa grandezza l'IC95 bootstrap e' 4,3x piu'
   largo e contiene lo zero. I verdetti reggono, la precisione dei numeri no.
3. Tre baseline diverse sotto lo stesso nome «libro 75/25»: 1,68 (hourly, tutti i muri),
   1,80 (canonical, §41/42/49/50/54), 1,63 (mediana d'ancora, §8/25) — spread 0,12 di Sharpe
   e 1,7pp di maxDD, piu' grande di quasi tutti gli effetti misurati.
4. «Soffitto direzionale ~1,15» contro 1,639 (§23) e 1,621 (§54) nella stessa ondata: seconda
   refutazione indipendente dell'argomento aritmetico di §12.
5. «EUR X/mese» versa ogni 30 GIORNI (12,17 versamenti/anno, +0,8-1,4%); e il contatore
   `versato` non si ferma al traguardo -> a 10 anni i bonifici fanno il 61%, non il 73%.
6. MDE: la catena opzioni misurata da me da' 77 giorni di superficie (registro 74-75, ok)
   = MDE 4,3 di Sharpe -> ogni SCARTATO di §4/§5/§7/§11 che poggia su uno Sharpe e' un
   non-risultato su quell'asse. §21 XS01-OOS, pilastro del canale funded, ha effetto +1,12
   contro un MDE di 1,13.
7. Errore mio catturato in sessione: la prima stesura de-luckava una serie gia' de-luckata
   (0,89^2) e stampava un finto +31,5% sul muro; il valore vero della scelta di modello e'
   +4,0%.

RISPOSTA AL MANDATO: no. La somma di TUTTI i lead positivi dell'ondata, se fossero
autorizzati e additivi (non lo sono), vale +0,036 EUR/giorno a $635. EUR250 -> EUR500 al mese
porta P(20a) dal 14% all'85%. Il valore dell'ondata e' difensivo ed e' reale; il mandato
«arrivare ai 50 giornalieri velocemente» ha risposta negativa.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 04:06:28 +00:00
Adriano Dal Pastro 8c57274bac registro §54 addendum: serie PREVDAY intatta 1512/1512 ma MDE 4,72 sulla finestra forward — il gate non puo' appoggiarsi al numero forward (e un mio meccanismo era falso) 2026-08-23 03:36:22 +00:00
Adriano Dal Pastro c97f221c62 registro §55: COSTO-CAPITALE — il costo endogeno non morde, e alla taglia di oggi il costo mancante ha segno negativo 2026-08-23 03:29:41 +00:00
Adriano Dal Pastro 73207f79b9 research(costo-capitale): il costo d'esecuzione e' una funzione del capitale, e il muro non si muove — a $635 il vincolo e' il pavimento min_order, di segno opposto
§55 COSTO-CAPITALE. Tutti i muri pubblicati ($272k/$278k/$313k/$325k, traiettorie,
versamenti) sono calcolati con un costo d'esecuzione COSTANTE, mentre un muro che si
raggiunge accumulando attraversa tutte le taglie. Qui il costo diventa una funzione,
misurata camminando il libro Deribit vero.

[VENUE] 50 istantanee di BTC_USDC-PERPETUAL / ETH_USDC-PERPETUAL in 35 minuti (domenica
notte UTC = la finestra piu' sottile della settimana, quindi conservativa). Mezzo spread
0,0065 / 0,0207 bps = UN TICK; costo sotto ~2 bps fino a $500k per ordine; il libro
visibile finisce a $2,8M (BTC) / $1,2M (ETH).

[CALC] Muro L3 congiunta $313.143 -> $315.080 col costo endogeno (+0,6%, DENTRO la
risoluzione Monte Carlo del muro stesso, punto fisso convergente in una iterazione).
La traiettoria EUR500/mese non si muove (P(20a) 85,1% -> 84,7%). Saturazione a ~$9,5M
per argmax di C x drift(C) e a $10M per il primo 1% di nozionale non eseguibile in un
istante: due definizioni indipendenti nella stessa decade, oltre un ordine di grandezza
sopra il muro. Il gradino di leva sopravvive (k* 12,50x -> 12,25x alla taglia del muro;
morde solo a $5M, dove crolla a 1,75x).

Le due riserve degli scettici sono misurate e non mordono qui: il costo che si annullava
in §52 e' quello dello SPOT (spread 100-500x piu' largo), e la partecipazione del 21,9%
di §53 e' la quota di una barra 5m a volume basso — l'ordine di oggi e' lo 0,13% (BTC) /
0,43% (ETH) della profondita' a 1 bps.

Trovato per strada, ed e' il fatto piu' utile: alla taglia di OGGI il costo che le tabelle
non contengono ha segno NEGATIVO. Il drift a $635 e' 13 bps/anno PIU' BASSO che a $5.000
per il pavimento min_order, ~2x cio' che lo slippage costa fra $313k e $1M.

Repliche 8/8 (TP01/SKH01/libro bit-exact; $272.061 e $258.338 al dollaro; accumula
bit-exact; walk_cost_bps identica a §52) + R9 k* = 12,25x come FD.k_star, e due controlli
POSITIVI obbligatori. Due errori miei catturati e pubblicati: banda p10/p50/p90 che si
incrociava oltre il libro visibile (tre oggetti-curva separati), e un controllo positivo
DEGENERE per costruzione (un costo costante sparisce da un drag differenziale).

Sola lettura, nessun ordine, solo GET pubbliche. Libro, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 03:28:10 +00:00
Adriano Dal Pastro 4a849f3f74 registro §56: XS-AMPIEZZA — la caduta non era ampiezza ma IC, e k=5 non e' invariante di scala 2026-08-23 03:04:32 +00:00
Adriano Dal Pastro bf617b75ff research(xs-ampiezza): NO — la caduta di XS01 su 11 gambe non era ampiezza, e' selettivita' piu' un IC che li' vale zero
L'ampiezza effettiva (participation ratio) scende solo da 9,34 a 7,23 (-23%) mentre lo
Sharpe scende dell'86%: sotto IR = IC*sqrt(ampiezza) la sola ampiezza spiega il 14% del
divario, e NESSUNA delle costruzioni dichiarate la muove (7,13-8,47). Il demeaning — la
mossa che creo' XSR01 — e' un NO-OP ALGEBRICO su XS01, perche' i pesi sommano gia' a zero
per costruzione (max|sum w| = 2,8e-17, serie identiche a 2,2e-16): non e' un risultato
debole, e' un'identita' che vale a ogni universo e per sempre.

Il divario sta altrove, ed e' due cose. (a) SELETTIVITA': k=5 su 11 gambe tiene 10
posizioni su 11 e non seleziona niente; k=5 non e' un parametro invariante di scala, fu
tarato su A=19. Congelando il QUANTILE invece del numero la mediana delle 10 fasi passa
da -0,04 a +0,69 (delta appaiato +0,83, positivo in 10/10 fasi, plateau su k in {1,2,3},
mentre su 19 gambe k non conta) contro +1,15 dell'universo pieno. (b) IC: -0,027 (t -0,88)
sulle 11 contro +0,057 (t +2,29) sulle 19, sotto TUTTI i 40 sottoinsiemi casuali da 11 —
e sui 9 alt maturi presi da soli e' NEGATIVO (-0,065, t -2,07) mentre le 8 mancanti da
sole non ce l'hanno (+0,008). L'informazione vive nel CONTRASTO fra le fasce: XS01 e' in
buona parte una rotazione major-maturi contro alt-recenti, non una selezione dentro una
fascia. §50 lo chiamava "sfortuna di listino" al 9° pctl dello Sharpe: sull'IC il
sottoinsieme di Deribit e' fuori dalla banda, per una ragione strutturale.

E tutto il recupero sta sotto la risoluzione del campione, per quattro strade: MDE
dell'hold-out ~2,3 di Sharpe su 1,64 anni attivi; lo spread di coda che dovrebbe pagarlo
ha t 0,2-0,6 contro 1,91 dell'universo pieno; il null di permutazione a fee zero (p
de-luckato sulle 10 fasi: mediana 0,130, sotto 0,05 solo nel 40%) separa il candidato dal
rumore su 19 gambe e non su 11; il deflated-Sharpe sulle 80 celle dichiarate FALLISCE
(0,158, massimo atteso dal rumore 1,065 contro candidato 0,459).

Due errori catturati su me stesso. (1) La selezione in-sample-only NON e' stabile alla
dichiarazione della griglia: con k in {2,3,4,5} la cella al buio era resid k=2 (HOLD
+1,33), aggiungendo k=1 diventa white k=1 (HOLD -0,53) — con ~1 anno di in-sample
(SE(Sharpe) 1,7) la procedura onesta e' una monetina. (2) La prima misura di
eseguibilita' usava |dW| invece di |d(W*scale)| e dava "100% eseguito": la posizione in
dollari e' W*scale e il vol-target muove il nozionale ogni giorno anche a pesi fermi.
Corretta, riproduce le due popolazioni di §45 per via indipendente (11,9% degli ordini =
62,5% del nozionale). A $635 passa l'83% del nozionale: il muro non e' il capitale.

Venue letto ora: 14/19 quotate (SUI 18/08, APT 21/08 senza NESSUNA quota, AAVE 15/08),
11 da >=1 anno, lotti $0,01-$7,72. Solo 2 delle 11 gambe netterebbero col libro live.

Replica bit-exact contro sleeves._xsec_returns (max|dif| = 0,0); controlli positivi su
tutti e tre i rilevatori (ampiezza su matrici note, IC con un segnale che bara = +1,000,
null di permutazione che separa 19 da 11). Sola lettura, nessun ordine, output
riproducibile a meno del timestamp.

Libro, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 03:02:41 +00:00
Adriano Dal Pastro 8694da31bc registro §54: GATE PREVDAY-01 scritto — la cella che gira non e' quella che la selezione onesta sceglie, e quella onesta butta la gamba short 2026-08-23 02:57:26 +00:00
Adriano Dal Pastro aaddd2c93c research(prevday): §54 GATE PREVDAY-01 scritto — il lead piu' forte gira la cella SBAGLIATA
Chiude un buco di PROCESSO: PREVDAY sta in forward-monitor dal 2026-06-21 senza gate
pre-registrato e senza deflated-Sharpe, mentre XSR01/DVOLSPREAD/STATARB ne hanno uno.

FAMIGLIA DICHIARATA PRIMA E CONTATA AL RIALZO: anchor{1,2,3,5} x k{0..1.00, 7} x
short{T,F} x min_hold{0,24,72} x tf{1h,4h} = 336 celle (le 11 gia' spese in giugno da
prevday_turnover e le >=8 della scoperta sono tutte DENTRO). Screen dichiarato: i 16
agenti dell'onda intraday + le 104 ipotesi del 20/06.

IL RISULTATO PRINCIPALE — la cella scelta AL BUIO (in-sample-only) NON e' quella che
gira: e' 4h LONG-FLAT (short=False), mentre il monitor gira 1h LONG-SHORT, che sta al
rango 186/336 in-sample e FALLISCE il DSR (0.905 contro 0.993 della cella al buio).
La gamba SHORT — l'intera ragione per cui PREVDAY fu promosso a LEAD — e' esattamente
cio' che la selezione onesta non compra. E il rovescio: la cella al buio sta a corr
0.641 da TP01 contro 0.152 della congelata (diversifica di meno).

BANDA D'ANCORA: PREVDAY UN'ANCORA CE L'HA (l'ora del confine-giorno) e §50 l'ha tenuta
FERMA. De-luckata sullo spazio congiunto (TP01 x24 · SKH01 x23 · PREVDAY x24, 300
estrazioni, differenze APPAIATE): dShFULL +0.191 -> +0.100, dShHOLD +0.362 -> +0.246 al
peso 15% — meta'. Il SEGNO regge al 100% delle estrazioni; la TAGLIA no. Replica
indipendente di §50 a candidato fermo: +0.191/+0.362 contro i +0.192/+0.363 pubblicati.
Standalone: canonica al 96o pctl delle 24 ancore (ShFULL 1.236 contro mediana 0.963).

MDE: 63 giorni = 0.17 anni -> SE(Sharpe) 2.41 naive / 4.23 Lo, t 0.85 / 0.48, IC95 largo
16.6 punti. Per distinguere uno Sharpe vero di 1.2 dal nulla all'80% di potenza servono
9.4 anni. Il forward serve a UCCIDERE, non a promuovere. E il "+2,04" pubblicato e' su
lente ORARIA: sulla lente giornaliera del progetto e' +1.56.

DSR: attesa a priori REFUTATA. Non si ribalta col conteggio (11 -> 560 celle costa 0.009);
si ribalterebbe solo con sd(trial) >= 0.363 contro 0.267 misurata. Su famiglia OMOGENEA il
deflated-Sharpe e' cieco sul conteggio ma NON vacuo: la cella mediana della stessa
famiglia fallisce (0.863).

INTEGRITA' (sola lettura provata con md5+mtime): 1512 barre su 1512 ore, 95.6%
ricostruibili bit-a-bit; le 67 divergenti sono 1.06/giorno all'ora del cron = ~32
min/giorno non registrati (contro i 4 min/GIORNO REGISTRATI di paper_statarb, §32).
paper_prevday e' sano, ma non al 100%.

FUNDING (mai in nessun backtest): -1.37%/anno di sleeve. La gamba short NON compensa —
incassa solo 0.26-0.46x l'incondizionato mentre la lunga paga 1.25-1.69x.

weights_tilt_null PASS a ogni peso, ma frac_random_beat_hold = 0.91: "migliora
l'hold-out" e' un claim generico su questo libro.

GATE PREVDAY-01: decisione 2027-06-21, 7 condizioni (DSR>=0.95 sulla famiglia
ri-dichiarata + sensibilita' alla partizione pubblicata; cella al buio == congelata,
altrimenti si ri-congela e il forward RIPARTE DA ZERO; delta di libro appaiato > +0.05
positivo al >=90%; weights_tilt_null; ADDS non-hedge sulla cella al buio;
day_boundary_robust != ARTIFACT-RISK; Sharpe forward > 0, soglia debole di proposito),
veto d'integrita' >=80% di barre ricostruibili, kill a Sharpe < -0.50 su >=180 giorni
attivi. Oggi 8/10 condizioni; le 2 che mancano sono la stessa cosa.

Nessun file di produzione toccato, nessuna proposta di cambio al libro live.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 02:55:39 +00:00
Adriano Dal Pastro 9d23ea2ef0 registro: ondata 8, lotto finale — tre filoni nati da cio' che l'ondata ha appena trovato 2026-08-23 02:23:35 +00:00
Adriano Dal Pastro e428659851 registro §52: SKEPTIC-SPOT — il lead regge a $600 e si annulla a $272k, esattamente al muro che pretendeva di spostare 2026-08-23 02:20:52 +00:00
Adriano Dal Pastro f5ebe689da skeptic(spot): il lead REGGE a $600 e si ANNULLA alla taglia del muro che sposta
§52 SKEPTIC-SPOT — attacco deliberato a §39/§45 (spot al posto del perpetual per
la gamba TP01). Sei attacchi, replica bit-exact prima di ognuno (max|dif| = 0.0 su
tp01_realistic; +2,106% di sleeve e +1,580% di libro protetti da assert).

Esiti: 1 allineamento REGGE · 2 controfattuale INCRINA · 3 tetto 1,0x REGGE ·
4 spread/profondita' INCRINA · 5 haircut REGGE · 6 disaster-SL REGGE.

Il risultato che cambia una conclusione e non una presentazione: il differenziale
di cammino spot-vs-perp e' +0,72 bps a $600 (-0,04%/anno) e +25,66 bps a $272k
(-1,54%/anno = il 97% del lead lordo). Il +1,55% e' misurato a una taglia a cui
l'esecuzione e' gratis e speso dentro un muro da $290k, dove non lo e': il muro
NON si sposta del 10,9% pubblicato.

Trovato invece che la storia dello spot ESISTE (get_tradingview_chart_data serve
BTC_USDC/ETH_USDC dal 2023-04-24, 29.196 barre orarie, 0 gap): §39 la dichiarava
assente. TP01 girato sul prezzo spot VERO contro il perp, 24 ancore appaiate, da'
+0,166%/anno di sleeve con la banda che contiene lo zero (16/24) -> il
controfattuale sul PREZZO e' innocuo. Ma lo strumento non esisteva per il 55,3%
del campione e nel 2023 aveva ~9% di ore senza scambi: il lordo passa da +1,580%
(7,4 anni) a +1,450% (era spot) a +1,180% (era liquida, 2024+).

Attacchi falliti, e vanno detti: il tetto 1,0x non morde (3 giorni su BTC, tutti
nel 2018-11 e in PERDITA: troncare avrebbe fatto guadagnare); nessun haircut <=100%
rende binding il margine (copertura 50,0x replicata al decimo); il disaster-SL tolto
a TP01 vale 0,15%/anno ammortizzato allo scenario operativo.

Tre errori miei, catturati e dichiarati nello script: (a) confrontavo il costo di
SPREAD dello spot con la banda NETTA di §45 — mele contro pere, nel verso che mi
conveniva: like-with-like le due bande si sovrappongono; (b) l'aritmetica del
margine metteva SKH01 a 1,0x su ciascun asset invece che sul proprio sleeve
(25,0x invece di 50,0x: §45 aveva ragione); (c) ammortizzavo su 7,4 anni la coda
di un blackout da 30 giorni preso come argmax, ottenendo 1,97%/anno = il 127% del
lead da un evento mai accaduto.

Squalificato dal proprio controllo positivo: gli stimatori di spread da OHLC
(Roll, Corwin-Schultz) attribuiscono 4-16 bps al perpetual, che e' a un tick ->
numeri cancellati, non riportati.

Correzione a §45: «lo spot non si liquida» e' falso — BTC/ETH hanno
in_cross_collateral_pool: true, quindi sono collaterale liquidabile (non binding).

Numero onesto rivisto: [+1,38%, +1,58%]/anno a $600, -0,11%/anno a $272k.
Sola lettura provata (git status -- src/ config/ scripts/live/ tests/ data/ vuoto),
0 ordini, solo GET pubbliche con pacing e astensione nei minuti :05-:10 e :24-:30.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 02:19:33 +00:00
Adriano Dal Pastro 892ca6e214 CLAUDE.md: il lotto minimo di VRP01 era misurato sugli inverse — sui lineari USDC e' 7,5x piu' piccolo, cade il lotto non la regola 2026-08-23 02:18:08 +00:00
Adriano Dal Pastro ab497cc028 registro §50: BOOK-3RD — nessun terzo sleeve ammissibile, e PREVDAY e' in monitor da giugno senza gate 2026-08-23 02:17:55 +00:00
Adriano Dal Pastro caa7cc4020 research(book-3rd): nessun terzo sleeve ammissibile oggi, e per sette candidati ci sono sette muri diversi — nessuno dei quali e' il capitale
§50 BOOK-3RD. Domanda: con ~$635 su Deribit, qual e' il MIGLIOR terzo sleeve realmente
eseguibile del LIBRO LIVE a 2 sleeve (`deribit_book_sleeves`, TP01 75 / SKH01 25) — e se la
risposta e' "nessuno", a quale capitale cambia? Un solo script, nessun file di produzione
toccato, nessun ordine.

REPLICA DI CONTROLLO PRIMA DI OGNI DELTA: ShFULL 1,813 / ShHOLD 1,437 / maxDD 9,42%
riprodotti al terzo decimale; replica ancorata (h=0, off=0) bit-exact contro lo sleeve di
produzione (max|dif| = 0,0), idem XS01, VRP01 e STATARB (0,746 contro il motore originale).

IL VINCOLO MAI MESSO IN TABELLA — IL NETTING. Letto dal sorgente: `book_net_target` somma i
due sleeve in UN numero per asset e `build_book_order` manda UN ordine, quindi un terzo
sleeve DIREZIONALE su BTC/ETH non paga un min-order proprio (misurato: 163 -> 344 ordini/anno
a $635, ma il turnover sale solo del 14%; e per disuguaglianza triangolare le fee modellate
per-sleeve sono un LIMITE SUPERIORE). Il rovescio: non puo' avere un proprio stop. Un terzo
sleeve su ALTRI strumenti richiede una riga in `_CONTRACT` = codice su un percorso con soldi veri.

LA MISURA (1000 estrazioni congiunte TP01 x24 · SKH01 x23 · candidato, mediana delle
DIFFERENZE APPAIATE, funding dentro, peso 15%):
  PREVDAY    +0,192 ShFULL / +0,363 ShHOLD / +1,31pp drift — eseguibile, netta, ADDS, e SENZA
             gate pre-registrato: e' il piu' forte ed e' il meno disciplinato.
  STATARB    +0,159 / +0,081 / -0,12pp — gate aperto 27/09; NEUTRAL, robust_oos FALSE.
  VRP01      +0,121 / +0,067 / +0,19pp — fermo per REGOLA, non per lotto (sotto).
  XS01(19)   +0,110 / +0,378 / +0,79pp — NON eseguibile: Deribit non quota 5 delle 19 gambe.
  DVOLSPREAD +0,073 / +0,062 / -1,12pp — gate aperto 24/10; il maxDD PEGGIORA sopra il 15%.
  XS01-D(11) -0,024 / -0,128 / -0,73pp — l'unica versione eseguibile oggi PEGGIORA il libro.

DUE FATTI DI VENUE, LETTI DALL'API E NON DALLA MEMORIA:
  (a) il muro del LOTTO di VRP01 era misurato sulla famiglia INVERSE, che un conto USDC non
      puo' marginare: sulla USDC-lineare il lotto ETH e' $242 (non $1.832) e il BTC $772 (non
      $6.210) -> 1 lotto ETH = peso 12% gia' da ~$2.000. Cade il lotto, NON la regola
      "niente short-vol da modello in deploy". 5a occorrenza dello schema `fee_watch`.
  (b) Deribit quota 14 dei 19 major di XS01, ma 3 sono listati fra il 15 e il 21 agosto (APT
      non ha nemmeno una quota). Sulle 11 con >=1 anno di listino il meccanismo collassa, e il
      null dei sottoinsiemi (100 estrazioni da 11 fra le 19) separa le due cause: il
      sottoinsieme MEDIANO fa gia' 0,548 contro 1,265 (62% della caduta = AMPIEZZA, non
      riparabile col capitale) e quello di Deribit sta al 9° percentile (il resto = QUALI
      gambe mancano). Aspettare 2-3 listing non basta.

`weights_tilt_null`: 25/28 PASS — e il numero da leggere non e' quello ma `frac_random_beat_hold`,
che arriva a 0,94: dove vale cosi', "questo candidato migliora l'hold-out" e' un claim GENERICO.
Il gate ha potenza (fallisce su XS01-D a 10/15/20%), ma resta necessario e non sufficiente.

LA SCALA: non esiste una soglia di capitale che ammette un terzo sleeve. Il capitale sposta
solo VRP01 (~$2.000 gamba ETH, ~$6.440 gamba BTC), che e' fermo per una regola. Le due date
che contano sono un GATE (27/09, gratis) e la DECISIONE DI VENUE ($20k), che e' cio' che
riapre XS01 sulle 19 gambe.

ONESTA': attesa a priori dichiarata prima di misurare, esito A1 confermata, A2 meta' giusta,
A3 e A4 REFUTATE, A5 confermata al rovescio. Caveat pubblicato: sono 7 candidati x 4 pesi = 28
configurazioni sullo stesso hold-out, nessuna passata per un deflated-Sharpe DI SCREEN — il
modo giusto di usare la tabella e' scegliere un candidato per una ragione dichiarata PRIMA.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 02:16:18 +00:00
Adriano Dal Pastro f4551090f5 CLAUDE.md: il guadagno in anni del gradino di leva dipende da una convenzione mai dichiarata (muro mobile vs congelato, 1,2 anni di differenza) 2026-08-23 02:07:52 +00:00
Adriano Dal Pastro 8c2fa6e46c registro §53: SKEPTIC-LEVA regge 5/6 — k max 1,40, il 1,50x cade, e nel ramo eq_fallback la scala moltiplica un buco esistente 2026-08-23 02:07:24 +00:00
Adriano Dal Pastro a4c9fca77a registro §47: ANCHOR-ENSEMBLE — su TP01 il drift non puo' cambiare per algebra, il segnale sta su SKH01, e la premessa del 02/07 era sbagliata 2026-08-23 02:06:01 +00:00
Adriano Dal Pastro e7ee0738a3 scettico(leva): il gradino 1,25x REGGE 5 attacchi su 6 — k max difendibile 1,40
Filone §53 SKEPTIC-LEVA. Sei attacchi con soglie dichiarate PRIMA, 10 numeri
pubblicati riprodotti prima di attaccarli. Sola lettura, zero rete, 127 s.

A1 DRIFT   REGGE   — il gradino diventa dannoso solo sotto +1,42%/anno di drift
                     (-2,70 SE, 0,25° pctl bootstrap a blocchi): fuori da IC95
                     [+4,78%] E da IC99 [+2,36%]. Il libro puo' perdere il 90,6%
                     del suo drift e il gradino resta non dannoso; il PEGGIOR
                     triennio mai realizzato (+5,35%) ci sta 3,8x sopra.
A2 SINISTRO REGGE  — Delta g(1,25) > 0 in 5/5 finestre giudicabili (2020-21 tolto
                     compreso). QUALIFICA misurata: nel biennio MOBILE peggiore
                     (dal 2021-10, drift -0,45%) il gradino COSTA -0,31%/anno =
                     -0,62% cumulato. Non falsifica per il criterio (li' perde il
                     LIBRO), ma il numero e' quello. Rapporto guadagno/costo 13:1.
A3 CODA    REGGE   — con Hill xi=0,43 (piu' severo del +0,34 pubblicato) il peggior
                     giorno strutturale a 1,25x e' 17,90% (<50%) e P(dimezzamento
                     10a) 0,100% contro 0,000%. CORREZIONE a §33: la coda muove k*
                     di 4,6 unita', non "1-2" — la conclusione regge (il drift ne
                     muove 6,2) ma il numero pubblicato e' ottimista ~3x.
A4 LENTE   REGGE   — sotto la lente accoppiata il ricarico del maxDD CALA con k
                     (1,2358 -> 1,2297 -> 1,2237): moltiplicativo, verso favorevole.
                     E la frequenza del disaster-SL e' invariante a k PER
                     COSTRUZIONE (innesco sul MARK, test di ri-piazzamento
                     RELATIVO): il numero di §40 va moltiplicato, non rifatto.
A5 INVARIANTE INCRINA — completo sul percorso FIDATO (0 violazioni su 576 combo:
                     il vero e' n_asset*min(WEIGHT*(W_TP01*lev+W_SKH), frac)*scala,
                     quindi l'invariante e' un LIMITE SUPERIORE). Ma nel ramo di
                     FALLBACK il denominatore del rapporto e' il WATERMARK, non
                     l'equity: leva vera fino a 5,00x GIA' a k=1,00 e 6,25x a 1,25.
                     La scala non apre il buco, lo MOLTIPLICA -> la guardia G3
                     della SPEC non e' una raffinatezza ed e' NON OPZIONALE, ma non
                     e' una chiusura. E il fattore 0,30 non e' un tetto di perdita
                     (§40: stop rotolante, passano -60% dall'ingresso).
A6 FUNDING REGGE   — rifatto col funding DENTRO e proporzionale a k (r_k = k*(r-f),
                     lineare per costruzione): il gradino vale +3,49a (muro mobile)
                     / +2,10a (muro congelato) contro +2,98a / +1,82a sulla lente
                     pubblicata. Il funding NON riduce il gradino: lo AUMENTA in
                     anni, perche' peggiora il caso base (17,28a contro 14,81a).
                     Ma il livello peggiora su tutta la colonna: k=1,25 col funding
                     (13,78a) resta peggio di k=1,00 senza (14,81a) -> il gradino
                     non ripaga il funding, lo attenua.

RICONCILIAZIONE: il «+1,8a / +EUR164» pubblicato NON era una discrepanza, era una
CONVENZIONE non dichiarata — e' la lettura a MURO CONGELATO (de-leva al traguardo),
riprodotta a 0,02a (+1,82a). Col muro che si muove con k il gradino vale +2,98a. La
differenza fra le due letture (1,2 anni) e' piu' grande di quasi tutti gli effetti
che questo progetto misura: va dichiarata. Il +EUR164 e' invece +EUR144 misurato
direttamente — la differenza E' l'ipotesi di linearita' dell'interpolazione.

K MASSIMO DIFENDIBILE = 1,40 (morde il peggior giorno strutturale <= 20%, soglia
AGGIUNTA da questo scettico); coi soli vincoli gia' dichiarati dal progetto sarebbe
1,67 (G6, il disaster-SL). Il 1,50x NON sopravvive: sfonda il 20% (21,48%) e sta al
90% del tetto G6. La scaletta SCALA_LADDER a 1,25 resta giusta: e' l'unico gate che
il progetto ha contro un parametro che nessun altro gate vede.

NON PORTATI: banda d'ancora del guadagno in ANNI (23x24 congiunte, fuori budget);
slippage a taglia crescente (la partecipazione 21,9% di una barra 5m diventa 27,4%
SUBITO, non a $5.000: va misurata PRIMA del gradino); costo di margine sopra 1x
(non esiste su perp lineare marginato); coda di venue (vive sul suo asse).

Nessun file di produzione toccato: git diff sui tracciati e' vuoto.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 02:05:22 +00:00
Adriano Dal Pastro 58395a594e research(§47): l'ensemble d'ancora e' ESEGUIBILE a ogni capitale — ma su TP01 vale +0,014 di Sharpe, e il segnale sta su SKH01
VERDETTO: ESEGUIBILE MA INUTILE SU TP01 — nessun cambio al libro.

La domanda mai chiusa: invece di de-luckare il NUMERO, si puo' de-luckare
l'ESECUZIONE (N tranche, N ore, 1/N di size)? Tre risposte:

(i)  batte l'ancora MEDIANA: si', di +0,014 di Sharpe FULL. E l'algebra dice
     che non puo' fare di piu': la posizione dell'ensemble e' la MEDIA delle
     posizioni, il lordo orario e' lineare -> lordo_ens == media dei lordi
     (max|dif| 1.4e-17, verificato). Tutto il guadagno e' vol (-1,1%); il
     drift si muove di +0,013% = solo fee-netting. Cio' che compra davvero
     non e' nella colonna Sharpe: sd(ShFULL) 0,061 -> 0, sd(ShHOLD) 0,112 -> 0.
(ii) batte la CANONICA che gira oggi: NO sull'hold-out (-0,223), SI su FULL
     (+0,024) e IS (+0,071). I due numeri non sono due stime della stessa
     cosa: +0,44 e' un'estrazione gia' avvenuta (98 pctl di 24), +0,21 e' cio'
     che si ottiene senza estrarre. La stima onesta del futuro e' +0,21.
(iii) eseguibile da quale capitale: da TUTTI, gia' a $635.

PREMESSA DEL 02/07 REFUTATA, CONCLUSIONE INTATTA. Il 02/07 boccio' il
tranching perche' "i delta per-ancora (~$1-2) sono sotto il min-order $5".
Ma `book.build_book_order` banda la posizione NETTA e manda UN ordine per
asset per giro: un delta per-ancora non e' mai un ordine. Il tranching non
moltiplica gli ordini per K, e la degenerazione non avviene (retention
0,88-1,06 a $635; a K=24 il path eseguito segue l'ideale MEGLIO che a K=1,
corr 0,9986 vs 0,9954). Cio' che lo boccia e' la taglia dell'effetto, non
l'esecuzione — e la ragione conta, perche' quella vecchia cadrebbe al primo
esecutore che mandasse un ordine per tranche.

FUNDING: canale chiuso per ALGEBRA, non per piccolezza. funding = pos*f e'
lineare in pos -> funding_ens == media esatta (max|dif| = 0). Il rapporto
condizionale 2,25x non si attenua (2,25 -> 2,26 da K=1 a K=24): la
correlazione esposizione-funding vive alla scala del regime, non dell'ora.

DOVE STA IL SEGNALE: SKH01, l'unica ancora a cui il 02/07 non porto' mai
questa domanda. Sulla lente del path che gira, mediana delle 23 fasi ShFULL
0,974 -> ensemble 1,286 (+0,312), maxDD 23,3% -> 16,6%: 20x TP01, perche' i
suoi trade sono DISCRETI (spostare la griglia cambia QUALI trade esistono).
Dentro il libro pesa il 25% e li' non si distingue da zero. 23 e' PRIMO ->
sulla griglia 30m non esiste sotto-ensemble simmetrico.

Contro-intuitivo misurato: tranciando entrambi gli sleeve gli ORDINI salgono
6,5x (197 -> 1283/anno) ma le FEE SCENDONO ($5,76 -> $5,29/anno) — su un
venue a fee proporzionale si paga il nozionale, e mediare 23 fasi trasforma
un +-1,0x che sbatte in una posizione frazionaria. Su un venue a pavimento
fisso il segno si ribalterebbe.

BARRIERA (canale funded): [A7] refutata sulla regola misurabile e con un
meccanismo — il lato binding non e' la barriera (-6%, P(breach) 0-7%) ma il
BERSAGLIO (+10%): meno vol allontana dal traguardo quanto dalla barriera, e
l'ensemble sta al 31 pctl su P(pass). MA la regola che il 22/08 ha misurato
uccidere e' la daily-loss a UN giorno, che close-only non puo' vedere
(cieca, non conservativa). Sul p1 giornaliero — cio' che quella regola legge
— l'ensemble batte il 66% delle configurazioni. Dichiarato come indizio.

COSTO VERO, e non e' negli ordini: 23 ancore su 24 di TP01 richiedono barre
di oggi, cioe' `fresh_5m` — il path che il 26/07 ricade in silenzio sul
certificato e che il 29/07 ha fallito 6 giri su 8. E' l'unica delle tre
obiezioni del 02/07 che sopravvive intatta.

Repliche prima di ogni delta: h=0 == tp01_baseline_daily; guardie di
causalita' su tutte le ancore; `banded()` == `r07.smallcap_net` bit-exact
(0.0e+00, stessi ordini); K=4 == EW di 4 book (2.2e-16 sul daily);
offset 0 == `sleeves._skyhook_returns()` (0.0e+00). I livelli del 02/07 sono
derivati col dato: dichiarato, non nascosto.

Due errori miei catturati e congelati in commento: (a) confrontavo
`turnover_per_year`, che eval_weights ARROTONDA, accanto a una
disuguaglianza stretta -> sembrava violata; (b) i percentili di coda usavano
un solo segno per tre colonne di cui due sono ritorni e una una frequenza ->
stampavo 34 dove il valore vero e' 66, cioe' "peggio della mediana" per un
numero migliore della mediana. E il criterio N_max SATURA (6/6 celle a ogni
capitale): un gate che passa sempre non misura niente, e lo dice il codice.

Book, pesi, ancore, cron, config INVARIATI. Nessuna proposta.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 02:03:55 +00:00
Adriano Dal Pastro 89ab19aed5 CLAUDE.md: rimosso il frammento di riga lasciato dalla correzione precedente 2026-08-23 02:00:43 +00:00
Adriano Dal Pastro c4514fc2c7 CLAUDE.md: il muro delle opzioni valeva per VENDERE — comprare costa il premio, e il muro vero e' il tick da 5 USDC 2026-08-23 02:00:33 +00:00
Adriano Dal Pastro d84471e6f7 registro §46: TAIL-HEDGE REFUTATO — il maxDD sale in 162/162, e comprare un'opzione costa il premio non il nozionale 2026-08-23 01:59:43 +00:00
Adriano Dal Pastro 5700280f65 research(tail-hedge): REFUTATO — la copertura di coda ALZA il maxDD del libro, 0/162 celle
§46. Prima misura del progetto sull'acquisto di put deep-OTM come assicurazione statica
sul libro (TP01 75 / SKH01 25), senza delta-hedge e senza pretendere alpha. Motore prezzi
RIUSATO da VRP01 (_bs_put/_strike_from_delta su DVOL reale). Griglia dichiarata prima:
3 delta x 3 tenori x 3 budget x 2 roll = 54 celle per lente di f (162 in tutto).

VERDETTO: il null del de-levering non arriva nemmeno a essere il gate che decide — la
premessa cade prima. Il maxDD SCENDE in 0/54 celle a OGNI lente di f (compresa f=1.00,
cioe' regalando alla copertura il prezzo di modello): 9,42% -> 9,53-10,37%. Meccanismo:
il bleed del premio cade DENTRO i drawdown, che su questo libro sono lunghi e poco
profondi, mentre il payoff cade su singoli giorni di crollo che NON sono il fondo del
drawdown. Beta del libro al sottostante +0,076 (il 19/05/2021 il mercato ha fatto -21,1%
e il libro -2,0%): la put protegge una perdita gia' ridotta di ~10x dalla strategia
stessa, quindi coprirla costerebbe ~1/beta volte il budget.

ATTESA A PRIORI, riportata anche dove sbagliata: (c) REFUTATA nella forma scritta — 15/20
dei peggiori giorni SONO crolli, e lo short-squeeze che avevo in mente sta fuori finestra;
(b) e (a) confermate, e (b) e' il meccanismo operativo.

f MISURATO OGGI sulle quote vere (420 put con bid E ask, catena USDC): 1,89 / 1,27 / 1,06
a delta -0,05 / -0,10 / -0,15 — piu' mite del 2,23-5,85 del 30/07, e il verdetto non
cambia. Struttura del modello che vale come risultato: f si paga solo sulla parte di
valore che converge a INTRINSECO, quindi un roll anticipato non lo paga (sensitivita' con
f asimmetrico riportata).

ESEGUIBILITA': corregge un muro ereditato. Comprare un'opzione costa il PREMIO, non il
NOZIONALE — i "lotti da migliaia di dollari" del 22/08 sono il collaterale per VENDERE.
Il lotto minimo BTC_USDC (0,01) costa $1,79-7,93; la copertura diventa comprabile a ogni
roll da ~$9,2k (30g, delta -0,05) a ~$38,8k (7g, delta -0,15). Secondo muro, STRUTTURALE:
il tick da 5 USDC — piu' la copertura e' deep-OTM (cioe' economica) piu' il tick domina.

CANALE FUNDED: sull'unica regola binding (max-loss 6% statico) la copertura va nel verso
sbagliato — alza il maxDD e quindi abbassa la leva ammessa (k 0,629 -> 0,594-0,620).

DUE ERRORI MIEI CATTURATI PRIMA DI PUBBLICARE, entrambi dal controllo e non a occhio:
(1) il controllo positivo "payoff gratis" FALLIVA perche' non accreditavo il valore
    dell'asset regalato, mentre il MTM successivo ne addebitava il decadimento -> il free
    lunch costava quanto il premio. Un controllo positivo rotto dichiara guasto l'apparato.
(2) la prova di causalita' dava 1,28e-04 ("DIVERGE"): confrontavo fino al taglio, ma il
    prefisso si ferma un roll prima -> differiva per ASSENZA di un roll, non per
    look-ahead. Finestra corretta: 0,00e+00 esatto.
(3) e un errore di CRITERIO: contavo "vittoria" anche dove il maxDD PEGGIORA, dove il null
    del de-levering e' degenere (k=1) e un Δdrift>0 risponde a una domanda di alpha, non a
    questa. Col criterio corretto le "3/54 vittorie" a f=1 diventano 0/54.

Controlli 3/3 OK (free lunch e f=0,1 riconosciuti, f=10 rifiutato). Causalita' esatta.
Lente wick accoppiata riusata da r0725_prop_coupled, copertura 100% del pannello.
Distorsioni dichiarate: finestra 2021-03+ (il DVOL non esiste prima, quindi marzo 2020 e'
FUORI CAMPIONE); spread misurato sui soli strumenti con bid E ask = pavimento che favorisce
la copertura; 3-5 breach in 5,4 anni non distinguono le varianti.

Libro, pesi, cron, config INVARIATI. Nessun ordine.
2026-08-23 01:57:56 +00:00
Adriano Dal Pastro c7ec178499 registro §49: TP01-TWIN REFUTED — l'ensemble protegge peggio nei 4 anni recenti a 0/24 ancore, e i meccanismi non erano ridondanti 2026-08-23 01:51:01 +00:00
Adriano Dal Pastro af19892c20 CLAUDE.md: il costo della catena USDC era +90% e sono +18% — il 587 non contava il filtro OI che il collettore applica 2026-08-23 01:49:37 +00:00
Adriano Dal Pastro 7d4f0c328e research(§49 TP01-TWIN): un ENSEMBLE di 5 meccanismi di trend NON protegge piu' di TP01 — REFUTED
Domanda: TP01 e' il 75% del libro live e dipende da UNA definizione di trend (TSMOM
30/90/180). Sostituirlo con un ensemble di meccanismi diversi ma tutti long-flat (Donchian,
incrocio EWMA, canale di Keltner, Kaufman/KAMA) migliora la PROTEZIONE — che e' il suo
compito — a pari drift e a pari costo? NON e' la domanda `marginal_vs_tp01` (secondo sleeve):
e' la STESSA quota di libro espressa da piu' meccanismi, quindi `weights_tilt_null` non si
applica (il vettore dei pesi e' identico nei due bracci).

Esito: REFUTED. Libro, pesi, cron, config INVARIATI.

Entrambe le attese a priori, scritte prima di misurare, sono REFUTATE:
 (A1) "correlano 0,85-0,95, l'ensemble e' TP01 con piu' fee" -> 0,795 sui rendimenti e 0,608
      sulle POSIZIONI; KEL/KAU stanno a 0,51-0,53 da TSMOM. Meccanismi genuinamente diversi:
      il filone non si chiude sulla matrice, va misurato fino in fondo.
 (A2) "meno DD sara' de-levering" -> k_isovol 0,990: NON C'E' NIENTE DA DE-LEVERE. Vol
      identica (12,1 vs 12,0%), esposizione media PIU' ALTA (0,152 vs 0,141), tempo a mercato
      70% vs 55%. Il null non e' "superato", e' SENZA POTENZA, e va detto cosi'.

Muore invece sulla DISTRIBUZIONE della protezione (criterio (B) di edge_watch importato dal
sorgente di produzione) e sul costo al libro:
 - per anno x 24 ancore: l'ensemble protegge PEGGIO in 2022, 2024, 2025 e 2026 a 0/24 ancore
   (degradazione UNANIME, non fortuna d'ancora) e meglio in 2019-2021 e 2023. I quattro anni
   in cui perde sono i quattro PIU' RECENTI. Nel 2022 (DD buy&hold 68%, il sinistro maggiore)
   il rapporto passa 0,04 -> 0,13 = 3,2x peggio.
 - 73/192 celle ancora-x-anno a favore dell'ensemble (TSMOM meglio nel 62%); rapporto MEDIO
   0,18 -> 0,21 (peggiora, 0/24 ancore favorevoli).
 - costo sul LIBRO 75/25: Sharpe hold-out delta appaiato -0,127, favorevole 3/24.
 - 0/30 delle 31 composizioni possibili batte TSMOM da solo su protezione E hold-out insieme:
   il compromesso non e' di questo ensemble, e' della famiglia.
 - e il criterio che si voleva migliorare NON E' BINDING: TSMOM ha rapporto peggiore 0,635
   contro la soglia 0,75 in 192 celle su 192.

ERRORE MIO catturato in sessione e riportato nello script: la prima stesura decideva sul CASO
PEGGIORE (max degli 8 rapporti), che migliora 0,56 -> 0,49, e avrebbe stampato "PROMOSSO A
LEAD". Il massimo di 8 numeri non e' una statistica: si era mosso perche' era migliorato UN
anno (il 2023, che deteneva il massimo) mentre 4 su 8 peggioravano. Secondo errore corretto:
il tempo a mercato era calcolato sulla serie 50/50 (non-zero se lo e' UNO dei due asset) e
dava 66,8/79,4% contro i 55,4/70,3% di eval_weights nella stessa pagina.

Onesta' verso l'ensemble: l'ancora canonica h=0 e' la MIGLIORE delle 24 per lo Sharpe hold-out
di TSMOM (100 pctl, replica indipendente della fortuna d'ancora del 02/07 e 26/07), quindi il
divario a h=0 (-0,37) e' gonfiato: il numero da citare e' la mediana appaiata, -0,067.

Fatto trasferibile: mediare meccanismi di trend NON diversifica il rischio di trend. Cinque
segnali guidati dallo stesso prezzo divergono solo ai BORDI del trend — cioe' nei ribassi — e
la media li tiene mezzi-lunghi mentre il singolo e' gia' flat. Piu' meccanismi = ingresso e
uscita piu' morbidi, non piu' assicurazione. Cio' che NON si conclude: che la monocultura sia
sicura — servirebbe un regime in cui il TSMOM fallisce, e in 7,4 anni non c'e'.

Controlli: replica bit-exact vs sleeves._tp01_returns (max|diff| = 0,0); criterio (B) 8/8 su
TP01 come pubblicato e 0/8 su buy&hold; stimatore di correlazione validato su corr(TP01,SKH01)
= +0,095 contro +0,09 pubblicato; il null del de-levering DEVE scattare e scatta su un
de-levering vero (target_vol 10%); causality_ok max_tail_diff 0,0 su 5/5 + ensemble.
DSR di famiglia 0,999 PASS ma dichiarato NON decisivo (famiglia omogenea -> sr0 piccolo per
costruzione); trial contati al rialzo 22 + 31 composizioni = 53.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:49:29 +00:00
Adriano Dal Pastro 4e1dae5c09 registro §51 e §48: cosa raccogliere (2 su 10, e il +90% era +18%) e il quinto lato del DVOL chiuso 2026-08-23 01:48:56 +00:00
Adriano Dal Pastro 9cb3465374 research(volvol): la vol-of-vol e' una variabile NUOVA che guarda INDIETRO — SCARTATA, quinto lato del filone DVOL chiuso
§48 VOLVOL. Il DVOL era stato usato in quattro modi, tutti sul LIVELLO o su una differenza
di livelli (VRP01 gate IV-rank, DVOLSPREAD, TP01xDVOL, DVOL-direzionale). Mai il secondo
momento. Qui si apre e si chiude.

ORTOGONALITA' (il gate, misurato PRIMA di costruire qualsiasi strategia): PASS con margine.
Max |corr| = 0.396 su 6 referenze x 6 celle; contro il LIVELLO del DVOL sta a 0.13-0.21 e
contro l'IV-rank di VRP01 a 0.01-0.24. **La meta' "ridondante" dell'attesa a priori e'
REFUTATA**: e' davvero una quinta variabile, non una quarta riscritta.

LEAD-LAG: e' un termometro, e peggio di quanto l'attesa dicesse. Il picco di
corr(VoV_t, |r|_{t+k}) non e' a lag 0 ma a lag **-5/-10**, con la curva monotona da +0.17
a lag -10 fino a +0.02 a lag +10: non accompagna il movimento, lo INSEGUE. E al netto di
RV_t e DVOL_t la correlazione con la vol futura a 10g e' **NEGATIVA** (-0.069 BTC /
-0.090 ETH). Controllo positivo del rilevatore superato 2/2 nei due versi.

GRIGLIA dichiarata prima e contata al rialzo: 3 finestre x 3 soglie x 4 usi = 36 celle
(27 direzionali + 9 sull'arm VRP). Tenuta piccola di proposito: su 168 trial il massimo
atteso dal puro rumore e' Sharpe 1.572, sopra il soffitto direzionale.
- study_family_honest: cella scelta in-sample-only SIZE w=10 p=0.50, marginal NEUTRAL,
  **DSR 0.448 FAIL** (0.441/0.381/0.228 a N=36/72/168) -> earns_slot_honest=False.
- La spia T1 in chiaro: la cella scelta ha **corr->TP01 0.995 SULL'HOLD-OUT** (0.667 sul
  pieno). E' TP01 con un nome diverso. Per uso: RISKOFF/SIZE ereditano lo Sharpe del trend
  (mediana IS 0.40/0.66), **DIR — l'unico uso in cui la variabile decide da sola — ha
  mediana IS -0.24 e 5 celle su 9 con FULL negativo**.
- Arm VRP01, replica del sleeve **bit-exact 2/2** prima di ogni delta: 5/9 celle battono il
  canonico (moneta), maxDD giu' in **9/9** = de-levering puro, e contro gate CASUALI che
  saltano lo stesso numero di settimane la mediana e' 0.71/0.72 con **0/9 celle al 95° pctl**.
  5° fallimento consecutivo di un gate nuovo su VRP01 dopo i 4 del 03/07.

IL NUMERO CHE CHIUDE, e non e' quello della griglia: il candidato migliore batte TP01 nudo
di **+0.034 di Sharpe su una finestra il cui MDE e' 1.51 — fattore 44**. Su questo dato la
domanda non e' rispondibile in positivo nemmeno in linea di principio. A chiudere sono le
due misure che hanno potenza e non dipendono da nessuna cella scelta: la parziale negativa
e il **controllo NON CAUSALE** (stessa cella con vol-of-vol che sbircia: **-0.292** sotto
TP01) -> non e' che la si stima male, e' che la variabile non contiene l'informazione.

Errori catturati su me stesso: (a) la lettura di §1 era CABLATA e diceva "il legame piu'
forte e' con la vol realizzata" mentre la tabella diceva SPREAD -> ora e' calcolata;
(b) il null del gate casuale estraeva le settimane INDIPENDENTEMENTE per gamba mentre il
gate vero e' guidato da due DVOL correlati -> bracciato coi due estremi, e la differenza
e' risultata immateriale (0.71 vs 0.72, sovrapposizione vera 0.29), ma andava misurata e
non assunta (nel 25/07 lo stesso errore valeva 2-3x); (c) un conteggio off-by-one su DIR.

Eseguibilita' a $635 NON e' il vincolo (haircut -0.002, turnover 4-5/anno): 8ª volta
nell'ondata che muore sull'edge e non sulla taglia del conto. causality_ok OK, oracolo OK.

Book, pesi, cron, config INVARIATI. Nessuna scrittura, nessuna rete, 20s di corsa.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:46:53 +00:00
Adriano Dal Pastro e2aee5730b research(newdata): raccogliere 2 fonti su 10 — il criterio di ricostruibilita' ne uccide 4 da solo
§51 NEWDATA-SCOUT. La scorta di dati e' esaurita (§43), quindi la domanda cambia: non "cosa
abbiamo e non guardiamo" ma "cosa NON abbiamo che vada iniziato OGGI". Ogni riga della colonna
ricostruibilita' e' PROVATA con una GET pubblica + controllo positivo, non dedotta.

VERDETTO: raccogliere la catena opzioni USDC-lineare (+117 chiamate/giro = +18%, non +90%);
il book depth L2 come CAMPAGNA A TERMINE, non come collettore. Tutto il resto: no.

- tape/liquidazioni Deribit: muro di ritenzione misurato fra -24h e -26h (non ricostruibile),
  ma il MDE lo manda al 2032 come segnale -> non raccogliere. E il campo `liquidation` non si e'
  fatto vedere in 1000 trade: non si accende una raccolta su un campo che non si sa se scatta.
- §10 proponeva un collettore di OI perpetual "perche' oggi ripartirebbe da zero": MISURATO,
  non riparte da zero — Bybit serve >=800 giorni di OI perpetual gratis (timestamp verificati
  dentro la finestra chiesta), e la famiglia funding e' chiusa su 4 lati -> testare prima.
- Binance OI/taker/long-short: muro vero a 30 giorni (l'API RIFIUTA, non risponde vuoto), ma MDE
  6 anni + venue USDT -> no.
- funding, DVOL, macro: ricostruibili E famiglie chiuse -> doppia eliminazione.

Correzione a un numero pubblicato: la catena USDC con gli STESSI filtri del collettore vivo
(<=95g, OI>=100) sono 113 strumenti, non ~587; l'origine del 587 resta ignota e lo dico.
Il +117 e' un numero di OGGI e cresce con la liquidita' USDC: va ri-misurato prima di accendere.

Bug catturato in sessione: urlopen solleva su HTTP 400, quindi il RIFIUTO di Binance veniva
ingoiato come guasto di rete e il muro si ribaltava in silenzio in "RICOSTRUIBILE" — stessa
conflazione error/no_quote gia' codificata in collect_chain. Guardia sulle finestre di cron
verificata in entrambi i versi; MDE replica la convenzione §43 (1,40 a -> 1,66).

Sola lettura sul disco, nessun ordine, nessuna chiave. Libro, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:46:16 +00:00
Adriano Dal Pastro fd8d5441af registro: ondata 8, secondo lotto — due scettici adversariali sui due lead che valgono soldi veri 2026-08-23 01:34:15 +00:00
Adriano Dal Pastro 5f6aa90180 registro: ondata 8, primo lotto — sei filoni (assicurazione di coda, ensemble d'ancora, vol-of-vol, ensemble di trend, terzo sleeve, cosa raccogliere) 2026-08-23 01:32:11 +00:00
Adriano Dal Pastro ca1e766069 CLAUDE.md: ondata 23/08 — 0 candidati, la scorta di dati esaurita, il timing dei bonifici refutato e il lead spot ridotto al solo funding 2026-08-23 01:24:20 +00:00
Adriano Dal Pastro 33c24b14b2 registro §45: SPOT-NETTING — il lead regge ma vale solo il funding; T1 sbloccato e' un declassamento e il netting perso risparmia commissioni 2026-08-23 01:22:54 +00:00
Adriano Dal Pastro 279c70222b research(§45): il percorso --no-net non deve crollare — apr assente si DICHIARA, non si formatta
Trovato dallo smoke test a cache fredda: senza get_currencies la sezione 1f cadeva su
TypeError formattando None. Un'analisi che non puo' girare offline non e' riproducibile.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:20:19 +00:00
Adriano Dal Pastro 13daccf6de research(§45): SPOT-NETTING — il margine non uccide il lead, il CODICE si'; e separare le gambe non aggiunge niente
Filone §45: quanto vale, e quanto costa, spostare TP01 sullo SPOT Deribit separandolo
da SKH01 (oggi nettati su un unico strumento). Solo misura, nessun file di produzione
toccato, nessun ordine.

Q1 MARGINE — il venue NON blocca: BTC/ETH sono `in_cross_collateral_pool: true`
[VENUE], lo spot ha `max_leverage: 10` (vive dentro il conto marginato, non in un
wallet a parte) [VENUE], e il margine iniziale misurato sul conto reale e' il 2,00%
del nozionale [CONTO: equity-available su 2 posizioni] -> nel caso peggiore la gamba
SKH01 resterebbe marginata 50x dal solo USDC libero, a QUALUNQUE capitale (il
rapporto e' invariante in E). L'haircut non e' leggibile e non e' binding.
A bloccare e' il CODICE: `shadow._equity` legge solo `account_summary('USDC')` e
`position_usd` matcha per instrument_name -> comprando spot il libro leggerebbe il
25% del conto vero e non vedrebbe la gamba. Non e' un cambio di strumento, e' un
cambio del percorso di sizing del live.

Q2 VALORE — T1 riprodotto (+0,051/+0,057 contro `hourly`, pubblicato +0,054/+0,061)
MA contro `fastdetect`, che il 26/07 stabili' essere il path del live vero, vale
-0,048 FULL (6/23 offset): sbloccarlo e' un DECLASSAMENTO. Il netting perso non
costa commissioni (-0,216% di equity/anno: e' un risparmio) ne' ordini (-6,3/anno):
costa tracking (+12%) e spread ([0,139%,0,250%]/anno). I due si compensano quasi.
Il valore vero e' il funding e basta: +1,58%/anno lordo di drift di libro.

Q3 — `fee_watch` DERIVA i suoi strumenti da `src.live.book.INSTRUMENT`: una gamba
spot sarebbe invisibile (stesso difetto corretto il 21/08 sugli inverse). Riga
dichiarata, non scritta. `convenzione('BTC_USDC')` = 'ignota' -> servirebbe anche
una terza famiglia o il cross-check sui fill resta muto.

Q4 — la liquidazione MIGLIORA (il 75% del libro esce dal perimetro; uno spot non si
liquida) ma la gamba TP01 resterebbe senza disaster-SL; il fisco PEGGIORA di
0,83%/anno se i derivati sono `c-quater`, e i comparti si SEPARANO (le minusvalenze
del perp smetterebbero di compensare le plusvalenze spot): costo nuovo, mai contato.

IPOTESI MIA NATA E REFUTATA: «convertire USDC in spot rinuncia all'interesse». Il
venue dichiara USDC `apr` 3,40; sul log del cron, 6 run flat (il piu' lungo 257 giri
= 10,7 giorni) mostrano equity INVARIATA al centesimo contro i +$0,59 attesi ->
limite superiore su qualsiasi interesse < 0,029%/anno. L'obiezione e' morta.

⚠️ Due istantanee del libro a 4 minuti danno differenziali di spread 2,27 e 4,08 bps
(+79%) e il contributo netto dell'esecuzione CAMBIA SEGNO fra le due: e' dichiarato
come banda, non come punto.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:19:04 +00:00
Adriano Dal Pastro 7264a8fe90 registro §43: DATA-UNUSED SCARTATO — la scorta di dati e' esaurita, e il candidato sta sotto il massimo atteso dal rumore 2026-08-23 01:13:21 +00:00
Adriano Dal Pastro 696f2e5bdd research(§43 DATA-UNUSED): inventario dei dati mai letti + l'unica ipotesi che ne esce, misurata
FASE 1 — censimento di data/ e di CHI lo legge (indice di 647 .py, Old/ escluso).
Colonne MAI lette: 26 su 31 di CoinMetrics (fra cui FlowIn/FlowOutExNtv, 2018-2026 al 100%),
`fetch_errors_json`, `iv_90d`. Tutto il resto con storia vera e' gia' stato analizzato: cio'
che resta non letto e' telemetria a finestra corta (catena opzioni 113 g, 0DTE 30 g, vol_term
58 righe). Corretti in sessione due difetti dell'inventario stesso: la ricerca a SOTTOSTRINGA
dava `iv` in 571 file, e le chiavi derivate dall'etichetta producevano due falsi "NESSUNO"
su famiglie realmente lette (eqx_, fut_deribit/fund_).

FASE 2 — EXFLOW: il turnover LORDO sugli exchange. SCARTATO.
La famiglia exchange-flow fu uccisa il 24/07 sullo STOCK (SplyExNtv). Misurato prima di
riaprirla: `In-Out` e' la derivata dello stock (corr +0.999 BTC / +0.752 ETH) mentre `In+Out`
e' ortogonale (+0.035 / +0.080) — il 94% del flusso si cancella, quindi il lordo e'
algebricamente assente da cio' che era stato provato. Griglia dichiarata prima: 3 variabili x
3 finestre x 2 modi x 2 segni = 36 celle, +4 gia' spese su EXS = 40 trial.
(1) La cella scelta al buio fa Sharpe FULL 0.951 contro un massimo atteso dal PURO RUMORE di
1.009: sotto la soglia che una griglia di monete raggiunge da sola (DSR 0.437 a N=36, 0.411 a
N=40). (2) La selezione in-sample torna sul CONTROLLO NEGATIVO messo apposta nella griglia
(NETCTL = l'informazione gia' uccisa): il lordo non e' selezionabile, hold-out -0.42, DILUTES.
(3) Zero informazione direzionale (|t|<1 su 2 asset x 2 variabili). Il legame col |ritorno| su
ETH (Pearson incrementale t +2.70) non sopravvive al rango (Spearman p=0.46) e cambia segno per
anno; su BTC e' "significativo" nel verso sbagliato.
Sottoprodotti: corr->TP01 0.50-0.65 = replica indipendente del "l'on-chain e' prezzo travestito"
del 24/07 su colonne che quell'ondata non aveva letto; haircut 0.000 a $635.

Corretti prima di pubblicare due errori miei: il pool "N=12" del deflated-Sharpe erano le 12
celle MIGLIORI (rows e' ordinata) e faceva PASSARE il candidato a 0.975 — con la partizione
legittima fa 0.678; e il residuo di vol calcolato a mano invece che per OLS ribaltava il segno
su ETH.

Solo ricerca: nessuna scrittura, nessun ordine, book/pesi/cron/config INVARIATI.
2026-08-23 01:10:52 +00:00
Adriano Dal Pastro 824531b5ba registro §44: DEPOSIT-TIMING SCARTATO 0/12 — il buy-the-dip compra il 51% piu' in basso e arriva nel 6,3% dei casi 2026-08-23 01:06:34 +00:00
Adriano Dal Pastro fc55698096 research(deposit-timing): il timing dei bonifici non paga — 0/12 celle, e il segnale compra davvero il 51% piu' in basso
§44. Prima misura di un calendario di versamento CONDIZIONALE (le 5 leve del piano
misurate finora confrontano solo calendari deterministici).

12 celle dichiarate prima: buy-the-dip x4 soglie, risk-off (TP01 a 0x), valore-medio
x3, anti-dip x4. Stesso flusso di cassa per tutte (EUR X/mese sul conto corrente);
cio' che cambia e' quando entrano nel libro, con la liquidita' in attesa a 0% reale.
Lente L3 CONGIUNTA (funding + fisco), muro $313k, block bootstrap 3000 percorsi.

Replica 4/4 prima di ogni delta: muro $313.143, riga EUR250/m 23,4a / P(20a) 14,4%,
riga EUR500/m 17,3a / 85,4%, e P0 del motore col buffer di cassa BIT-EXACT contro
PN.accumula.

SCARTATO. 0/12 in ogni lente (mercato vero, IID, drift dimezzato, EUR250, EUR500);
migliore -0,03% appaiato contro una risoluzione MC della differenza appaiata di 2,0pp,
e su una cella che aspetta 1 giorno = P0 travestito.

Il meccanismo, misurato invece che assunto: buy-the-dip 20% compra davvero al 0,494
del livello medio del piatto (51% piu' in basso) e arriva al capitale-rendita nel 6,3%
dei casi contro l'85,4%. Comprare meglio e comprare tardi sono la stessa mossa.
Sotto la soglia bassa si ribalta: dip 5% compra a 1,009, cioe' PIU' IN ALTO — una
condizione poco profonda non compra il calo, ritarda dentro la salita.

Due errori catturati su me stesso da un controllo: (i) il ritardo-gemello dava
"informazione" +11,5% sul mercato vero e mi avrebbe fatto scrivere che il dip predice
— sotto IID, dove non c'e' niente da prevedere, la stessa colonna vale +14,9%, quindi
e' meccanica (attesa variabile contro fissa); (ii) senza la colonna dell'attesa avrei
letto P4 anti-dip come "stesso segno => rumore": e' piatto perche' in un mercato che
sale la sua condizione e' quasi sempre gia' vera (16 giorni contro 3682).

Rischio di venue separato dal timing: la cassa fuori dall'exchange riduce la penalita'
di +2,4pp a p=1% e +3,8pp a p=2% su dip 10%, contro una penalita' di timing di -15,7pp,
e P(libro azzerato) e' identica per tutte le politiche.

Ordine di grandezza: la migliore politica di timing vale -0,1pp di P(20a); passare da
EUR250 a EUR500 al mese vale +71pp.

Solo script di ricerca. Book/pesi/cron/config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:05:11 +00:00
Adriano Dal Pastro 6f74dcb843 registro §41: TP01-SIZE SCARTATO — Spearman IS/HOLD −0,527, e la premessa del coordinatore sui bucket di convinzione era falsa 2026-08-23 01:04:43 +00:00
Adriano Dal Pastro 96d37c7013 research(tp01): sizing conviction-aware SCARTATO — l'ottimo del knob sta ai due estremi opposti nelle due meta' del campione
§41 TP01-SIZE. Domanda: esiste una size che risponde alla CONVINZIONE (invece che
solo alla vol realizzata) e che, A ISO-VOL, alzi il drift di TP01? Sarebbe un
miglioramento k-indipendente sul 75% del libro live. Risposta: NO.

Griglia dichiarata PRIMA di guardare: 60 celle (rho = g(1/3)/g(1) x q = esponente
del vol-targeting), TF 1d, 24 ancore, segnale CONGELATO. Replica bit-exact del
canonico max|diff| = 0.0 su target_series E sui rendimenti di sleeve.

- FATTO STRUTTURALE che corregge la premessa: la convinzione NON vale {1/3,2/3,1}.
  La media di 3 segni sta in {-1,-1/3,0,+1/3,+1} -> il bucket 2/3 e' ARITMETICAMENTE
  IMPOSSIBILE. La famiglia ha UN grado di liberta' (rho), non tre: potenza/floor/
  soglia sono la stessa cella riparametrizzata.
- NULL DEL RE-LEVERING misurato in forma pura: togliere il vol-targeting (q=0) porta
  il CAGR da 16,32% a 46,75% (+186%) e a ISO-VOL fa -2,40pp. Era TUTTA leva.
- Il meglio dell'intera griglia e' +0,30pp di CAGR iso-vol. La cella scelta AL BUIO
  (rho=0,25 q=1,25) peggiora l'hold-out del LIBRO in 0/24 ancore e il suo maxDD in
  24/24, contro +0,19pp di CAGR.
- Spearman(ShIS, ShHOLD) = -0,527 sulle 60 celle: qui scegliere in-sample e' PEGGIO
  di una moneta. Meccanismo misurato: Spearman(rho, ShHOLD) = +1,000 a TUTTI e sei i
  q (monotono), mentre in-sample e' a gobba -> la convinzione e' informativa
  in-sample e ANTI-informativa in hold-out. Nessuna cella e' proponibile.
- L'unica con guadagno hold-out robusto e' il BINARIO rho=1 (dShHOLD +0,243, 24/24),
  che perde FULL e drift iso-vol e si potrebbe scegliere solo guardando l'hold-out.
- deflated-Sharpe 0,999 PASS ma QUASI VACUO (famiglia omogenea, sr0 0,197):
  sensibilita' pubblicata, FALLISCE a sr0 >= 0,9. Conferma §10 dell'ondata 22/08.
- Controlli positivi 3/3 (de-levering puro, oracolo look-ahead con causality_ok=False,
  anti-controllo rho=3). Eseguibilita' a $635: haircut 0,001 -> non e' il vincolo.
- Sottoprodotti: banda d'ancora del canonico ricalcolata su dati odierni (hold-out
  canonico 0,441 = 96° pctl, mediana onesta 0,219) e altlib.tp01_baseline_daily NON
  e' bit-exact col sleeve (1 ulp su 68,5% dei giorni: _to_daily fa (1+r).prod()-1).

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 01:02:07 +00:00
Adriano Dal Pastro 8e7d181171 registro §42: TP01-LS SCARTATO — la short toglie drift in 0/24 ancore e senza il 2022 il divario raddoppia 2026-08-23 00:56:10 +00:00
Adriano Dal Pastro 790849cb54 CLAUDE.md: il trasporto degli allarmi non e' mai stato validato — un tentativo, nessun registro, stato marcato prima dell'invio 2026-08-23 00:54:35 +00:00
Adriano Dal Pastro 3e3b41d842 research(tp01-ls): la gamba SHORT del trend a 1d e' SCARTATA — toglie drift a 0/24 ancore
§42 TP01-LS. Meccanismo TP01 di produzione CONGELATO, un solo grado di liberta': il
pavimento della direzione TSMOM (floor 0 / -1/3 / -2/3 / -1, 4 trial dichiarati prima).
Replica bit-exact 3/3 a 0.0 (floor=0 == CANONICAL long_only=True, floor=-1 == long_only=
False, sleeve 50/50 == src/portfolio/sleeves._tp01_returns) + 4a replica candidate_daily
vs tp01_baseline_daily a 0.0. Controlli positivi 4/4 (causality_ok su variante leaky,
implausible_sharpe su serie senza perdite, gate iso-vol su leva pura, anchor_luck_delta
A-vs-A).

Esito: la short NON paga il proprio costo. dDRIFT appaiato -1.91%/anno positivo in 0/24
ancore, dShFULL -0.354 (0/24), maxDD +8.80pp (24/24); gate iso-volatilita' FAIL (dCAGR
-6.19% a pari vol); senza il 2022 il divario RADDOPPIA (dShFULL -0.406, 0/24); anni
positivi 2/8 (2022 +1.84, 2025 +0.27) e non compensano gli altri sei; marginal_vs_tp01
= NEUTRAL su tutte e tre le celle (multicut False, corr 0.79-0.93, alpha -2.6%/anno);
la cella scelta AL BUIO in-sample e' IL CANONICO mentre quella scelta sull'hold-out e'
floor=-1/3 = firma di selezione-sull-hold-out. Non e' morte-per-fee: a fee ZERO 1.338
contro 0.904. Attesa a priori del coordinatore CONFERMATA e superata.

Unica metrica nel verso della short: dShHOLD +0.292 in 23/24 ancore — ma l'hold-out e'
1.6 anni, non e' selezionabile in-sample, e all'ancora canonica non si vede (-0.008:
caso speculare della lezione 26/07). Libro 75/25 con SKH01: dSh -0.356 in 0/24, e la
gamba short isolata ha Sharpe -0.335 con corr +0.10 a SKH01 (non ridondante, solo
perdente). Trovato per strada: src/live/book.py clippa gia' TP01 con max(tp_frac, 0.0)
-> il long-flat e' cablato anche nell'esecutore, non solo in CANONICAL.

Nessun file di produzione toccato. Libro, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018M8Ncho6QV9FWLdyy4VyQf
2026-08-23 00:54:17 +00:00
Adriano Dal Pastro 0ff03babae audit: il trasporto degli allarmi e' un punto singolo di guasto — un tentativo, nessun registro, stato marcato prima dell'invio (6,9% misurato) 2026-08-23 00:50:21 +00:00
Adriano Dal Pastro 09bae3b9ea registro: ondata 7 — cinque filoni su angoli mai toccati (sizing per convinzione, short del trend, dati inutilizzati, timing dei bonifici, separazione spot/perp) 2026-08-23 00:46:51 +00:00
Adriano Dal Pastro 3a4592bdfc CLAUDE.md: nodo del disaster-SL sciolto — rotolante ma scatta MENO; e il docstring della cadenza in book_execute e' una trappola viva 2026-08-23 00:38:16 +00:00
Adriano Dal Pastro 9973b04bc1 research(wave-0822): SL-ANCHOR — il nodo sciolto dal LOG (la SPEC lo diceva non misurabile); rotolante ma il timore e' refutato, e il docstring della cadenza e' una trappola 2026-08-23 00:37:46 +00:00
Adriano Dal Pastro 0f64eb4720 CLAUDE.md: evitare il funding — datati scartati, spot lead subordinato alla domanda fiscale, e il muro USDC di ieri falsificato 2026-08-23 00:19:05 +00:00
Adriano Dal Pastro f5d88f10bb research(wave-0822): FUNDING-AVOID — datati scartati, SPOT e' lead (+1,55%/anno a iso-vol) ma la domanda fiscale vale piu' del risparmio; corretto il muro USDC di §34 2026-08-23 00:18:27 +00:00
Adriano Dal Pastro db9d844351 CLAUDE.md: la chiave di scala specificata — tetto sul prodotto, il test di guardia smette di controllare, e il nodo del disaster-SL rotolante 2026-08-22 23:58:19 +00:00
Adriano Dal Pastro ef30c20af5 research(wave-0822): SCALE-SPEC — chiave specificata, il tetto va sul PRODOTTO, e il test di guardia non si rompe ma smette di controllare; corretto un mio numero conflato 2026-08-22 23:57:48 +00:00
Adriano Dal Pastro 1d513632c7 CLAUDE.md: GATE PROP-01 chiuso 3/3 senza date; P(50/g) onesto 2,6%; XS01 paga funding; il biglietto batte il versare solo perche' il piano esiste 2026-08-22 23:37:14 +00:00
Adriano Dal Pastro df08460af0 research(wave-0822): GATE-C — gate riformulato senza date, PASS 2/2; XS01 PAGA funding; il biglietto batte il versare solo perche' il piano esiste 2026-08-22 23:36:38 +00:00
Adriano Dal Pastro 2da765bcbb CLAUDE.md: il piano al netto di TUTTO — EUR250/mese fa P(20a) 14-26%, non 92%; e le correzioni si sommano invece di compensarsi 2026-08-22 23:13:37 +00:00
Adriano Dal Pastro 758bcce97f research(wave-0822): PIANO-VERO — la tabella congiunta fisco+funding; EUR250/mese passa da P(20a) 92% a 14-26%, e le correzioni si sommano invece di compensarsi 2026-08-22 23:13:05 +00:00
Adriano Dal Pastro fc0c0a2923 CLAUDE.md: il funding misurato — 2,16%/anno, muri +17,5%, e l'avvertenza che fisco e funding si sommano senza che nessuna tabella li contenga entrambi 2026-08-22 22:43:56 +00:00
Adriano Dal Pastro ee5cbb2c08 research(wave-0822): FUNDING misurato — 2,16%/anno di drift, muri +17,5%; esposizione e funding sono correlati e la stima ingenua sottostima di 2x 2026-08-22 22:43:24 +00:00
Adriano Dal Pastro d930492d47 research(wave-0822): CC01 riaperto col 2022 dentro — resta scartato, ma la liscezza era una proprieta' della COLONNA (HL 4,2 bps vs Deribit 106,2) 2026-08-22 22:38:38 +00:00
Adriano Dal Pastro 8eaf7aa730 CLAUDE.md: terza ondata — due gate d'attesa eliminati, il cap e' un clamp non un moltiplicatore, e il funding non e' in nessun backtest 2026-08-22 22:12:01 +00:00
Adriano Dal Pastro 73ae21c955 research(wave-0822): WORST-DAY — la riserva sulla leva e' mal tarata di 2-4 ordini di grandezza, ma il knob di scala NON ESISTE; e il funding non e' in nessun backtest 2026-08-22 22:10:43 +00:00
Adriano Dal Pastro ebc8cf7d7c research(wave-0822): GATE PROP-01 gamba (b) PASS 23/23 — e la distorsione su SKH01 dichiarata due volte e' refutata; P(50/g) 7,8% -> 4,4% 2026-08-22 22:02:26 +00:00
Adriano Dal Pastro dd4391b55b research(wave-0822): GATE-RECON — il difetto ribalta STATARB (+1,96 -> -2,02), la premessa della rigenerazione e' confermata per via diretta 2026-08-22 21:54:59 +00:00
Adriano Dal Pastro bcffcc01af research(wave-0822): GATE PROP-01 gamba (a) CHIUSA — 13/13 sul venue; e la quota d'ingresso e' un deposito rimborsabile, non una fee 2026-08-22 21:40:12 +00:00
Adriano Dal Pastro a1407874cb CLAUDE.md: seconda ondata — XS01 regge fuori finestra, il canale funded scende a 7,8%, e il deflated-Sharpe non ha regione utile in mezzo 2026-08-22 21:35:40 +00:00
Adriano Dal Pastro 89af0554d5 diary(2026-08-22): seconda ondata — XS01 fuori finestra regge, il canale funded si ridimensiona di 5x, il deflated-Sharpe non ha regione utile 2026-08-22 21:33:55 +00:00
Adriano Dal Pastro e460caf667 research(wave-0822): PROP-RECAL — il 42% del numero funded stava in 6 gambe che fuori campione non esistono; P(50/g) 42% -> 7,8% 2026-08-22 21:32:25 +00:00
Adriano Dal Pastro fd37add518 research(wave-0822): BIN-FREQ — direzione reale (0/72 sul segno inverso), taglia = selezione; e due premesse del briefing refutate 2026-08-22 21:22:43 +00:00
Adriano Dal Pastro 74539db8b8 research(wave-0822): DEPEG — XS01-OOS sopravvive al falsificatore di venue; il caso peggiore non e' il depeg ma il 2025-10-10 2026-08-22 21:17:36 +00:00
Adriano Dal Pastro aaa32daff7 CLAUDE.md: buco di colonna nell'archivio catena (underlying 100% None pre-30/07) e come chiuderlo con la parita' put-call 2026-08-22 21:08:57 +00:00
Adriano Dal Pastro 1b5ddd1ba1 research(wave-0822): SURFACE-RV — la superficie e' arbitrage-free sui prezzi eseguibili; l'incoerenza al mid E' la larghezza del mercato 2026-08-22 21:08:36 +00:00
Adriano Dal Pastro 409de063f6 research(wave-0822): registro — TP01-SINISTRO, l'allarme falsificato nel verso 2026-08-22 21:08:02 +00:00
Adriano Dal Pastro 82ccff2553 research(wave-0822): TP01-SINISTRO — l'allarme e' falsificato nel verso; il rischio dell'ottimo funded e' XS01, non TP01 2026-08-22 21:07:19 +00:00
Adriano Dal Pastro 93ce12931a CLAUDE.md: ritiro una regola mia — dealer_net_gamma non e' il GEX invertito, e' una convenzione dichiarata nel sorgente su questa VPS 2026-08-22 20:54:29 +00:00
Adriano Dal Pastro 1ec928cf09 research(wave-0822): XS01-OOS — l'edge esiste FUORI dalla finestra di scoperta ed e' piu' grande li'; il gate del prop-alloc si sostituisce, non si aspetta 2026-08-22 20:52:40 +00:00
Adriano Dal Pastro 0f2e195674 research(wave-0822): MAKER scartato (il segno dipende da < contro <=) + CRITICO — la cucitura dell'ondata, non i filoni 2026-08-22 20:51:47 +00:00
Adriano Dal Pastro 103dd7bce5 research(wave-0822): BOCPD — il falsificatore eseguito con potenza, 0/68 celle adattive; l'adattivita' spiega il -7% del vantaggio 2026-08-22 20:50:03 +00:00
Adriano Dal Pastro 0bcc5bc5d0 research(wave-0822): apre il registro della seconda ondata — 7 filoni sui buchi della prima 2026-08-22 20:34:08 +00:00
Adriano Dal Pastro 827ae54dc1 CLAUDE.md: ondata 2026-08-22 — difetto dei monitor forward, tre soglie falsificate, la leva invisibile ai gate, e una regola ritirata 2026-08-22 18:04:52 +00:00
Adriano Dal Pastro 272622b6e8 research(wave-0822): PROP-ALLOC — riallocare per la barriera vale il 4%, diversificare vale tutto, e la banda va da 42% a 0,7% 2026-08-22 18:03:12 +00:00
Adriano Dal Pastro 93147a95c8 diary(2026-08-22): ondata multi-agente — 20 filoni, 0 candidati, 1 difetto di produzione, 3 soglie falsificate 2026-08-22 18:02:22 +00:00
Adriano Dal Pastro fbb6e75e67 research(wave-0822): MONITOR-AUDIT — 4 monitor su 6 rotti, il gate STATARB si ribalta, ma la finestra e' rigenerabile e nessuna data si sposta 2026-08-22 17:52:53 +00:00
Adriano Dal Pastro cef559b350 research(wave-0822): ritirato anche il sottoprodotto sull'universo USDC 'piu' liquido' — piu' OI e meno quote 2026-08-22 17:46:33 +00:00
Adriano Dal Pastro 987569c5a3 research(wave-0822): corretta la mia inferenza su BTC_USDC — l'OI non misura la negoziabilita' 2026-08-22 17:46:22 +00:00
Adriano Dal Pastro fe6ad97225 research(wave-0822): ALT-OPT — l'open interest e la negoziabilita' sono anti-correlati (rho −0,77); corretta la mia inferenza su BTC_USDC 2026-08-22 17:46:13 +00:00
Adriano Dal Pastro 1750b5a93b research(wave-0822): lo scettico RITIRA il difetto di contabilita' (non esiste, bit-exact) e chiude oggi il gate del 22/12 — il meccanismo e' un filtro di frequenza 2026-08-22 17:43:33 +00:00
Adriano Dal Pastro b6c0deb866 research(wave-0822): BASIS-CALENDAR scartato — il basis dei datati E' il funding del perp; ma in regalo 240k barre di futures scaduti col 2022 dentro 2026-08-22 17:39:55 +00:00
Adriano Dal Pastro 32ed18222e research(wave-0822): lo scettico conferma il gradino di leva ma corregge due contorni — e la lente close-only e' cieca solo sulle regole a UN giorno 2026-08-22 17:36:45 +00:00
Adriano Dal Pastro 5fe931e00d research(wave-0822): SLIP-AUDIT — nessun costo nascosto a questa taglia, ma la misura scade (22% del nastro a 600 diventa 687% a 20k) 2026-08-22 17:34:51 +00:00
Adriano Dal Pastro 090129359b research(wave-0822): HL-EXEC refuta il muro dei 20k di XS01 e lo slippage come rischio #1 — e il 20k di venue e' un'altra cosa 2026-08-22 17:33:55 +00:00
Adriano Dal Pastro ea22a0e20c research(wave-0822): XSR-REPRO trova un difetto di produzione (i monitor forward registrano ~41 min/giorno); SKEW scompone il f di VRP01 — il 42% e' struttura a termine 2026-08-22 17:29:19 +00:00
Adriano Dal Pastro f0122d97a1 research(wave-0822): VOL-SIZE — il null di permutazione si cita col segno, non col decimale (gira su 3 ancore su 23) 2026-08-22 17:24:23 +00:00
Adriano Dal Pastro f975272ec8 research(wave-0822): VOL-SIZE — il p-value del null di permutazione si cita col segno, non col decimale (3 ancore su 23) 2026-08-22 17:24:10 +00:00
Adriano Dal Pastro e8bbb92f8a research(wave-0822): VOL-SIZE e' un LEAD — e un overlay giornaliero su equity a gradino e' look-ahead che nessun causality check vede 2026-08-22 17:23:22 +00:00
Adriano Dal Pastro aa72e0c9ed research(wave-0822): versione finale di r0822_term_structure (sezione 7 + tre fix dell'agente) 2026-08-22 17:21:24 +00:00
Adriano Dal Pastro 110f894bdf research(wave-0822): TERM-STRUCTURE e OI-PIN scartati — la catena ereditata ha 74 giorni utili, non 3,7 mesi 2026-08-22 17:19:45 +00:00
Adriano Dal Pastro 75606d0f44 research(wave-0822): VRP-QUOTE-VERE scartato — e collect_chain raccoglie la famiglia di contratti che il conto non puo' marginare 2026-08-22 17:19:07 +00:00
Adriano Dal Pastro f4b14f305b research(wave-0822): FLOW-SQUEEZE scartato — e il filone funding si chiude sul QUARTO lato (affollamento) 2026-08-22 17:12:42 +00:00
Adriano Dal Pastro bd5b634209 research(wave-0822): ORTHO-SCREEN 7/7 scartato (e uno screen largo non puo' passare il proprio DSR); XS-LITE falsifica il muro dei 20k di XS01 2026-08-22 17:12:15 +00:00
Adriano Dal Pastro 14c1a75a7e research(wave-0822): GROWTH-POLICY — il libro gira al 7% di Kelly, e ogni gate del progetto e' cieco alla scala 2026-08-22 17:10:03 +00:00
Adriano Dal Pastro 3b206c8e6d research(wave-0822): DEALER-GAMMA scartato — e dealer_net_gamma e' il GEX col segno invertito 2026-08-22 17:08:20 +00:00
Adriano Dal Pastro ff4aa94528 research(wave-0822): ledger degli esiti — ADAPTIVE-HORIZON scartato 2026-08-22 17:03:07 +00:00
Adriano Dal Pastro fa86a7b089 research(wave-0822): brief condiviso per l'ondata multi-agente 2026-08-22 16:43:06 +00:00
Adriano Dal Pastro cb8d9e2a0e docs: SOL escluso — decisione dell'operatore, con la condizione di riapertura
L'analisi del 22/08 (eec7642) concludeva "scartato"; qui la conclusione diventa una
DECISIONE registrata, con la stessa disciplina usata per la decisione di venue del
26/07: cosa NON si ri-discute, cosa la riaprirebbe, e una nota per il futuro-me.

Nessun cambio di codice: l'universo direzionale era gia' BTC/ETH ed e' presidiato da
test_l_universo_direzionale_resta_BTC_ETH.

Riapertura: ~3 anni di storia SOL certificata (dal 2024) tali da rifare la misura
SENZA la finestra 2022-23 che la certificazione segnala — quindi non prima del 2028 —
oppure un meccanismo che non sia TP01/SKH01 congelati. I parquet alt_sol_* restano su
disco per quel giorno (precedente: i 51 HL tenuti dopo il rifiuto dell'espansione
XS01), fuori dal feed attivo e non rinfrescati dal cron.

La nota per il futuro-me c'e' perche' l'argomento piu' probabile per riproporre SOL
("e' eseguibile su Deribit") e' proprio quello che l'analisi ha gia' escluso:
l'eseguibilita' non e' mai stata il problema, l'hold-out lo e' a 24 ancore su 24.

Book, pesi, config, cron: INVARIATI. Suite 631 verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-22 08:46:35 +00:00
Adriano Dal Pastro eec76424ee research(sol): SOL come terza gamba direzionale — SCARTATO, il guadagno e' un anno solo
Domanda dell'operatore dopo "hai gia' analizzato XRP/SOL/UNI?": si', ma sempre
dentro panieri cross-sectional su Hyperliquid. SOL e' l'UNICO dei tre eseguibile su
Deribit e TP01/SKH01 non erano mai stati misurati su di lui. Ipotesi a priori
registrata PRIMA di guardare: diluisce (trend multi-asset 19/06, corr 0.74).
Confermata.

DATO. Storico ricostruito da Deribit mainnet (SOL/USDC:USDC, 466.776 barre 5m dal
2022-03-15, 0 gap, resample maxΔ 0.00bps) e certificato: >1% da Coinbase nell'1.3%
(2022) e 0.6% (2023) delle barre, med 8.1 -> 3.9 bps dal 2022 al 2026; flat 1h 0.2%,
5m 20.8%. Conferma esatta del verdetto del 19/06. Da qui DUE LENTI dichiarate prima
di misurare: L-FULL (2022-03+) e L-PULITA (2024+).

GAMBE SOLE, meccanismi CONGELATI (nessuna ri-ottimizzazione su SOL): TP01 SOL Sh 0.91
con hold-out -0.24; SKH01 SOL Sh 0.51 con maxDD 40.5%. Quest'ultimo non e' un
dettaglio: SKH01-V2-DD fu SELEZIONATA il 23/06 sul criterio maxDD<30% (BTC 21%,
ETH 27%) -> su un asset nuovo fallisce il criterio per cui la variante esiste.

BOOK, 24 ancore, mediana delle differenze APPAIATE: dSharpe hold-out -0.166 e >0 in
0/24 ancore in ENTRAMBE le lenti. L-PULITA: dSharpe FULL -0.099 (0/24), dCAGR -1.34pp
(0/24). L-FULL: dSharpe FULL +0.094 (24/24) ma dCAGR +0.10pp.

IL DD SCENDE MA E' DE-LEVERING (5a occorrenza dopo VRP-DD, TP01xDVOL, MAT01, azioni
intere UCITS): a pari maxDD, su L-PULITA basta k=0.886 sul book a 2 gambe per avere
Sharpe 1.54 contro 1.30 e CAGR 14.5% contro 12.6%. L'unica lente in cui SOL aggiunge
e' quella costruita sui dati che la certificazione segnala.

E DENTRO QUELLA LENTE IL GUADAGNO E' UN ANNO: dSh 2022 -0.91 / 2023 +1.06 / 2024
-0.29 / 2025 -0.20 / 2026 -0.22 = 4 anni su 5 negativi. La gamba SOL da sola fa
Sh -1.99 / +2.65 / +0.45 / +0.17 / +1.46. Il 2023 e' la risalita post-FTX da ~$8 a
~$100: un evento, non un meccanismo. Corr col book +0.404 (L-FULL) / +0.561
(L-PULITA), vicina allo 0.74 che boccio' il trend multi-asset, e in salita man mano
che il dato migliora.

L'ESEGUIBILITA' NON E' IL VINCOLO: SOL_USDC-PERPETUAL ha min 0.001 SOL = $0.09 contro
il pavimento min_order $5. Primo candidato bocciato senza che il muro sia la taglia
del conto.

EFFETTO COLLATERALE TROVATO SU ME STESSO. Il "guardrail solo dati certi" dichiarato in
CLAUDE.md — load_data("SOL") -> FileNotFoundError — NON e' codice: load_data non ha
whitelist, solleva solo perche' il file non c'e'. Ricostruendo SOL in
data/raw/sol_1h.parquet il guardrail si e' disattivato in silenzio, e quel file non
viene rinfrescato dal cron (--asset BTC ETH) -> sarebbe diventato dato stantio con
l'aspetto di dato attivo. Riparato con la convenzione gia' in uso (hl_/eq_/eqx_/fut_):
SOL vive in data/raw/alt_sol_*.parquet. Congelato in due test, di cui uno DERIVA gli
asset a rischio da rebuild_history.DERIBIT_INSTR. La prima stesura di quel test
elencava i prefissi a mano e bocciava eqx_, fut_, vol_term_, fundnews_ (namespace
veri): l'invariante si deriva dal codice, non si elenca — stessa lezione di fee_watch.

Book, pesi, universo direzionale, config, cron: INVARIATI. Suite 631 verdi.
NB: test_gtaa_band_gate e' tornato VERDE da solo, senza modifiche al codice, perche' il
cron ha riscritto i parquet equity — la conferma in positivo della diagnosi del 07/08.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-22 07:11:16 +00:00
Adriano Dal Pastro 8cfe15cbd5 fee_watch: sorvegliava i perpetual INVERSE mentre il book trada i LINEARI USDC
Trovato in un check generale. INSTRUMENTS era la tupla cablata
("BTC-PERPETUAL","ETH-PERPETUAL") — gli inverse, regolati in BTC/ETH — mentre
src.live.book.INSTRUMENT punta a BTC_USDC-PERPETUAL / ETH_USDC-PERPETUAL.

Due conseguenze, e la seconda era gia' visibile ogni giorno nel log:

1. Il tier sorvegliato era di un prodotto che il book non tratta. Oggi coincidono
   (3.50/1.50 su entrambe le linee) ma la prova che si muovono in modo indipendente
   e' nel progetto: il cambio del 18/08 tocco' tick e size dei SOLI lineari USDC
   (inverse ancora tick 0.5 / min 10.0, lineari 0.1 / 0.0001). Un aumento sulla sola
   linea lineare sarebbe stato invisibile, e la regola decisa in anticipo
   (<=5bps nulla / >10bps rivedere il peso SKH01) applicata al numero sbagliato.

2. Il cross-check sui trade REALI — la fonte autorevole, cioe' quanto abbiamo
   davvero pagato — non poteva misurare nulla per costruzione: chiedeva la storia di
   uno strumento con zero fill. Stampava "NON MISURATO (nessun trade recente
   leggibile)" anche in un giorno con 4 esecuzioni. Verificato sul conto: inverse
   0 trade, _USDC-PERPETUAL 3 (BTC) e 1 (ETH).

FIX. INSTRUMENTS si DERIVA da src.live.book.INSTRUMENT: la divergenza non e' piu' un
rischio da ricordare, e' impossibile.

E non era un rename di due stringhe: le due famiglie hanno unita' DIVERSE. Inverse
amount = nozionale USD e fee in valuta base; lineare amount = quantita' base e fee
gia' in USDC. Ripuntare senza correggerle avrebbe dato, su un fill vero (0.001 BTC
@ 74.305,80, fee 0,02600703 USDC), ~2,6e8 bps invece di 3,50 — senza sollevare
nulla. Aggiunte convenzione() (lineare / inverse / IGNOTA: una famiglia non nota non
si indovina, si dichiara) e fee_bps_di_un_fill(), entrambe pure. Il cross-check ora
gira e da' 3,50 bps effettivi = il tier esatto; il report stampa lo scarto
effettivo-tier con ⚠️ oltre 1 bps.

Test 13 -> 17, verificati per MUTAZIONE: rimettendo la tupla cablata fallisce
test_sorveglia_esattamente_gli_strumenti_DEL_BOOK; scambiando le convenzioni
fallisce test_le_due_famiglie_hanno_unita_DIVERSE_e_scambiarle_non_fa_rumore, che
contiene il controllo positivo (la convenzione sbagliata NON solleva niente, mente).

3a occorrenza in un giorno della stessa forma di difetto, dopo i test di book_live
(potenza zero a libro flat) e la taratura di venue_watch (misurata con bitfinex
mentre il live girava senza): un controllo puntato su una configurazione diversa da
quella che gira passa sempre, e non sta controllando niente. REGOLA: un sorvegliante
DERIVA il proprio bersaglio dal codice sorvegliato, mai lo ridichiara.

Book, pesi, config, cron, soglie fee: INVARIATI. Suite 625 verdi, 1 rosso noto
(test_gtaa_band_gate). NB: la prima corsa dopo il fix ha inviato una notifica
Telegram legittima ("strumento nuovo nella sorveglianza"); lo stato e' poi assestato.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-21 19:19:22 +00:00
Adriano Dal Pastro fac9978d87 venue: la taratura ri-misurata — «zero falsi allarmi in 8 anni» non descriveva la produzione
B1 (memoria) + B2 (misura). Il 19/08 stava solo in un diario e in un commit: la
sessione che ha cambiato il tripwire di venue, la tabella _CONTRACT e le referenze
non era in CLAUDE.md — 2a occorrenza dopo edge_watch, e riguarda di nuovo qualcosa
che gira con soldi veri. Ora c'e', insieme al debito che dichiarava.

B2: il debito era «la taratura non e' ri-misurata a tre referenze». Ri-misurandola
(scripts/research/r0821_venue_refs.py, riusa dislocation/episodes/zero_fp_frontier
di r0726) il problema non era dove ci si aspettava.

1. «Zero falsi allarmi in 8 anni» veniva dal consenso Coinbase+Bitstamp+BITFINEX
   dello script di ricerca; il sorvegliante live gira su Coinbase+Bitstamp. Due
   liste di referenze in due posti diversi, e nessun test poteva accorgersene.
   Sull'insieme reale i falsi allarmi sono 1: 2020-03-13 07:00-10:00 UTC, 4 ore a
   -418 bps di picco su BTC = il crash COVID, cioe' proprio l'evento che CLAUDE.md
   elencava come esempio di cio' su cui NON scattava. La firma che lo dimostra: le
   "65.043 ore BTC" citate in memoria sono esattamente le ore utili del set con
   bitfinex; sul set reale sono 69.633.

2. Kraken non lo ripara: su 8 anni porta un mese. Il tetto ~700 candele
   dell'endpoint pubblico e' stato ri-verificato oggi sulla rete (704 barre su
   70.286 richieste = 1,00%), non creduto da un commento del 26/07.

3. Perche' spariva a 3 referenze, ed e' il punto trasferibile: con bitfinex dentro
   1 delle 4 ore diventa BLIND, lo streak si azzera e l'episodio non esiste — ma la
   dislocazione e' ancora li' (mediana -343 bps). Lo zero non veniva da un consenso
   piu' accurato, veniva da un'ora buttata (ore utilizzabili 93,4% vs 100,0%).

4. La direzione dichiarata il 19/08 ("piu' BLIND, allerta di meno") e' confermata ma
   la sua taglia dipende dal venue, non dal numero tre: confronto appaiato sulle
   stesse ore, con bitfinex -13,91 pp di ore utilizzabili, con kraken +0,00 pp.

5. Controllo positivo intatto: Bitfinex 2018-19, 22 episodi, il piu' lungo 2.324h,
   picco 1.136 bps = 11,4x la soglia.

DECISIONE: (100 bps, 4h) NON si tocca, ma la giustificazione cambia. 1 falso allarme
in 8 anni costa 0,031%/anno di equity attesa contro il 100% che un vero positivo
evita (ogni p plausibile e' 16-160x sopra il break-even); alzare a 150 bps per
ripristinare lo zero porterebbe il margine su FTX da 3,0x a 2,0x, sotto la gamba (b)
del criterio dichiarato prima di guardare i dati. La memoria si contraddiceva da
sola — «zero falsi allarmi» al punto (2), «a 1 ogni 8 anni serve p > 0,031%» al
punto (4) — e la meta' giusta era quella dell'economia.

Congelato il MECCANISMO, non il numero: tests/test_venue_watch.py 35 -> 37, due test
puri (lo spread max-min e' monotono nel numero di referenze; una sola ora BLIND
spezza lo streak, con un caso di controllo che DEVE scattare).

Soglie, book, pesi, config, cron: INVARIATI. Suite 621 verdi, 1 rosso noto
(test_gtaa_band_gate, altro asse). Diario: docs/diary/2026-08-21-venue-taratura-*.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-21 17:55:16 +00:00
Adriano Dal Pastro e69cc5bd81 test(book): i due test della formula del report avevano potenza ZERO a libro flat
I due confronti `abs(net_target - formula) < 1e-6` erano insoddisfacibili per
costruzione: `book_report` PUBBLICA valori arrotondati (`net_target` a 2 decimali,
`tp_frac` a 4) mentre l'ordine viene costruito sul valore non arrotondato
(`build_book_order(inst, net, ...)`), quindi un test che ricalcola la formula dal
`tp_frac` pubblicato eredita DUE arrotondamenti. Nessun ordine e' mai stato sbagliato:
lo scarto e' 0.5-1.5 centesimi su target da $114 e $954, con min_order a $5.

⚠️ Il difetto vero non e' la tolleranza, e' la POTENZA: con `tp_frac=0` e `skh_sign=0`
il target e' esattamente `0.0`, i due arrotondamenti sono esatti e l'invariante passa
senza essere mai esercitata. Dal 2026-06-23 al 2026-08-18 il book e' stato flat quasi
ininterrottamente -> per due mesi questi test non hanno verificato nulla su una formula
di produzione, e il difetto e' emerso solo quando TP01 e SKH01 sono andati long insieme.
Stessa lezione del 26/07 (test_skh_partial_entry): un self-check su eventi rari si
campiona sugli EVENTI, non sulla popolazione.

- `_budget_arrotondamento(equity)`: tolleranza DERIVATA (0.005 del round del net +
  WEIGHT*equity*W_TP01*0.00005 del round del tp_frac propagato), non tarata sul risultato.
- `test_la_formula_del_report_ha_potenza_anche_a_libro_flat`: segnale FORZATO su 4
  frazioni scomode (long+SKH long, long+SKH short, flat+SKH short, cap) con contatore
  che verifica che tutti i casi diano target != 0 -> la copertura non dipende dal mercato.
- `test_il_budget_di_arrotondamento_non_copre_un_errore_di_formula`: controllo POSITIVO,
  i modi reali di rompere la formula (pesi scambiati, cap non applicato, segno invertito)
  devono stare oltre 100x il budget. Una tolleranza che assolve tutto non e' una tolleranza.

Verificato per MUTAZIONE, non a occhio: `round(net, 0)` in book.py -> falliscono tutti e
tre (incluso il nuovo, che e' il punto); `W_TP01 <-> W_SKH` -> falliscono test_net_target_sizing
e il controllo positivo. src/live/book.py ripristinato bit-identico, produzione NON toccata.

38/38 in tests/test_book_live.py; suite 619 passati, 1 fallito (il noto
test_gtaa_band_gate, altro asse, invariato).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-21 17:17:27 +00:00
Adriano Dal Pastro c932fab304 venue_watch: disciplina degli allarmi, specifiche contratto controllate, terza referenza
Il 18/08 sono usciti quattro 🚨 identici con 'PRIMO PASSO: prelievo di prova'
per una manutenzione Deribit annunciata, e tutti e quattro DOPO che il book
aveva gia' ripreso a eseguire. Il book si era comportato bene (due giri di
astensione, 'non eseguo a cieco'); il difetto era negli allarmi.

1. Il blocco piattaforma era un if secco senza memoria, accanto a un rilevatore
   tarato con cura che allerta una volta per streak. Ora passa da lock_step(),
   pura e testata: manutenzione entro tolleranza = un solo avviso morbido, che
   sfora = un solo 🚨 ('ha SFORATO'), blocco inspiegato = 🚨 subito, rientro
   annunciato una volta. public/status illeggibile NON e' un rientro.

2. Il messaggio diceva 'locked=true' cablato mentre il parser accetta anche
   'partial': dichiarava un valore che non aveva letto, e il runbook manda a
   controllare proprio quel campo. Ora stampa e salva il valore grezzo.

3. Deribit ha cambiato tick e size dei perpetual lineari USDC il 18/08 e la
   tabella _CONTRACT, cablata a mano, non se n'era accorta. Nessun ordine
   rifiutato solo perche' i cambi erano riduzioni: e' andata bene per la
   direzione, non perche' ce ne fossimo accorti. Tabella aggiornata ai valori
   verificati e aggiunto check_specs(), che gira nel venue_watch orario (fuori
   dal percorso ordini) e dichiara la direzione: 'granularita'' = conforme,
   'rifiuto' = il venue rifiuta. La tabella dichiarata resta l'autorita' per
   costruire un ordine, il venue e' il controllore.

4. Aggiunta Kraken come terza referenza: Coinbase ha comprato Deribit, e una
   referenza che e' la casa madre non misura piu' se Deribit scolla dal mondo.
   THRESHOLD_BPS e PERSIST_HOURS invariati, ma il consenso ora e' su tre serie
   e quel numero non e' ri-misurato: dichiarato nel codice e nel diario. La
   direzione dell'errore e' 'allerta di meno', non 'grida al lupo'.

Test 23 -> 35 su venue_watch, suite intera 618 verdi. Book, pesi e config
invariati; dry-run del book verificato. Diario: docs/diary/2026-08-19-*.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-19 10:10:55 +00:00
Adriano Dal Pastro b1c3ff1bb8 docs(fisco): quadro fiscale verificato sulle fonti — la citazione normativa era sbagliata
Verificato sulle fonti (Fisco Oggi dell'Agenzia, Eutekne, Fiscomania, Circolare AdE 30/E
del 27/10/2023, guide professionali) cio' che il progetto assumeva senza averlo mai
controllato. NON e' un parere fiscale.

CONFERMATO, e nessun numero del piano cambia: 33% sulle plusvalenze cripto realizzate dal
1/1/2026 (art. 67 c.1 lett. c-sexies TUIR); franchigia EUR 2.000 abolita dal 2025;
minusvalenze riportabili 4 periodi ma solo contro plusvalenze cripto (art. 68 c. 9-bis);
patrimoniale 2 per mille sul valore al 31/12; regime dichiarativo per gli exchange esteri.

CORRETTO: il progetto citava «L.199/2025» come origine del 33% in 5 punti (r0725_capcurve,
r0725_ib10k x2, r0727_tasse, r0807_asset_compare, diario 24/07). E' falso. Il 33% dal 2026
e l'abolizione della franchigia vengono dalla L. 207/2024 art. 1 c. 23-29. La L. 199/2025
art. 1 c. 28 ritaglia il 26% per i soli token e-money denominati in EURO: BTC/ETH e le
stablecoin in dollari restano al 33%.

RESTA APERTA la domanda che vale $22k di muro: la Circolare 30/E non tratta i derivati, e
le fonti professionali collocano i derivati su cripto fuori dalle cripto-attivita'
(c-quater, RT Sez. II, 26%) — ma parlando di CFD di broker UE regolati in euro, non di
contratti inverse marginati e regolati IN CRIPTO su sede extra-UE. Registrata la domanda
da porre al commercialista nei termini esatti.

Trovata per strada una conseguenza modellistica: se i derivati sono c-quater, sono un
comparto di compensazione separato → il buffer di carry UNICO di r0807_piano_netto e
r0727_tasse e' ottimistico sulla coda (non sull'aliquota).

REGOLA: una fonte normativa citata in un commento di codice si verifica come un numero —
questa era sbagliata da settimane in 5 file e nessun test poteva accorgersene.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 19:51:50 +00:00
Adriano Dal Pastro 3bc620e914 docs: memoria — gate GTAA corretto, storia troncata di TLT, tabelle del piano al netto
Tre aggiornamenti alla memoria operativa:

1. Il bullet "BANDA GTAA01 AL 25%" registrava «proposta 4/30 in-sample, 5/30 hold-out →
   il rango NON migliora» come evidenza. Non lo era: quel criterio lo passa il 47% della
   griglia per costruzione. Sostituito col criterio decidibile (la banda scelta al buio
   in-sample E' la proposta, quella scelta sull'hold-out no), che e' piu' forte del
   precedente. Registrata la storia troncata di TLT e la guardia cablata.

2. Il bullet "IL FISCO DURANTE L'ACCUMULO" dichiarava che tutte le tabelle a 15-20 anni
   erano al lordo. Ora ci sono le versioni nette (muro, traiettorie, versamenti, rendita)
   con il controllo di replica.

3. Le due tabelle lorde piu' citate (traiettoria da $600 e "quanto versare per un
   orizzonte dato") portano un rimando esplicito alla versione netta: restano perche'
   sono la replica di controllo del fattore d'ancora, non perche' siano il piano.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 19:31:02 +00:00
Adriano Dal Pastro 02e0cf775f research(capitale): il piano rifatto AL NETTO — il muro si sposta poco, i versamenti molto
Il 07/08 era stato misurato che l'accumulo composto al lordo sovrastima il capitale del
30% a 10 anni, ma i numeri del piano non erano stati rifatti. Qui lo sono.

Il muro usava una convenzione ASIMMETRICA: prelievo lordizzato (€50/g netti → $29.690
lordi) ma capitale che compone senza mai pagare imposte. Coerente (imposte annue dentro
il portafoglio, prelievo gia' netto): perpetua 10.91% → 7.70%, muro $272.061 → $258.338
(-5.0%). I due errori vanno in versi opposti e si compensano quasi — per caso, non per
costruzione.

E' sulle traiettorie che il fisco morde, e si legge nella PROBABILITA':
€250/mese P(entro 20a) 92% → 52%; €500/mese 100% → 99%. Il versamento necessario a P=90%
passa da €237 a €371/mese a 20 anni (+57%), da €509 a €672 a 15 (+32%), da €1.178 a
€1.323 a 10 (+12%): l'errore era composto, quindi cresce con l'orizzonte. Rendita a 20
anni con €250/mese: 91.30 → 46.61 €/g, P(€50/g) 90% → 42%.

Controllo di replica superato prima di guardare i numeri nuovi: a fisco spento la macchina
riproduce $272.061 al dollaro (implementazione separata) e la colonna LORDA riproduce 4
righe su 4 della tabella pubblicata. Trovato per strada: perp_and_wall gira a 2000 path e
a quella taglia da' $269.648 — la terza cifra del muro e' rumore Monte Carlo.

Errore mio catturato prima di pubblicare: la mediana degli anni calcolata sull'INTERO
vettore coi non-arrivi a -1 faceva risultare €250/mese PIU' VELOCE col fisco (15.7 →
15.3 anni) mentre P crollava. Un non-arrivo va codificato +inf, mai -1.

Book/pesi/cron/config INVARIATI: non tocca la produzione.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 19:30:49 +00:00
Adriano Dal Pastro 963776e5d2 research(gtaa): il gate (A) non misurava cio' che dichiarava — e TLT ha 13.5 anni in meno
Il test del gate sulla banda GTAA01 aveva smesso di passare senza che il codice fosse
cambiato (data/raw/ e' gitignored, IB rivede ADJUSTED_LAST all'indietro ogni notte).
Invece di allentare la soglia, misurata la risoluzione del criterio.

`rank_in <= rank_oos` lo passano 14/30 celle (47%) PER COSTRUZIONE: la somma dei ranghi
e' la stessa nelle due finestre. E sulla proposta si decideva su 0.00116 di Sharpe contro
uno spread di griglia di 0.3124. Il 27/07 quel criterio passava, e passava per caso.

Criterio sostituito con quello decidibile: la proposta e' una BANDA (la cadenza settimanale
e' gia' produzione), quindi a cadenza fissa la banda scelta sui soli dati pre-2015 e' 25%
= la proposta, margine +0.0151 (13x il vecchio); chi avesse scelto sull'hold-out avrebbe
preso 40%. Controllo positivo incluso. Regge sull'universo coerente a 5 gambe.

TROVATO PER STRADA: TLT parte dal 2016-02-03 invece che dalla quotazione (2002-07-22) →
GTAA01 gira su CINQUE gambe prima del 2016, e quella assente e' la gamba obbligazionaria.
Non e' di oggi (cosi' dal primo giro nel cron log del 24/06, prima della validazione) e non
e' un fetch da rifare: una richiesta retro esplicita a IB ritorna 0 barre.

Nessuna certificazione l'aveva visto perche' tutte guardano DENTRO la serie: una serie
troncata e' integra, senza gap, senza spike, senza duplicati. Cablate due guardie in
fetch_ib_equities.certify — TRONCATO (storia persa vs disco; il file NON viene sovrascritto
ne' fuso, ADJUSTED_LAST e' ri-aggiustato all'indietro e il giunto creerebbe un salto) e
STORIA-CORTA (parte dopo la quotazione, con distinzione dal tetto della richiesta 30Y).
Controlli negativi obbligatori: giro normale, serie al cap, ETF giovane, simbolo fuori
tabella.

Produzione INVARIATA: REBAL_BAND_USD resta $50, GTAA01 resta non deployabile (PRIIPs).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 19:30:34 +00:00
Adriano Dal Pastro ba5ea2f5c3 docs: diario 07/08 e memoria — e un gate di GTAA01 che ORA FALLISCE
Diario 2026-08-07-crescita-fisco-etf-scelta.md + i bullet corrispondenti in
CLAUDE.md (fisco d'accumulo, confronto book/ETF, scelta 50/50, simulatore web).

Registra anche un buco trovato ricostruendo il piano: i QUATTRO risultati del
27/07 sera (r0727_3k_vs_5k, r0727_orizzonte10, r0727_tasse) non erano ne' in
CLAUDE.md ne' in un diario — vivevano solo nei messaggi di commit, e uno di essi
cambia il numero di testa del piano.

GATE GTAA01 CHE FALLISCE (test_gtaa_band_gate::test_la_proposta_non_e_selezionata
_sull_hold_out): la proposta e' 9a/30 in-sample e 8a/30 sull'hold-out contro il
4/30 e 5/30 registrato il 27/07 — cioe' migliora dove non doveva essere guardata.
Caratterizzato prima di riportarlo: i due ranghi distano 0.00116 di Sharpe su
un'ampiezza di griglia di 0.3124 (0.4%), quindi il criterio non ha mai avuto
margine; il calcolo e' deterministico (2 corse, max|diff| = 0.0) e il codice e'
invariato dal 27/07 -> e' cambiato il DATO, perche' data/raw/ e' gitignored e i
parquet equity sono riscritti ogni giorno dal cron con ADJUSTED_LAST di IB, che
e' retroattivo.

REGOLA NUOVA: un gate validato su dati sovrascritti ogni giorno non e'
ri-verificabile. Il lato cripto non ha il problema (rebuild_history.py ricostruisce
da sorgente deterministica), il lato equity si'.

Il test NON e' stato toccato: allentare una soglia perche' ha smesso di passare e'
proprio cio' che questo progetto vieta, e un xfail silenzierebbe il segnale.
Niente di operativo dipende da questo (GTAA01 non e' deployabile per il blocco
PRIIPs e non e' nel book live), ma l'affermazione "il rango NON migliora
sull'hold-out" oggi e' falsa e la decisione su cosa farne e' dell'operatore.

Book, pesi, cron, config/live.json e i gate pre-registrati: INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 18:44:36 +00:00
Adriano Dal Pastro ed2532b991 feat(web): simulatore di accumulo nel browser, verificato contro il Python
scripts/web/ — motore in JavaScript (engine.js) sui ritorni VERI del book
esportati da export_series.py, pagine assemblate da build.py. Da "sistema
dinamico dove imposti valore iniziale, mensile e durata, e calcola la best curva
fissando il tempo": la simulazione gira nel browser, quindi il motore va
riscritto e VA PROVATO che dia la stessa risposta.

test_engine.js confronta mediane e probabilita' con r0807_growth_yearly.py su due
configurazioni, esige che il versato (deterministico) coincida al centesimo, e
include un controllo positivo — un motore col fisco spento DEVE risultare fuori
tolleranza, perche' un test che non sa fallire non e' un test. Il risolutore e'
validato contro dep_necessario di r0727_tasse.py: -0.4 / -0.6 / -1.1%.

smoke.js ESEGUE le pagine con un DOM finto. Serve perche' node --check valida solo
la sintassi: ho pubblicato una pagina che lo passava e moriva alla prima riga
utile (chiavi Python "0.0" ricostruite in JS come String(0) = "0"; i pesi
intermedi funzionavano per caso).

Altri due errori che questi strumenti hanno intercettato:
- due anni di dati di un grafico scritti A MEMORIA perche' tail aveva troncato
  l'output -> ora i dati si INIETTANO da JSON (build.py), il passaggio manuale
  non esiste piu';
- una "distorsione sistematica" del motore JS (+0.75%, 8 semi tutti positivi) che
  erano 8 estrazioni contro UN punto Python rumoroso. Misurato bene, 8 semi per
  parte: -0.01%, t = -0.04; ed entrambi i campionatori cadono entro 1.7 SE
  dall'atteso ANALITICO della media di blocco.

Scelta guidata da una misura: la banda del versamento suggerito resta +-1% da
1.200 a 3.000 percorsi -> non domina il Monte Carlo ma la granularita' della
bisezione (~5 EUR). Percorsi tenuti bassi e incertezza dichiarata, invece di
pagare tempo per una precisione che non arriva.

Nessun impatto sulla produzione: non tocca book, pesi, cron o config.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 18:44:13 +00:00
Adriano Dal Pastro 56141b0ffe research(portafoglio): book vs ETF — le due lenti si contraddicono, la scelta robusta e' 50/50
r0807_asset_compare.py (book / S&P 500 / MSCI World sullo stesso piano) e
r0807_best_strategy.py (quale peso scegliere a 12 anni). Da "e se mettessi in
MSCI World o ETF SP500?" e "quale e' la miglior strategia?".

Tre cose rese comparabili: la GRIGLIA (azioni su calendario con 0.0 a borsa
chiusa = convenzione GTAA01; senza, Sharpe x1.20), il FISCO (book realizza ogni
anno al 33%, UCITS ad accumulazione paga il 26% alla vendita -> le curve ETF sono
valori di liquidazione: il differimento e' un vantaggio strutturale dell'ETF e
va nel modello), il BERSAGLIO (272.061$ vale per la rendita perpetua DEL BOOK e
per il 33% -> ricalcolato per ciascuno).

Il risultato non e' chi vince, e' che le due lenti si contraddicono: sulla storia
piena il book arriva al 115% del proprio bersaglio e l'S&P al 32%; sulla stessa
finestra 118% e 110%, e l'S&P ACCUMULA PIU' del book. Il divario e' tutto nei
crolli 2000/2008 che la strategia non ha mai vissuto.

E sulla stessa finestra il rendimento e' quasi identico (17.4% vs 16.8%): la
differenza e' tutta nel rischio (vol 11.0 vs 19.6%, maxDD 10.5 vs 33.7%). Il book
non guadagna di piu', perde di meno — conferma indipendente di cio' che il
progetto scrive di TP01 dal 19/06, contro un'alternativa vera.

Difetto corretto in sessione: un MIX esiste solo dove esistono ENTRAMBE le serie.
La prima stesura confrontava "storia piena" contro "stessa finestra" ma calcolava
i bersagli del mix sull'intersezione in tutti e due i casi -> dichiarava 30 anni e
ne usava 7 (per l'ETF puro: rendita 8.63% invece del 4.16% vero). Rifatto su una
finestra sola con gli scenari come spostamento del drift, simmetrico sui due lati.

A 12 anni vince 50/50 sul RIMPIANTO massimo (20% contro 52% del book puro e 53%
dell'ETF puro); il criterio del solo caso peggiore non distingue 25% da 50%
(27.09 vs 26.99% = pareggio nel rumore). L'asimmetria fra i due stress e' il
risultato: quello sull'equity e' misurato (30 anni esistono), quello sul book e'
giudiziale (7.4 anni sono tutta la sua storia).

MSCI World e' un PROXY 70% SPY + 30% EFA: URTH/ACWI/VT non sono
nell'abbonamento dati del conto IB, e la nota lo dichiara invece di nasconderlo.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 18:43:57 +00:00
Adriano Dal Pastro 68c6894d85 research(capitale): il fisco durante l'ACCUMULO non era mai stato contato
r0807_growth_yearly.py: crescita anno per anno separando versamenti e guadagno,
con e senza l'imposta d'accumulo. Nasce da "grafico della crescita per anno con
versamento e con guadagno".

TAX_RATE compariva in UN SOLO punto del progetto: la lordizzazione del bersaglio
in fase di PRELIEVO. L'accumulo componeva al lordo per dieci o vent'anni.
Costo (lump 5k + 500/mese): -15.7% a 5 anni, -29.8% a 10, -42.6% a 15 — replica
coerente col 27/07 su lump 10k (-16.8/-31/-44%). L'errore e' COMPOSTO.

Conseguenza: tutte le tabelle a 15-20 anni pubblicate in CLAUDE.md sono al lordo.

Contro-intuitivo e misurato: versare di piu' RITARDA il sorpasso (l'anno in cui
il guadagno cumulato supera il versato) — 7o anno a 500/mese, 8o a 800 — perche'
alza l'asticella. I 300 in piu' comprano il traguardo (12o anno invece del 15o,
P(bersaglio) a 15a da 73.2% a 99.0%), non il sorpasso.

Riusa senza riscriverle la contabilita' fiscale di r0727_tasse.accumula e il
block bootstrap di r0725_capcurve.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-07 18:43:38 +00:00
Adriano Dal Pastro f81c783ea7 fix(sicurezza): dashboard 8787 solo su 127.0.0.1, era raggiungibile da internet
La riga era "8787:8787", cioe' pubblicata su tutte le interfacce. ufw non la
fermava: il DNAT che Docker installa in nat/PREROUTING devia il pacchetto prima
della catena INPUT su cui ufw lavora, e in FORWARD la catena DOCKER lo accetta
prima delle catene ufw-*-forward (DOCKER-USER era vuota). Verificato: da IP
pubblico la dashboard rispondeva HTTP 200.

Dietro c'erano conto e posizioni reali (monta .env.mainnet per lo Shadow live),
senza autenticazione, su http.server della stdlib, processo root.

Svista e non scelta: la riga sotto lega gia' il gateway IB a 127.0.0.1 con il
commento "raggiungibile solo da localhost dell'host".

Dopo il fix: DNAT con -d 127.0.0.1/32, listener solo su 127.0.0.1:8787, da IP
pubblico connessione rifiutata. pythagoras-ibgw non toccato.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-08-04 09:35:49 +00:00
Adriano Dal Pastro fb01c5714c research(vrp): f misurato sul 10g — il mio sospetto era sbagliato, e il campione non basta ancora
Book, pesi, config INVARIATI. Nuovo sorvegliante in cron_daily.

IL CAMPIONE C'ERA GIA': 8 scadenze utilizzabili per asset su 8, entrambe le
strutture, 16 osservazioni ciascuna. Non serviva aspettare per fare la misura;
serve aspettare per rispondere alla DIFFERENZA, che e' un'altra domanda.

CORREZIONE A UN ARGOMENTO PUBBLICATO POCHE ORE FA. Nel gate del tenore avevo
scritto che la cella vincente 'sta massimizzando l'errore di modello' perche'
compra l'ala piu' lontana. Misurato: il meccanismo e' confermato e piu' forte
del previsto (f_long 5.85 contro 2.23) ma la conclusione era ROVESCIATA —
quell'ala pesa il 3.2% del premio corto invece del 18.4%, quindi sul credito
NETTO l'effetto e' minore: f_net 0.852 contro 0.718, il candidato ha un f
MIGLIORE. Con f_net = (f_short - k*f_long)/(1-k), un f_long grande fa danno
solo moltiplicato per un k grande: avevo guardato il fattore e non il peso.
La decisione (nessun cambio) regge, ma su tre gambe invece di quattro.

Artefatto di tick escluso prima di crederci: l'ask dell'ala sta a 22 tick
mediani, minimo 15, 0% delle osservazioni a <=2 tick.

LA DIFFERENZA NON E' STABILITA: appaiata per (asset, scadenza) fa +0.109 con
IC95 [-0.047, +0.193], 11/16 positive -> contiene lo zero. Replica indipendente
del canonico: 0.718 per un percorso con finestra DTE e pairing diversi da
quello che stamattina dava 0.73.

CRITERIO PRE-REGISTRATO, congelato in un test: >=40 coppie E ampiezza IC95
<=0.12 (oggi 16 e 0.241), prima gamba verso fine ottobre 2026. Il sorvegliante
rifa' la misura ogni giorno e notifica una volta sola quando basta — lezione
DVOLSPREAD, un lead senza sorvegliante e senza data e' un lead perso.

Calibrazione della soglia verificata prima di fidarsene: con differenza vera
nulla lo zero e' escluso nel 5.0/4.0/3.0% dei casi a n=16/40/60, cioe' il 5%
atteso. Il test iniziale su seed fisso falliva perche' quel seed era uno dei 5%
legittimi: sostituito con un test sulla proprieta'.

REGOLE: (a) un fattore di errore si giudica moltiplicato per il suo peso;
(b) prima di credere a un rapporto estremo su un prezzo piccolo, contare i
tick; (c) una soglia sull'ampiezza di un IC richiede di verificarne la
copertura; (d) 'non abbastanza campione' non e' 'nessuna differenza'.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 22:17:11 +00:00
Adriano Dal Pastro 36dc55748e research(vrp): buco del tenore chiuso col gate onesto — earns_slot_honest = False
Book, pesi, cron, config INVARIATI.

La griglia strutture del 03/07 si fermava a 10 giorni. Famiglia dichiarata nel
docstring PRIMA di guardare i numeri: 8 tenori (5-35g) x 3 delta corti x 3
lunghi = 72 celle, perche' riaprire il tenore riapre la struttura e i trial si
contano al rialzo.

study_family_honest e' cablato sui candidati direzionali (factory -> target_fn
via candidate_daily) e VRP01 non lo e': usati i suoi tre componenti reali —
selezione in-sample-only, altlib.deflated_sharpe, altlib.marginal_vs_tp01 —
importati e non riscritti (c'e' un test d'identita').

ESITO. Cella scelta al buio 10g -0.28/-0.05 (Sh IS 1.75 / FULL 1.55 / HOLD 1.01)
contro il canonico 7g (1.50/1.32/0.82; rango 17/72 in-sample). Batte il canonico
ma DSR 0.948 < 0.95 FAIL. marginal_vs_tp01 = ADDS per entrambe: il verdetto non
e' 'VRP01 e' rotto', e' che il vantaggio non sopravvive al conto dei trial.

IL BUCO SI CHIUDE SUL CONTENUTO, non sul gate: la regione mai esplorata PERDE.
Miglior cella >10g = 18g, rango 8/72, e solo 3/10 della top-10 sta oltre i 10
giorni -> lo studio conferma il 03/07 invece di ribaltarlo.

IL VINCITORE STA DOVE IL MODELLO SBAGLIA DI PIU': compra l'ala piu' lontana
(delta lungo -0.05), come 5/10 della top-10, cioe' la gamba che il 30/07 ha
misurato sottoprezzata ~2.3x. Sospetto motivato, non dimostrazione: il mediano
non separa -0.10 da -0.05, si separa la coda alta. Ma f non e' misurato fuori
dalla struttura canonica, e la sensibilita' a f uniforme e' la lente sbagliata
per una struttura il cui errore e' concentrato in una gamba sola.

ROBUSTEZZA DEL VERDETTO, PUBBLICATA: DSR 0.983 PASS a N=8, 0.948 FAIL a N=72,
0.909 a N=360. Il verdetto si ribalta col conteggio. La griglia era dichiarata
in anticipo e il conto fatto al rialzo, ma fallisce per 0.002: si cita come
tale, non come refutazione netta. Congelato in un test.

Seguito giusto = una MISURA, non un altro backtest: quanto vale f sul
10g/-0.05 sulle quote vere, ora che la catena la raccogliamo noi ogni ora.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 22:06:31 +00:00
Adriano Dal Pastro 04cb572535 research(vrp): profit-take al 50% REFUTED, e una correzione a un numero di stamattina
Book, pesi, cron, config INVARIATI.

VRP01 tiene fino a scadenza (S1 = px[i+tn], nessuna gestione infra-settimana)
e il profit-take era l'unico grado di liberta' non misurato: i 4 overlay del
03/07 erano tutti sul lato del RISCHIO, questo e' sul lato del PROFITTO.
Replica del sleeve bit-exact (max|diff| = 0.0) prima di ogni delta.

VERDETTO con fee reali per gamba: canonico ShFULL 1.32 -> PT25 0.22 /
PT50 -0.18 / PT75 -0.45. Null del de-levering REFUTED 6/6: a PT25 basta
k=0.818 per lo stesso DD con Sharpe 1.32 invece di 0.22.

MECCANISMO (confronto appaiato per ingresso): scatta sull'86-91% dei VINCENTI
e sul 19-25% dei perdenti -> tronca i vincenti del 27% e salva un perdente su
cinque. La peggior settimana e' IDENTICA (-7.27%) in ogni variante: nelle
settimane brutte lo spread non tocca mai +50%, quindi e' pura troncatura
dell'upside.

IPOTESI MIA REFUTATA IN SESSIONE: 'su 7g chi tocca +50% e' chi sarebbe scaduto
senza valore, quindi a scadenze lunghe paga'. Testata su 7/10/14/18/21/28g:
delta Sharpe negativo a tutti e sei. A 18g (il tenore di cerbero-bite) il DD
migliora 7.1->3.8% ma lo Sharpe crolla = firma del de-levering.

CORREZIONE a un numero pubblicato oggi: il sleeve modella le fee come 12.5%
del credito netto, il listino vero e' 0.03% del sottostante per gamba (cap
12.5% del premio della singola opzione, che quasi mai morde) -> sovrastima di
~2x. Il numero onesto di VRP01 con f=0.73 e' ShFULL 0.47, non 0.31.
fee_frac NON cambiato: il forfait e' conservativo e i numeri di ammissione di
questo progetto si tengono conservativi.

A $3.000 la domanda non e' il rendimento: BTC min 0.1 = $6.210 di collaterale
per lotto -> FUORI; ETH min 1 contratto = $1.832 -> 1 lotto. Il sleeve 50/50
diventa ETH-only e al peso di book (12% = $360) sono 0 lotti.

REGOLE: (a) un'uscita si giudica appaiata per INGRESSO, mai allineando le serie
sulla data di USCITA — e' quella che la variante cambia, e l'inner-join tiene
solo i casi in cui non e' successo niente (errore commesso e corretto in
sessione, congelato in un test); (b) una regola d'uscita che scatta piu' spesso
sui vincenti che sui perdenti non e' protezione, e' troncatura; (c) prima del
rendimento a un capitale dato, misurare il lotto minimo del venue.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 21:57:15 +00:00
Adriano Dal Pastro a2f28153d8 docs(bite): verificato il primo giro post-eliminazione, e come NON leggere quote_status
Il giro delle 21:25 (primo con bite gia' cancellato): 576 chiamate, 0 risposte
429, 0 errori. E' il controllo che conta, perche' il guasto del 29/07 era la
raffica di bite che saturava il rate limit per-IP.

Aggiunta la tabella dei 5 giri della giornata, che mostra invarianza prima/dopo.

⚠️ E una precisazione sul nostro stesso strumento: 'ok' significa ALMENO UN LATO
del book, non quota completa. Con ok=572 le righe a due lati sono 432 (75.5%).
Che sia strutturale (opzioni molto OTM) e non un degrado si vede dall'invarianza
fra i giri, non dal fatto che il numero sembri alto.

E' 'una riga presente non e' un dato presente' un livello piu' in giu', applicata
allo strumento costruito per quella lezione: la battuta di cuore vedrebbe il
guasto del 29/07 (quote vuote) ma non una deriva verso book a un lato solo.
Nessuna soglia cablata: con 5 giri di storia sarebbe inventata, e una soglia
inventata e' peggio di nessuna soglia. La colonna da guardare e' 'due lati %'.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 21:33:46 +00:00
Adriano Dal Pastro 933ccff057 docs(bite): cerbero-bite ELIMINATO — cosa e' stato verificato prima di cancellare
Container, volume, immagine e cartella rimossi il 2026-07-30 (12 GB liberati).
Book, pesi, cron, config INVARIATI: la raccolta era gia' passata al successore
e la sovrapposizione fra le due ha coperto la consegna senza buchi.

Le quattro verifiche, nessuna delle quali era 'il backup esiste':

1. Snapshot COMPLETO, non solo integro: SHA256 OK su entrambi i file, ma
   soprattutto conteggi confrontati tabella per tabella fra volume vivo e
   snapshot (1.232.212 / 17.406 / 59 / 0), identici anche ai parquet importati.
   Un hash prova che il file non e' corrotto, non che contenga tutto.

2. I 10,6 GB di backup interni al volume non contenevano dati unici. La domanda
   giusta non era la loro dimensione ma se bite potasse lo storico: tutti e tre
   i campioni controllati hanno la STESSA riga piu' vecchia (2026-05-01T20:53:49)
   e conteggi monotoni crescenti -> nessuna potatura, sottoinsiemi stretti.

3. Zero dipendenze a runtime: ne' cron, ne' systemd, ne' route traefik, ne'
   altri progetti. I riferimenti rimasti sono documentazione, che resta.

4. cerbero-mcp e' un progetto DIVERSO e serve a PythagorasGoal (Hyperliquid,
   percorso del conto). Progetto compose separato; la rete traefik condivisa e'
   external: nel compose di bite, quindi down -v non la tocca. Verificato dopo:
   Up 41 hours (healthy). Due servizi con lo stesso prefisso sono un incidente
   che aspetta.

Il codice non e' stato perso: era su Gitea (Adriano/Cerbero-Bite) e l'unica
modifica pendente e' stata committata la' come commit di dismissione.

REGOLA: prima di cancellare una sorgente si verifica che la copia sia COMPLETA,
non che esista.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 21:24:39 +00:00
Adriano Dal Pastro e9a4538054 chore(gitignore): la battuta di cuore del collettore e' stato runtime, non sorgente
data/chain_collect/runs.jsonl era finito tracciato nel commit d55eb13: e' lo
stato del collettore (una riga per giro, oraria), della stessa famiglia di
data/paper_*, data/live, data/venue_watch, data/fee_watch — tutti gia'
gitignored. Tracciato avrebbe sporcato ogni commit futuro con una riga di
heartbeat e messo in git un file che il monitor riscrive da solo.

Rimosso dall'indice (il file su disco resta: e' la serie che monitor_health
sorveglia) e la cartella aggiunta a .gitignore.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 20:34:08 +00:00
Adriano Dal Pastro 444b804415 ops(backup): PythagorasGoal nel backup rotativo, solo il dato non ricostruibile
data/raw/ e' gitignored e /opt/docker/scripts/backup.sh non copriva questo
progetto: dopo lo spegnimento di cerbero-bite la catena opzioni esisteva in
due copie SULLO STESSO DISCO.

Aggiunta do_pythagoras con criterio dichiarato — si salva cio' che non si
puo' riscaricare:
  dentro (28 MB): catena + contesto, data/paper_* e data/chain_collect
    (serie forward-only che alimentano i gate pre-registrati: non sono
    ricalcolabili, sono un registro di cosa si sapeva e quando),
    options_daily, live, venue_watch, fee_watch, config/live.json
  fuori (~110 MB): quanto si riscarica dai venue (rebuild_history, fetch_dvol,
    fetch_hyperliquid, fetch_ib_equities) + cache

Due guardie provate nei DUE versi: fallisce se la catena e' assente o vuota
invece di produrre un archivio che sembra a posto, e verifica che il tar
contenga davvero la catena (caso negativo: 0 file prodotti). La radice e'
sovrascrivibile via PYG_ROOT solo per poter far scattare la guardia.

Verificato che dopo un riavvio la raccolta riprenda da sola: cron enabled +
active, nessuna dipendenza da docker o cerbero-mcp; giro provato con env -i
(574 chiamate, 0 errori). Finestra scoperta fino al :25 successivo, senza
catch-up.

/opt/docker/scripts NON e' un repo git: la modifica vive solo su disco, il
diario e' l'unico posto in cui e' scritta.

Book, pesi, config, strategia INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 20:25:08 +00:00
Adriano Dal Pastro d55eb13533 feat(chain): assorbita la raccolta catena opzioni, cerbero-bite dismesso
cerbero-bite viene eliminato. L'unica sua parte irreversibile e' il DATO:
una catena opzioni non si ricostruisce a posteriori (Deribit non serve book
storici, non c'e' un secondo venue). Il codice si riscrive; le ore non
raccolte no.

ASSORBITO
- scripts/live/collect_chain.py + scripts/cron_chain.sh (cron 25 * * * *):
  raccolta propria, ~570 strumenti/giro, ~3 min.
- scripts/analysis/import_cb_archive.py: archivio 1.23M righe (2026-05-01+)
  + market_snapshots 17.402 righe (2026-03-26+: dealer gamma, gamma flip,
  rischio liquidazioni, funding cross — dati che non abbiamo altrove).
- snapshot sqlite integrale in /opt/docker/backups/manual/ (SHA256).

NON ASSORBITO, con motivo: motore credit-spread ETH (regola "niente
short-vol da modello in deploy", conto a $52 contro minimo $720), GUI, kill
switch/dead-man/audit (abbiamo venue_watch/edge_watch/monitor_health/
fee_watch), dvol_history (fetch_dvol.py ha storia PIU' LUNGA: 2020+ contro
2026-05), decisions/positions (0 posizioni).

TRE DIFETTI DI BITE NON REPLICATI, tutti misurati il 30/07:
1. una chiamata per strumento invece di due (get_order_book?depth=3 da' gia'
   quote+greche+IV+OI+book+underlying) + prefiltro OI in una chiamata sola:
   551 -> ~290 chiamate per asset;
2. pacing invece di raffica. Il carico non e' mai stato il problema: 570
   chiamate/ora = 0.16/s DISTRIBUITE; bite le sparava in 26s (~44/s) e si
   auto-saturava il rate limit per-IP (12.186 risposte 429 in 26h, 96% al
   minuto :00). Primo giro reale: 574 chiamate, 0 risposte 429. Il minuto :25
   e' scelto: :00 era la raffica, :07 e' cron_book (feed 5m di SKH01).
3. quote_status esplicito {ok, no_quote, error} e book_depth NULL su errore
   mai 0. "Book vuoto" e "chiamata fallita" sono cose diverse: e' per questo
   che il guasto del 29/07 (50% di quote perse, 38 ore) non produsse alcun
   segnale. Le righe ereditate restano 'unknown': bite non lo registrava e a
   posteriori non e' ricostruibile.

Battuta di cuore in data/chain_collect/runs.jsonl anche a giro fallito,
sorvegliata da monitor_health (1h, max_age 3h): un collettore fermo non
produce niente, e il niente si legge come "nessun dato quel giorno".

Difetto trovato per strada: due formati ISO nella stessa colonna (92 righe
di backfill senza microsecondi). pd.to_datetime senza `format` ne inferisce
uno solo e manda gli altri a NaT -> il dropna a valle li toglieva in
silenzio, e la serie di contesto perdeva 5 settimane slittando dal 26/03 al
01/05. Corretto con format="ISO8601" e scarto RUMOROSO.

Book, pesi, config, strategia INVARIATI. 537 test verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 20:14:34 +00:00
Adriano Dal Pastro 8c18e82f1a research(vrp): il f del credito netto e' 0.73 sulle quote reali, non 1.0
Prima integrazione della catena opzioni Deribit mainnet accumulata da
cerbero-bite (/opt/docker/cerbero-bite, dal 2026-06-09: entrambe le ali,
1g-3mesi, oraria, con book_depth). E' l'unica fonte di prezzi opzioni VERI
del progetto, e non e' ricostruibile a posteriori: Deribit non serve book
storici, un'ora non raccolta e' persa.

VRP01 prezza entrambe le gambe con BS su DVOL ATM (VRP_CFG f=1.0 sul credito
NETTO). Misurato agli STESSI strike su 8/8 scadenze settimanali con entrambe
le gambe quotate (delta -0.270/-0.099 contro target -0.280/-0.100):

  f gamba corta   1.02   <- replica la calibrazione del 20/06
  f gamba lunga   2.30   <- l'ala che si COMPRA
  f credito NETTO 0.73   IC95% [0.698, 0.780], 0/15 osservazioni >= 1.0

Meccanismo, non rumore: IV(corta)-DVOL +0.8pp ma IV(lunga)-DVOL +7.5pp -> il
modello prezza a vol ATM anche l'ala comprata. Il difetto non e' nel premio
incassato ma nella protezione comprata, cioe' proprio il "defined-risk" per
cui v2 fu promosso.

Conseguenza standalone (solo f): 1.00 -> FULL 1.08 / HOLD +0.58; 0.80 -> 0.51
/ -0.02; 0.73 -> 0.31 / -0.23. Book 5-sleeve: FULL -0.069, HOLD -0.103, DD
invariato = dentro la banda d'ancora, ma ~meta' del contributo LOO di VRP01
era il prezzo che il modello si faceva da solo.

VRP_CFG["f"] NON cambiato: 15 osservazioni, 7 settimane, e 0/8 passano il
gate IV-rank>0.30 -> il f e' misurato nel regime in cui il sleeve sta FLAT.
Caveat quantificato, non nuovo parametro. Il criterio del 19/06 (rivalutare
quando cerbero-bite cattura un crash) e' intatto.

Book, pesi, cron, config INVARIATI.

Regole nuove congelate nei test:
- il f di una struttura multi-gamba non e' il f di una sua gamba (misurare la
  sola gamba venduta da' la risposta sbagliata con segno rassicurante);
- un guasto IN CORSO si misura al GIORNO PEGGIORE, non in media (la prima
  stesura della certificazione diluiva un guasto di 2 giorni da 51.7% a 13.5%);
- una riga presente non e' un dato presente.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-30 19:51:52 +00:00
Adriano Dal Pastro 7d64dd4c2b live(feed): l'allerta funzionava, la sua CAUSA era una riga cablata
Il 29/07 il feed 5m di SKH01 e' ricaduto sul certificato in 6 giri orari su 8
(eta' 265->685 min, +60 a ogni giro = firma esatta del fallback): latenza
d'uscita da ~1h a ~11h, book flat, nessuna posizione esposta. L'allerta del
26/07 ha segnalato 6/6, poi ha stampato un perche' che non aveva misurato —
la nota "fetch pubblico KO" era cablata, identica in ogni caso, compreso
quello in cui la coda fresca E' attaccata e il vecchio e' il certificato.

E la causa vera non era recuperabile per costruzione: _fetch_recent_5m ingoia
l'eccezione di pagina con un break e a prima pagina fallita ritorna un frame
vuoto, indistinguibile da "il venue non ha barre".

Cablato: livefeed.last_fetch_error() (registra E logga nel punto in cui
l'errore viene ingoiato) -> book_report.skh_feed_errors -> allerta con la
causa. Stesso buco chiuso sul ramo gemello "conto offline", che la ragione
l'aveva gia' in mark_src e non la stampava mai.

La causa del 29/07 resta IGNOTA e va citata cosi': una prima stesura la
attribuiva a un rate limit per-IP come se fosse un fatto -> rimossa, sarebbe
stato lo stesso difetto che stavo correggendo scritto meglio. Cron spostato
al minuto :07 come ripiego da UNA osservazione, dichiarato tale.

Test 11 -> 16 (incluso il caso a meta' paginazione: coda parziale attaccata,
mancano le barre PIU' recenti). Book/pesi/config/strategia INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-29 12:20:42 +00:00
Adriano Dal Pastro 0a77290636 research(capitale): il fisco durante l'ACCUMULO non era mai stato contato — vale il 31% a 10 anni
r0727_tasse.py. TAX_RATE=0.33 compare in tutto il progetto in UN SOLO punto: la lordizzazione
del bersaglio (fase di RENDITA). L'accumulo compone al lordo per dieci o vent'anni.

10.000 EUR + 500/mese, 10 anni, capitale mediano:
  nessuna imposta (modello pubblicato)  229.638$   P(entro 10a) 34.5%
  plus 26%                              173.284$                 8.5%
  plus 33% + patrimoniale 0.2%          158.401$                 3.8%   = -31%

Versamento necessario a 10 anni (lump 10k): P=50% da 602 a 880 EUR/m; P=75% da 790 a 1.051.
Cioe' +33%: il numero dato stamattina (790-870 EUR/m) era al lordo del fisco.

L'errore e' COMPOSTO, non una tantum: -16.8% a 5 anni, -31% a 10, -44% a 15, -55% a 20.

Assunzioni dichiarate (NON un parere fiscale): 33% cripto da L.199/2025 (misurato anche a 26%,
perche' e' aperto se i derivati di sede estera seguano quel regime), minusvalenze riportabili
4 anni, 0.2% annuo sul valore. Il modello tassa la variazione ANNUA di valore, quindi anche la
parte non realizzata a cavallo del 31/12: e' un LIMITE SUPERIORE rispetto alla pura
realizzazione, ma il turnover del book lo rende stretto.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 19:51:42 +00:00
Adriano Dal Pastro 067c89fc16 research(capitale): aggiunta la riga 10k al filone orizzonte-10
10.000 EUR + 500/mese: P(entro 10 anni) 33.9% (contro 19.7% con 5k), mediana 10.7 anni,
rendita a 10 anni 42.25 EUR/g. Raddoppia quasi la probabilita' ma resta fuori dal vincolo.

Versamento richiesto con lump 10k: P=50% -> 604 EUR/m, P=75% -> 793, P=90% -> 975.
Cioe' 5.000 EUR in piu' oggi valgono 77 EUR/mese per 10 anni (~9.240): meno del 2.45x
misurato su 20 anni, perche' a orizzonte corto il lump compone meno.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 19:37:34 +00:00
Adriano Dal Pastro fa18621eb3 research(capitale): 50 EUR/g in 10 anni costa ~870 EUR/mese, non 500
Vincolo nuovo dell'operatore (49 anni, non oltre 10 anni). r0727_orizzonte10.py.

Il piano attuale NON regge il vincolo: 5.000 EUR + 500/mese danno P(entro 10a) = 19.7%
(mediana incondizionata ~11.4 anni).

Quanto serve al mese per 10 anni, con lump 5.000:
  P=50% -> 689 EUR   P=75% -> 870 EUR   P=90% -> 1.047 EUR
A P=75% si versano $119.273 per arrivare a $272.061: e' la frase del 26/07 col prezzo
attaccato (a orizzonte corto non fai lavorare la strategia, compri il capitale coi bonifici).

Tabella inversa (lump 5k), cio' che si compra in 10 anni:
  500/m -> 36.90 EUR/g    800/m -> 55.57    1.000/m -> 72.66    1.500/m -> 105.94

Due difetti miei corretti prima di pubblicare:
- la colonna "anni mediani" era CONDIZIONATA ai percorsi che arrivano: mostrava 9.4 anni
  accanto a P=15%, che e' contraddittorio. Ora e' etichettata "mediana SE ce la fa".
- il muro stampato (254.524$, ricalcolato dalle serie di questo script) non era quello usato
  nelle simulazioni (272.061$ pubblicato). Le due costruzioni del book live danno rendite
  perpetue 10.91% e 11.67%; si tiene la conservativa e si dichiara la differenza.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 19:29:37 +00:00
Adriano Dal Pastro 1aa5a0616a research(capitale): 3k o 5k -> ~3.7 mesi su 11.5 anni, non e' una decisione importante
r0727_3k_vs_5k.py. Domanda dell'operatore, poi ristretta a "fregatene del fuori": quanto
versare su Deribit dei 6.043 EUR fermi in XEON.

Tutto su Deribit, 500 EUR/mese, bersaglio 272.061$:
  3.000 EUR -> 11.73 anni    4.000 -> 11.58    5.000 -> 11.42    6.043 -> 11.28
Ogni 1.000 EUR in piu' all'inizio vale ~1.8 MESI. P(entro 20a) 100% in tutti i casi.

Il motivo strutturale: fino al traguardo entrano ~69.000 EUR di versamenti, quindi il
versamento iniziale e' il 4-9% del flusso totale. La decisione che conta e' la SOSTENIBILITA'
dei 500/mese (26/07: smettere al 5o anno porta P(muro) dal 90% al 53% = venti volte l'effetto
misurato qui).

Aggiunto anche il taglio con il venue dentro (quota fuori 46% vs 16%) e il fatto che con i
versamenti su Deribit quella quota si DILUISCE: 4.0 anni di copertura versando 3k, 0.7 anni
versando 5k -> la differenza fra i due e' temporanea, non una postura permanente.

simulate() accetta dep_to (dove vanno i versamenti); replica del 26/07 preservata.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 19:17:59 +00:00
Adriano Dal Pastro 17b0f2cb47 research(capitale): "5k messi dove" — lo split si ottiene versando di meno
Misura nuova: a $6.050 lo split CON GTAA01 e' impossibile (servirebbe il 50% del conto per
i $3.000 di gamba minima), ma quello in LIQUIDITA' non ha soglie.

Due correzioni prima dei numeri:
- la configurazione vera e' 5.000 + 500/mese (dal commento in config/live.json del 26/07),
  non i 250/mese di tutte le tabelle. Nessuna azione di config: il cap e' gia' armato e
  vale min($3.000, equity_osservata x 0.5) = leva lorda <=1x.
- a $6.050 non si sblocca nulla (GTAA01/XS01/XSR01 tutti fuori portata o sotto gate):
  il book resta TP01+SKH01.

Split in liquidita' (p=1%, 20a): fuori 10% -> P(perso tutto) 18.4% -> 3.5% (0.0% con cassa
in banca), salvati $6.818; 25% -> salvati $17.045, al prezzo di 0.9pp di P(arrivare) e circa
un anno di ritardo mediano.

P(perso tutto) SATURA a qualunque quota > 0: la protezione binaria si compra col fatto di
avere un secondo conto. Cio' che distingue le quote e' il salvataggio.

ERRORE CORRETTO IN SESSIONE: la colonna del salvataggio riportava prima il capitale a 20 anni
condizionato al fallimento ($77k al 10% = 11x il vero), gonfiato dalla convenzione ereditata
dal 26/07 per cui i versamenti si dirottano ai superstiti -> attribuiva allo split il valore
di continuare a versare, che si ottiene comunque aprendo un altro conto. Ora misura il
salvataggio istantaneo, congelato in un test.

simulate() accetta un hazard PER VENUE (una cassa in banca non fallisce come un exchange);
la replica esatta dei numeri del 26/07 e' preservata e testata.

Test: 4 nuovi (508 totali), tutti verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 14:58:50 +00:00
Adriano Dal Pastro fd05307c96 research(capitale): il lump-sum vale 2.45x, e la protezione dalla rovina non passa da GTAA01
Quattro filoni chiesti dall'operatore ("proposte"). Book, pesi, config: INVARIATI.

1. LUMP-SUM + VENUE (r0727_lumpsum_split.py). Tutte le traiettorie del 25-26/07 avevano
   START=600 cablato: mai misurato un versamento iniziale, mentre ~10k EUR stanno fermi
   altrove. Macchineria validata: con lump 0 riproduce IDENTICI i numeri del 26/07.
   - 10k EUR oggi e mai piu' nulla -> traguardo 17.2a, P 62%, rendita 61.58 EUR/g
   - equivalenza onesta: +154 EUR/mese per 13 anni = 24.523 EUR, cioe' 2.45x
     (la prima stesura misurava i versamenti risparmiati: numero giusto, domanda sbagliata)
   - col rischio venue: a 11.500$ lo split e' possibile (quota IB 26%, non 25%) e taglia
     P(perso tutto) da 18.4% a 3.5% a p=1%, costando 1.9-2.6pp di P(arrivare)
   - SPLIT-CASSA: seconda gamba ferma costa altri 0.6-0.8pp e protegge IDENTICO
     -> la protezione non e' bloccata dal PRIIPs: serve un CONTO, non uno sleeve

2. FEE WATCH (scripts/live/fee_watch.py). Nuovo schema Deribit dal 1 agosto senza numeri
   pubblicati -> sorvegliante invece di promemoria. Legge il tier base dall'endpoint
   pubblico (oggi taker 5.00 bps), applica la regola congelata e allerta sui cambiamenti.

3. MONITOR HEALTH (src/live/monitor_health.py). Tre gate pre-registrati si decidono su
   serie forward di cui una sola era sorvegliata. Misura coda E buchi interni: una serie
   bucata ma fresca passa qualunque guardia di freschezza.

4. BANDA GTAA01 25% VALIDATA (r0727_gtaa_band_gate.py). 30 celle, 29.9 anni, dpy=252.
   Non e' selection-on-holdout (4/30 IS, 5/30 OOS), DSR 0.999, tracking OK ma AL BORDO.
   Il modo di fallire non e' il de-levering (la vol non scende) ma la perdita di tracking.
   Impatto sul book: zero -> REBAL_BAND_USD non toccato, si applica al deploy.

Aggiunto anche il bullet edge_watch, cablato il 26/07 e mai finito in CLAUDE.md.

Test: 56 nuovi, 504/504 verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-27 14:14:39 +00:00
Adriano Dal Pastro 3f0812c7fc research(gtaa): DEGIRO ha tutte e sei le gambe — verificato sul conto reale
Screenshot della watchlist "Pythagoras" su flatexDEGIRO: le 6 gambe ci sono tutte, coi
ticker esatti raccomandati. Era Revolut a non avere R2US.

VERIFICA INDIPENDENTE che le due linee EUR (VUAA, XNAS su Tradegate) siano gli stessi
fondi, dai dati e non dallo screenshot: il rapporto prezzo-IB/prezzo-Degiro dev'essere un
solo cambio -> 1.1341 e 1.1315, scarto 0.23%. Le altre 4 stanno a 0.993-0.998 (gia' USD).
Due fondi diversi non darebbero lo stesso cambio.

ERRORE MIO, dello stesso tipo che avevo codificato come regola un messaggio prima: per
cercare le linee in euro delle altre 4 gambe ho interrogato IB per TICKER sulle borse
tedesche, ottenendo "nessuna linea EUR" su 4/4. Falso. Cercando per ISIN ognuna ce l'ha:
ZPRR (=R2US), IS04 (=IDTL), EGLN (=IGLN, Londra EUR), IS0R (=IHYU). Un "assente" da una
ricerca per ticker su una borsa dove quel ticker non esiste non significa "non esiste".

TURNOVER PER GAMBA a $10k (21 ordini/anno): IDTL 9 ordini / $6.257 = 46% del totale,
poi VUAA 17%, IGLN 12%, XNAS 12%, IHYU 7%, R2US 6%. Il 71% del turnover e' su gambe in
USD ($9.752/anno) -> conversione $24/anno a 25bps. Spostare la sola IDTL sulla linea in
euro (IS04) copre il 64% del turnover convertibile.

Ma non e' un risparmio netto (spread Xetra piu' larghi delle linee primarie di Londra,
tariffa di connettivita' per borsa) e su $10k si parla di decine di dollari l'anno in
entrambe le direzioni: non e' una decisione importante, ed e' piu' utile dirlo che
costruire una precisione finta.

Il prompt W-8BEN di Degiro non riguarda queste sei: sono fondi irlandesi, non titoli USA.

Stato: preparazione, non azione (saldo Degiro EUR 328,92; GTAA01 richiede >=$3k e la
decisione venue tiene tutto su Deribit fino a $20k).

Book, pesi, cron, config INVARIATI. 448 test verdi (+1).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XBbYmiXqbUNuGpK9sfbsGp
2026-07-27 11:36:27 +00:00
Adriano Dal Pastro 378f448450 research(gtaa): ZPRR e' R2US (stessa ISIN) + correzione sul verso del costo FX
L'operatore ha verificato su Revolut: R2US assente, ZPRR e SPY4 presenti.

(1) ZPRR (Xetra EUR) == R2US (Londra USD): stessa ISIN IE00BJ38QD84, stessa classe di
quote, stesso NAV. La gamba small cap e' risolta. Regola: si cerca per ISIN, non per
ticker — lo stesso fondo ha ticker diversi su borse diverse.

(2) SPY4 IE00B4YBJ215 NON e' small cap ne' S&P 500: e' SPDR S&P 400 MID cap (l'S&P 500
e' SPY5). Misurato come ripiego su 6.5 anni: Sharpe 0.86 vs 0.86, corr fra i due sleeve
0.991, peggiore in 3/7 anni = moneta. Sulla finestra corta di 3.2 anni sembrava -0.15:
era rumore. Ripiego accettabile per ragione meccanica (small e mid USA correlano ~0.95
giornaliero), NON validato — e' proprio perche' non si distinguono che la scelta non
conta.

(3) CORREZIONE a un'indicazione data ieri. Avevo scritto "una linea in EUR aggiunge la
conversione per ordine". Vero solo per un conto in USD: per un conto in EURO vale
l'opposto. L'esposizione economica e' identica (il fondo detiene attivi USD, nessuna
delle due linee e' coperta) — la valuta di quotazione non copre nulla, decide solo se
serve una conversione. Regola giusta: prendere la linea nella valuta del proprio saldo.
Misurato: turnover lordo $13.655/anno su $10k -> 25bps = -0.07 Sharpe = $34/anno = ~$1.6
per ordine, contro una soglia di $18.90.

Regola generale: un costo di conversione non e' una proprieta' dello strumento ma della
coppia strumento-CONTO.

Book, pesi, cron, config INVARIATI. 447 test verdi (+3).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XBbYmiXqbUNuGpK9sfbsGp
2026-07-27 11:25:20 +00:00
Adriano Dal Pastro d0c804ebfc research(gtaa): l'assenza di API DEGIRO vale -0.02 di Sharpe, non e' squalificante
Domanda dell'operatore: "degiro ha api?". Fatto: no, non ufficiale; Revolut nemmeno
(la sua e' per pagamenti); IB si'. I wrapper non ufficiali girano su credenziali +
seed 2FA e si rompono IN SILENZIO a ogni cambio di front-end — e il progetto ha gia'
pagato quel prezzo con fresh_5m il 26/07. Un esecutore che puo' rompersi senza dirlo
e' peggio dell'esecuzione manuale.

Misurato il costo di NON automatizzare invece di discuterlo:
  carico operativo: 15 settimane/anno con >=1 ordine (29% dei controlli, 1.4 per volta)
  ritardo 1g  -0.02 Sharpe (peggiora in 6/11 anni = moneta)
  ritardo 3g  -0.13
  ritardo 10g -0.27

Il costo non e' il ritardo tipico ma la coda: il rischio dell'operativita' manuale e'
la dimenticanza, e si copre con un allarme, non con una API (gtaa_rebalance_plan esiste
gia' in produzione ed e' nato per un esecutore).

Nota di metodo: sulla finestra UCITS di 3.2 anni la curva del ritardo NON e' monotona
(5g -0.26, 10g -0.13) -> il campione corto non risolve differenze di questa taglia,
quindi il numero si legge sulla finestra lunga a 10 anni, dove lo e'.

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XBbYmiXqbUNuGpK9sfbsGp
2026-07-27 11:05:33 +00:00
Adriano Dal Pastro 842b0e865b research(gtaa): il numero di ordini e' un parametro — il costo smette di essere binding
Correzione dell'operatore: "io ho gia' Revolut e Degiro e li uso da anni, IB sono solo
iscritto". La raccomandazione di ieri (restare su IB) poggiava su "il conto esiste
gia'", che era falso. Il gateway IB serve solo per i DATI del segnale (basta il paper),
quindi il broker di esecuzione e' libero e la scelta si gioca solo sul costo per ordine.

(a) I 77-149 ordini/anno sono la conseguenza di REBAL_EVERY=5 / REBAL_BAND_USD=50,
scelti il 25/07 per il listino IB su azioni USA e a una taglia sola. A cadenza
settimanale allargare la banda NON costa: Sharpe a costo zero 1.27 ($50) -> 1.27 ($400)
con ordini 84 -> 23. Rallentare la cadenza invece costa (1.27 -> 1.12 mensile). La banda
filtra la deriva del vol-target, non il segnale di trend. Controllo fuori finestra: sui
veicoli USA su 10 anni lo Sharpe a costo zero perde 0.02 mentre gli ordini calano del
74% -> non e' un artefatto della finestra UCITS corta.

(b) MA la banda in dollari assoluti e' la parametrizzazione sbagliata: a $3.000 una
banda da $400 e' l'80% della gamba -> 3 ordini/anno, a mercato il 45% del tempo invece
del 66%, con Sharpe 0.71 ancora "accettabile". Null de-levering in veste nuova: non
travestito da meno drawdown ma da meno costi. Il controllo non e' lo Sharpe ma la quota
di tempo a mercato.

(c) Configurazione proposta: banda = 25% della gamba -> 21 ordini/anno a OGNI capitale,
esposizione 66% ovunque, soglia $5.65/ordine a $3k (contro $2.08 del canonico). Proposta,
non cambio di produzione: non passata per study_family_honest ne' deflated-Sharpe, e
GTAA01 non e' deployabile prima dei $20k.

(d) ISIN da contract details IB per la ricerca sul conto reale (VUAA/XNAS/R2US/IDTL/
IGLN/IHYU, tutti IE, Londra in USD). La valuta della linea conta piu' del broker: una
linea in EUR aggiunge ~25bps per ordine = ~0.15 di Sharpe.

Book, pesi, cron, config INVARIATI. 444 test verdi (+9).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XBbYmiXqbUNuGpK9sfbsGp
2026-07-27 06:01:01 +00:00
Adriano Dal Pastro be4690375f research(gtaa): la via UCITS e' aperta e costa ~zero — il broker non e' la variabile
Domanda dell'operatore: "usiamo revolut o degiro". Risposta misurata: cambiare
broker non sblocca nulla (il PRIIPs e' una norma, non una politica di IB); cambiare
VEICOLO si', e costa ~zero.

CORREZIONE A UNA MIA AFFERMAZIONE. La nota in gtaa.py diceva che gli UCITS fanno
perdere la validazione a 30 anni. Falso: il PRIIPs vieta di COMPRARE, non di
GUARDARE — i prezzi dei 6 ETF USA restano leggibili, quindi il segnale gira sui 30
anni per sempre e cambia solo il veicolo su cui si incassa.

Misure (3 lenti, un grado di liberta' per volta, 6.3 anni comuni):
  L0 segnale USA + rend. USA   Sh 0.81 / CAGR 3.96%
  L2 segnale UCITS + rend. UCITS Sh 0.84 / CAGR 4.08%
  drag del veicolo +0.10%/anno EW, coerente coi TER; ritenuta USA ~35bps a FAVORE
  dell'UCITS e non inclusa nel drag.

Lo stimatore ovvio sbagliava: la media delle differenze giornaliere dava -0.47%/anno
su CSPX contro -0.06% vero (SE ~7%/anno = 15x la quantita' stimata, piu' drag di
varianza). La deviazione fra veicoli sullo stesso indice si misura sul RAPPORTO
CUMULATO.

Il vincolo non e' il broker ma il prezzo di UNA azione, che e' una scelta: CSPX $802
vs VUAA $144 sullo stesso S&P 500. A $3.000 con azioni intere l'insieme STORIA tiene
4/6 gambe (a mercato il 33%), l'insieme DEPLOY 6/6 (65%) -> il frazionamento non
serve. Letto su gambe-vive+vol, non su Sharpe: il vincolo intero ALZA lo Sharpe
perche' de-leveraggia (null de-levering, 4a occorrenza).

Resta da verificare una cosa sola: 77-149 ordini/anno contro soglie $0.90 ($3k) /
$2.23 ($10k) / $7.62 ($50k) per ordine. Raccomandazione: restare su IB.

Feed equity: aggiunto il CROSS-CHECK che mancava (src/data/eq_crosscheck.py). Il
primo veicolo estero ha trovato subito CSPX 2012-01-13 con open/high in USD e
low/close in EUR (fattore 1.2797 = EURUSD del giorno), invisibile alla guardia
maxret>50% — stesso schema dello split 2:1 del 25/07. Soglia non tarabile sulla
deviazione (rumore 9.90%, margine 2.2x): cambiata statistica in |dev|/movimento del
gemello -> margine 5.3x. Limite EURUSD 1.09 dichiarato e chiuso sul DANNO (dSharpe
mediano -0.003), congelato in un test.

Book, pesi, cron, config INVARIATI. 435 test verdi (+24).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XBbYmiXqbUNuGpK9sfbsGp
2026-07-26 23:01:54 +00:00
Adriano Dal Pastro 6664575e1c ❌ GTAA01 NON deployabile: blocco PRIIPs CONFERMATO sul conto reale
Il rischio sollevato poche ore fa e' stato verificato tentando l'ordine. Il broker rifiuta:
"Trading limitato — Questo prodotto non dispone di un KID in inglese o in una lingua
approvata per il vostro Paese. I clienti retail possono negoziare prodotti retail
preconfezionati solo se e' disponibile un KID appropriato."

Non e' piu' un'ipotesi regolatoria: e' un rifiuto d'ordine documentato.
SPY/QQQ/IWM/TLT/GLD/HYG sono ETF domiciliati USA, gli emittenti non pubblicano il KID e i
broker UE ne vietano l'ACQUISTO al retail. ⚠️ Le QUOTAZIONI restano visibili — l'operatore
vedeva tutti e sei i prezzi in piattaforma, ed e' esattamente cio' che rendeva invisibile
l'assunzione.

COSA CADE: lo sleeve cosi' com'e' non e' deployabile, e con esso il piano di attivarlo a
~$13k. Restano valide come RICERCA e nulle come DEPLOY: validazione a 30 anni (22/06), fix
costi IB (25/07), GTAA_MIN_CAPITAL, e il LOO del 26/07 che lo indicava come l'unico sleeve
positivo nel 100% delle estrazioni su tutte e tre le metriche.

COSA NON CADE: tutte le traiettorie, i muri e le tabelle di rendita usano
book_series(with_gtaa=0) = solo TP01+SKH01 su Deribit -> nessun numero del piano va
rifatto. E il book live non lo include.

VIA D'USCITA (non percorsa): equivalenti UCITS. NON e' una sostituzione di ticker —
storia piu' corta (si perde la validazione a 30 anni, cioe' cio' che lo rendeva credibile),
ritenuta/TER/replica diversi (decine di bps su un CAGR del 3.65%), quotazione LSE/Xetra con
orari e valuta diversi da uno sleeve che decide sul close USA. Percorso onesto: validare
sull'INDICE e negoziare il VEICOLO, dichiarando tracking error e ritenuta come costi.

REGOLA: la negoziabilita' sul conto REALE va verificata quando lo sleeve entra in RICERCA,
non quando entra nel book. Cinque settimane di misure poggiavano su un'assunzione mai
controllata, e il controllo e' costato un ordine di prova.

Book, pesi, cron, config INVARIATI. 411 test verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 22:10:43 +00:00
Adriano Dal Pastro b3082de9af ⚠️ GTAA01: negoziabilita' degli strumenti MAI VERIFICATA (rischio aperto)
Domanda dell'operatore ("GTAA01 puo' essere in revolut?") che scopre un'assunzione mai
controllata in 5 settimane di lavoro sullo sleeve.

GTAA01 usa SPY, QQQ, IWM, TLT, GLD, HYG = ETF DOMICILIATI NEGLI USA. Sotto il regolamento
PRIIPs un investitore retail residente nell'UE tipicamente NON puo' acquistarli, perche'
gli emittenti USA non pubblicano il KID; i broker UE — Interactive Brokers incluso, che e'
esattamente il venue che lo sleeve assume — li bloccano in acquisto per la clientela
retail.

COSA POGGIA SU QUESTA ASSUNZIONE: i 30 anni di storia, il fix dei costi IB reali del
25/07, la soglia GTAA_MIN_CAPITAL $3.000, il contributo al book, e il risultato del LOO del
26/07 che lo indica come l'UNICO sleeve positivo nel 100% delle estrazioni su tutte e tre
le metriche. Nessuno di questi numeri e' sbagliato come backtest; quello che non e' mai
stato verificato e' se lo sleeve sia ACQUISTABILE dal conto reale dell'operatore.

DA VERIFICARE PRIMA DEL DEPLOY, non dopo. Se il blocco c'e' servono gli equivalenti UCITS
(CSPX/SXR8, EQQQ/SXRV, IUSN/CSUSS, DTLA/IDTL, SGLN/IGLN, IHYU), che sono strumenti DIVERSI
per domicilio, valuta, TER e replica -> rifetch dei dati e rivalidazione, non una
sostituzione di ticker.

SU REVOLUT nello specifico la domanda resta piu' stretta: universo ETF limitato, prodotto
retail leggero, e un ribilanciamento settimanale a 6 gambe con banda $50 non e' cio' per
cui e' pensato. Il confronto va fatto su esistenza degli strumenti e costo per ordine.

Nota permanente nel sorgente sopra EQ_UNIVERSE + bullet in CLAUDE.md.

REGOLA: la negoziabilita' di uno strumento sul conto REALE va verificata quando lo sleeve
entra in RICERCA, non quando entra nel book. E' l'analogo azionario di cio' che il progetto
gia' fa sul crypto (min-order, haircut small-cap, eseguibilita' a $600): la stessa
disciplina non era stata applicata all'equity.

Book, pesi, cron, config INVARIATI (GTAA01 non e' nel book live).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 22:01:26 +00:00
Adriano Dal Pastro dc4135a781 fix: le soglie della tabella anni contraddicevano la decisione venue
L'operatore ha chiesto "GTAA01 e XS01 sono in deribit?". No, e la domanda scopre
un'incoerenza in cio' che avevo presentato.

MAPPA REALE DEI VENUE:
  TP01, SKH01  -> Deribit          (gli unici LIVE)
  VRP01        -> Deribit opzioni  (paper: regola "niente short-vol da modello")
  XS01         -> Hyperliquid      (stat-mode, serve ~$20k sulla gamba)
  GTAA01       -> Interactive Brokers, 6 ETF azionari (paper)

L'INCOERENZA: la tabella anno-per-anno annotava "anno 1: GTAA01 entra nel book" e
"anno 8: XS01 eseguibile", ma attivare GTAA01 E' lo split di venue, e l'operatore ha
deciso il 2026-07-26 di restare 100% Deribit fino a $20k. Le due cose non stanno insieme:
sotto i $20k quelle attivazioni non avvengono.

COSA NON ERA SBAGLIATO: i NUMERI. `book_series(with_gtaa=0)` usa il solo book Deribit a 2
sleeve, quindi tutte le traiettorie, i muri e le rendite pubblicate NON assumono nessuna
delle due attivazioni — sono Deribit-only e coerenti con la decisione. Sbagliata era solo
la colonna di annotazione, che descriveva cio' che sarebbe POSSIBILE come se fosse
pianificato.

Etichette corrette: le soglie ora dicono "sarebbe eseguibile ... ma la decisione venue dice
$20k", e i $20k sono marcati come il punto in cui GTAA01/XS01 diventano una SCELTA.

REGOLA: un'annotazione che descrive una possibilita' accanto a numeri che descrivono un
piano viene letta come parte del piano. Se una decisione registrata la esclude, va detto
nella riga stessa.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:57:59 +00:00
Adriano Dal Pastro 95f7fb30a3 fix: il massimo di una simulazione non e' una statistica della strategia
L'operatore ha contestato un numero che avevo citato io ("anno migliore +184%"). Aveva
ragione, e l'errore era di METODO, non di calcolo.

IL NUMERO E' VERO. Tracciato l'anno estremo: 18 blocchi da 20 giorni, nessuno
significativamente negativo (+20% +15% +12% +10% +8% ... -1%). La popolazione lo consente:
blocchi 20g reali con mediana -0.1%, p95 +8.5%, max +22.4%, skew +2.15 — firma classica di
un trend-follower. E la materia prima esiste: la miglior finestra 365g REALE e' +89.8%.

MA CITARLO ERA SBAGLIATO, perche' il massimo di N estrazioni cresce con N:
  su   1.000 anni simulati -> max  +96.0%
  su   5.000               -> max +135.2%
  su 114.000               -> max +184.3%
Il numero che avevo dato parlava del mio N_PATHS, non del book. Con 1.000 percorsi avrei
scritto +96% per la stessa identica strategia.

I NUMERI CORRETTI SONO I PERCENTILI: p1 -11.9% · p5 -5.5% · MEDIANA +16.0% · p95 +51.2% ·
p99 +71.8%. Vale simmetricamente per il "peggiore -27.4%", anch'esso minimo campionario (a
1.000 percorsi era -19.1%): la coda sinistra onesta e' p1 = -11.9%.

CABLATO: r0726_decadimento.py aveva lo stesso difetto ("drawdown PEGGIORE 44.2%") -> ora
stampa p99 = 26.0% e dichiara che il 44.2% e' un massimo campionario da non citare come
"il caso peggiore".

REGOLA: il massimo (o il minimo) di una simulazione e' una statistica del NUMERO DI
SIMULAZIONI, non della strategia. Si citano i percentili. Stessa famiglia dell'errore gia'
codificato oggi ("un percentile stampato a 0 decimali mente esattamente agli estremi"):
gli estremi sono dove i numeri sembrano piu' informativi e lo sono meno.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:49:45 +00:00
Adriano Dal Pastro 66b4b2b9c0 research: tabella anni parametrizzabile da riga di comando
"E con 1000 al mese?" non deve richiedere di modificare lo script: importo mensile e
versamento iniziale passano come argomenti. Modificarlo ogni volta significherebbe avere
due versioni dei numeri in giro senza sapere quale ha prodotto cosa.

  uv run python scripts/research/r0726_tabella_anni.py            # EUR 500/mese
  uv run python scripts/research/r0726_tabella_anni.py 1000       # altro mensile
  uv run python scripts/research/r0726_tabella_anni.py 1000 10000 # mensile + iniziale

EUR 1.000/mese: traguardo al capitale mediano all'anno 9 (2035) invece del 12; P(traguardo)
80% a 10 anni contro 16%. Il totale versato a 20 anni raddoppia ($270.917 vs $138.482).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:38:09 +00:00
Adriano Dal Pastro bdd9e60355 research: tabella anno per anno del piano (EUR 5.000 + 500/mese)
Mette in forma leggibile le misure di r0726_piano_5k500.py, anno per anno e con gli anni
di calendario, piu' tre colonne che mancavano e che servono a leggerla onestamente:
quanto hai VERSATO fino a quel punto (senza, il capitale sembra rendimento), la banda
p10-p90 (meta' dei percorsi sta fuori dalla mediana) e la soglia attraversata.

Traguardo EUR 50/g al capitale mediano: anno 12 (2038). P(traguardo) 16% a 10 anni,
53% a 12, 92% a 15, 99.9% a 20.

Il pezzo che conta: la quota di capitale che viene dal RENDIMENTO invece che dai
versamenti e' 10% al primo anno, 39% al quinto, 63% al decimo, 88% al ventesimo. I primi
anni si giudicano sui versamenti, non sui risultati — e' il motivo per cui il piano e'
fragile all'interruzione precoce (misurato: i primi 5 anni sono il 25% dei soldi e il 58%
del risultato).

Regola del progetto rispettata: un numero pubblicato deve avere uno script committato che
lo riproduce.

Ipotesi dichiarate in testa allo script: x0.89 misurato, book live TP01+SKH01, fisco 33%,
NESSUN rischio di venue e NESSUN decadimento dell'edge (misurati in r0726_venue_risk.py e
r0726_decadimento.py, da leggere insieme a questa).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:35:37 +00:00
Adriano Dal Pastro 95caeb87da feat(live): allerta sul salto di equity — conferma il versamento, segnala un prelievo
La verifica "il cap si adegua?" esisteva solo come sorveglianza di sessione, e il
versamento slitta di giorni: una verifica che vive in una chat non e' una verifica. Resa
permanente e generalizzata.

`write_equity_watermark` ora ritorna {prev, new, pct} quando il salto fra due letture
consecutive supera EQUITY_JUMP_ALERT = 10%; `book_report` lo espone come `equity_jump` e
`book_execute` manda un Telegram con il NUOVO DIMENSIONAMENTO accanto (cap/asset, nozionale
lordo, leva), cosi' il messaggio si legge senza aprire il repo.

Il book ha vol ~0.4%/giorno: un salto del 10% fra due giri orari non puo' venire dal
trading. Quindi l'allerta copre DUE casi con un meccanismo solo:
  - VERSAMENTO: conferma che e' atterrato e che il sizing lo ha seguito;
  - USCITA DI FONDI: un prelievo che non hai chiesto, o una perdita anomala. E' questo il
    caso che conta di piu', ed e' il motivo per cui la soglia e' a due code.

Prima lettura in assoluto -> nessun allarme (senza un "prima" non c'e' un salto).
Il watermark si aggiorna ANCHE quando allerta, o il cap resterebbe indietro (test cablato).

411 test verdi (+7). Strategia, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:23:28 +00:00
Adriano Dal Pastro e320e3c2ba merge: edge watch — criteri di kill pre-registrati per il book live 2026-07-26 21:14:53 +00:00
Adriano Dal Pastro a1b4416ac0 feat: EDGE WATCH — criteri di kill pre-registrati per il book LIVE
"Come faccio a capire se l'edge e' morto?" scopre un buco: il progetto ha gate di kill
pre-registrati per i CANDIDATI (DVOLSPREAD 24/10, XSR01 23/10, STATARB 27/09) e NESSUNO
per il book che gira con soldi veri. La risposta implicita era "si vedra'", cioe' quello
che il progetto non accetta dai candidati.

LA RISPOSTA SCOMODA: non si puo' sapere in fretta. Sharpe rolling a 12 mesi: il 56% dei
casi "edge morto" e' indistinguibile da uno vivo. Un anno brutto e' rumore, non
informazione.

CRITERIO A (ritorno, book intero): Sharpe rolling 36 mesi sotto -0.5. Tarato sul nullo
(edge intatto) -> falso kill 1.8% in 10 anni; controllo positivo (edge morto) -> lo
riconosce nel 91% dei casi, rilevamento mediano 3.8 anni. La lentezza non e' un difetto
della regola ma statistica: a 12 mesi la stessa regola ucciderebbe un edge VIVO nell'80%
dei casi. Non esiste una versione veloce e onesta.

CRITERIO B (TP01, che e' DIFENSIVO): serve un criterio diverso perche' il LOO del 26/07 ha
misurato il contributo hold-out di TP01 negativo nel 99.1% delle configurazioni d'ancora —
firma dell'assicurazione, che paga premio negli anni senza incendio. "Non ha guadagnato"
NON e' evidenza di morte. Criterio: in un anno con DD buy&hold > 10%, il DD di TP01 deve
restare sotto il 75%. Storico 8 anni di sinistro, 8/8 superati (protezione 1.8x-34.4x).
Negli anni SENZA sinistro il criterio non si valuta: non c'e' informazione. Questo criterio
e' VELOCE dove l'altro e' lento.

COSA SUCCEDE SE SCATTANO (dichiarato ora per non deciderlo nel momento sbagliato):
(A) il book NON si spegne da solo -> revisione con weights_tilt_null + deflated-Sharpe sui
dati nuovi; spegnere e' decisione dell'operatore. (B) fallito in DUE anni di sinistro
consecutivi -> TP01 non assicura piu' e il peso 75% va rimesso in discussione.

CABLATO: scripts/live/edge_watch.py in cron_daily.sh, allerta Telegram, non tocca
l'esecuzione. Stato oggi: Sharpe 36m +1.51, protezione 8/8.

IL LIMITE, DETTO: il criterio A rileva la morte ~4 anni dopo, e non e' riparabile con una
regola migliore (e' il contenuto informativo dei dati). La difesa vera e' che il piano
regge a un edge dimezzato (11.6 -> 15.8 anni, P(20a) ancora 77%) e che i rischi VELOCI
(venue, esecuzione, feed) hanno sorveglianze che scattano in ore.

404 test verdi (+11). Book, pesi, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:14:53 +00:00
Adriano Dal Pastro 1296fa2d96 research: "dai per scontato che non perdiamo mai?" — meta' infondata, meta' e' il punto piu' debole del piano
Obiezione dell'operatore, presa sul serio. Due parti con risposte opposte.

PARTE 1 (infondata): le perdite SONO nel modello. Il block bootstrap ricampiona i ritorni
reali a blocchi di 20 giorni e conserva la forma dei drawdown. Serie reale: 35.6% giorni
in perdita, 27.5% flat, 36.9% in guadagno; giorno peggiore -3.94%, peggior mese -5.76%.
Sui 5.000 percorsi: maxDD mediano 14.4%, p90 19.8%, PEGGIORE 44.2%; anni-calendario in
perdita 5.8% su 95.000 anni simulati.

⚠️ ERRORE MIO CATTURATO PRIMA DI PUBBLICARE: la prima stesura diceva 63.9% di giorni in
perdita. Artefatto — il de-luck sottrae una costante a OGNI giorno (e' cosi' che riduce il
drift lasciando la vol invariata, come prescrive la misura d'ancora), quindi trasforma il
27.5% di giorni FLAT in piccoli negativi. REGOLA: una correzione uniforme sul drift e'
giusta per le domande sul drift e sbagliata per quelle sulla distribuzione — la stessa
serie dice 36% o 64% a seconda di quale si guarda, senza che sia cambiato niente.

PARTE 2 (coglie il punto): l'assunzione ottimista c'e' ed e' che l'EDGE CONTINUI A
ESISTERE per vent'anni. Il bootstrap assume che il futuro sia il passato rimescolato;
nessuna parte del progetto misura il decadimento dell'alpha. Misurato ora:
  edge intatto            -> 11.6a, P(20a) 99.9%
  edge dimezzato          -> 15.8a, P 76.6%
  decade a zero in 20a    -> 14.3a, P 65.5%
  decade a zero in 10a    -> oltre 20a, P 18.4%
  morto dall'anno 10      -> oltre 20a, P 42.0%
  morto dall'anno 5       -> oltre 20a, P 0.0%
Il piano NON e' fragile a un dimezzamento dell'edge, lo e' alla sua morte. E i due casi
non sono distinguibili in anticipo: e' la ragione per cui esistono i gate pre-registrati.

IL LIMITE STRUTTURALE: il peggior BIENNIO dell'intero campione e' +3.0%, cioe' POSITIVO.
Sette anni di storia crypto contengono due tori: un decennio davvero brutto non e' mai
successo, quindi il bootstrap non lo puo' estrarre. Se i 20 anni fossero tutti come quel
biennio, P(traguardo) 2.9% e capitale finale $149.014 contro $136.847 versati — il piano
non fallirebbe, semplicemente non renderebbe. Non e' un parametro da alzare: non si puo'
simulare un regime peggiore di qualunque cosa ci sia nel campione.

Book, pesi, piano INVARIATI. Cambia cosa si sorveglia.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 21:06:53 +00:00
Adriano Dal Pastro 28b63cf3a3 test: isola il watermark nei test del book (leggevano lo stato di produzione)
Il commit precedente e' stato pushato con un test rosso: la catena `&&` leggeva l'exit
code di `tail`, non di pytest. Errore mio, riparato qui.

LA CAUSA E' PIU' SERIA DEL TEST. `test_cap_falls_back_to_fixed_on_eq_fallback` falliva
perche' `_write_cfg` isolava la CONFIG ma non il nuovo watermark: i test leggevano
`data/live/equity_seen.json` REALE, quindi il loro esito dipendeva da quanto c'e' sul
conto vero. Un test che non menziona il watermark cambiava risposta a ogni deposito.

`_write_cfg` ora monkeypatcha anche EQUITY_WATERMARK su tmp_path e accetta un parametro
`watermark` esplicito. Aggiunti due test sul comportamento nuovo:
  - fallback con watermark $596.92 e cap config $3.000 -> $298/asset, leva <= 1x;
  - fallback con watermark $6.047 -> $3.000/asset (il tetto di config).
Il test storico resta e ora documenta il caso "conto mai visto" -> taglia sicura.

393 test verdi (exit code verificato, non dedotto dal tail).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 20:56:03 +00:00
Adriano Dal Pastro 8b21d29e69 fix(dashboard): taglia del book letta dal conto, non cablata
Il cruscotto dichiarava "cap $300/asset · capitale reale ≈ $600" come testo fisso: sarebbe
diventato falso al primo deposito, sulla pagina che si guarda per capire cosa sta girando.
Ora legge equity reale + max_notional_per_asset_frac + disaster_sl_pct dalla config.

Reso dinamico solo il testo di stato del book LIVE. I $600/$2000 restanti in dashboard.py
sono i capitali d'inizio CONGELATI dei libri paper (forward-monitor): quelli devono
restare fissi o le serie perdono continuita'.

Verificato il percorso di ESECUZIONE: nessuna assunzione cablata sulla taglia da $600
(book.py / shadow.py / book_execute.py). Reso: "capitale reale $596.92 · cap $298/asset ·
disaster-SL on-book −30%".

391 test verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 20:53:57 +00:00
Adriano Dal Pastro b023cc2bdf fix(live): cap di fallback legato all'ultima equity osservata + cap config 300 -> 3000
L'operatore ha autorizzato "si alza il cap a 3000". Verificato PRIMA di eseguire: il
deposito non era ancora arrivato (equity reale $596.92), e alzare il cap in quel momento
sarebbe stato pericoloso NEL VERSO OPPOSTO.

IL PROBLEMA. Quando l'equity reale non e' leggibile, shadow_report ripiega su paper_cap =
$2.000 NOMINALI, che non e' il conto vero: il sizing diventa 0.5 x 2000 x (...) = fino a
$1.000/asset, e il cap fisso e' l'unica cosa che impedisce a quel nominale di diventare
leva reale.
  cap $300  -> fallback $600 lordi su $597 = 1.00x  OK
  cap $3000 -> fallback $2.000 lordi su $597 = 3.35x  NO
Cioe' il cap sarebbe stato troppo alto proprio nel momento in cui non si sa quanto c'e'
sul conto, e con disaster_sl_pct -30% quella e' la configurazione peggiore possibile.

LA CORREZIONE. Invece di alzare un numero da ricordare, il cap di fallback e' legato al
conto: cap_fallback = min(cap_fisso_di_config, ultima_equity_reale_osservata * frac), con
watermark in data/live/equity_seen.json scritto da book_report ogni volta che l'equity
reale e' leggibile. Il cap di config torna a essere un TETTO DICHIARATO.
Senza watermark (primo avvio, file cancellato) -> CAP_UNKNOWN_USD = $300: non si sa niente
del conto, si usa la taglia storicamente sicura.

VERIFICATO SUL CONTO VERO, nei due regimi:
  oggi, watermark $596.92    ->   $298.46/asset = leva 1.00x
  dopo il versamento, $6.047 -> $3,000.00/asset = leva 0.99x
Sicuro in entrambi gli ordini di eventi, senza dipendere da un'azione manuale al deposito.

Questo CHIUDE l'azione pre-registrata il 2026-07-02 ("al deposito alzare il cap a
equity/2"), rimasta ineseguita per 24 giorni — non eseguendola, ma rendendola non
necessaria.

REGOLA: un parametro di sicurezza che va aggiornato a mano a ogni cambio di scala e' un
difetto, non una configurazione. Lo stesso numero era sbagliato in un verso prima del
deposito e nell'altro dopo: la soluzione non era scegliere il valore giusto, era legarlo
alla grandezza che lo determina.

Guardie: tests/test_cap_watermark.py (11), A DUE LATI — il cap non puo' ne' superare il
conto reale (leva nascosta) ne' restare sotto dopo un deposito (strozzatura).
Dry-run sul conto reale: cap/asset $298, book flat, nessun ordine. 391 test verdi (+11).

Strategia, pesi, cron INVARIATI. Cambia solo config/live.json e il calcolo del cap di
fallback.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 20:44:27 +00:00
Adriano Dal Pastro eb7c3af636 merge: piano 5k+500/mese + strozzatura cap post-deposito 2026-07-26 20:34:00 +00:00
Adriano Dal Pastro 1227b2baab research: il piano dichiarato EUR 5.000 + EUR 500/mese, e la strozzatura del cap
L'operatore ha dato i numeri veri: EUR 5.000 subito + EUR 500/mese. Cambia la scala
(conto da $597 a $6.047 = 10.1x), quindi ricalcolato in dedicata invece che estrapolato.

QUANDO: traguardo EUR 50/g ($272.061) a p10 9.4a / MEDIANA 11.6a / p90 14.4a;
P(entro 15a) 94%, P(entro 20a) 100%. Rendita mediana: EUR 6.37/g a 3 anni, EUR 11.57/g a
5, EUR 35.18/g a 10, EUR 87.63/g a 15.

VALIDAZIONE INCROCIATA: la variante "solo EUR 500/mese da $600" da' 12.4 anni = esattamente
il numero pubblicato il 25/07 con macchineria diversa.

IL LUMP VALE 0.8 ANNI (12.4 -> 11.6), MENO di quanto suggerisse il "fattore 6" del
calendario, e la ragione e' aritmetica: EUR 5.000 sono ~10 mesi di versamenti a EUR 500,
quindi comprano ~10 mesi. Anticipare vale in proporzione a quanto si anticipa. La mia
aspettativa era piu' alta ed e' corretta.

SOGLIE: $3k e $5k superate il giorno 1 (GTAA01 e XSR01 diventano eseguibili); $13k a ~0.9
anni (GTAA01 entra nel book deployable); $20k a ~1.6 anni = LA DECISIONE VENUE DEL 26/07
SMETTE DI ESSERE UN'IPOTESI E DIVENTA UNA DATA (~19 mesi); $117k a ~7.6 anni (XS01).
Le soglie superate subito NON autorizzano ad anticipare il gate XSR01 del 23/10.

CON IL RISCHIO DI VENUE: P(traguardo) 100% -> 88% a p=1% (P(perso tutto) 23.2%); a p=5% il
capitale mediano e' ZERO. Il piano regge fino a p=2%.

⚠️ AZIONE OPERATIVA TROVATA (non eseguita, e' config su soldi veri): `book._cap` ripiega su
max_notional_per_asset_usd=$300 quando l'equity reale non e' leggibile. A $597 il fallback
era INERTE (equity/2 = $298 ~ $300); dopo il versamento equity/2 vale ~$3.023, quindi un
fallback strozzerebbe il book al ~10% del target, in silenzio. E' l'azione gia'
pre-registrata il 2026-07-02 ("al deposito alzare il cap a equity/2"). Cablato
test_il_cap_fisso_diventa_una_strozzatura_dopo_un_deposito, che FALLISCE se si deposita
senza adeguare il cap.

Aggiunta anche la sezione (F) frontiera di sostenibilita' a r0726_deposits.py: capitale e
rendita per (importo x anni sostenuti), e il confronto "tirare poco tempo vs comodo a
lungo" — EUR 400/m per 5a batte EUR 200/m per 20a, ma EUR 600/m per 3a perde contro
EUR 250/m per 15a.

Book, pesi, cron, config INVARIATI. 380 test verdi (+3).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 20:34:00 +00:00
Adriano Dal Pastro d1cf44f874 merge: piano versamenti — interruzione, crescita, calendario, domanda inversa 2026-07-26 20:23:46 +00:00
Adriano Dal Pastro 4703f75f9f research: i versamenti — le 4 ipotesi che il piano non aveva mai fatto
Tutte le traiettorie del 25-26/07 assumevano versamento PIATTO, ININTERROTTO, PER SEMPRE:
l'ipotesi meno realistica dell'intero piano. Misurate le deviazioni che succedono davvero,
con la stessa macchineria (block bootstrap sui ritorni reali del book live, fattore
d'ancora x0.89 misurato).

(1) SMETTERE — il costo non e' proporzionale ai soldi mancanti. EUR 250/m per K anni poi
stop, orizzonte 20a: 3a ($10.410) -> $202.771 / P(muro) 32.7%; 5a -> $287.081 / 53.3%;
20a ($66.818) -> $496.778 / 90.0%. I PRIMI 5 ANNI SONO IL 25% DEI SOLDI E IL 58% DEL
RISULTATO -> un'interruzione al 12° anno costa poco, una al 3° quasi tutto. Argomento per
partire con un importo sostenibile invece che ambizioso.

(2) CRESCENTE E' PEGGIO DI PIATTO A PARI SOLDI. EUR 150/m +5%/anno versa EUR 67.998 ->
$401.889; piatto EUR 250 versa EUR 66.818 -> $496.778 = +24% con gli stessi soldi, solo
perche' entrano prima. Metrica giusta per confrontare piani di taglia diversa =
$ finale / $ versato (piatti 7.4x, crescenti 5.1-5.9x).

(3) STESSO TOTALE, CALENDARIO DIVERSO = FATTORE 6. EUR 60.000 distribuiti: ultimi 10 anni
$178.494 (11%) / piatto 20a $496.778 (90%) / primi 5 anni $1.104.587 (99.4%). NON
significa "versa tutto subito": un piano che non si sostiene non e' un piano.
Verificato COL RISCHIO DI VENUE DENTRO (il front-load mette piu' capitale sull'exchange
prima = proprio il rischio del giorno): REGGE, 2.22x -> 2.09x a p=2%, perche' il rischio
colpisce il tempo, non il calendario. MA a p=5% il capitale mediano e' $0 PER OGNI
CALENDARIO -> formulazione piu' netta del rischio di venue trovata finora: non erode il
piano, lo CANCELLA.

(4) LA DOMANDA INVERSA — rendita netta EUR/g mediana per versamento e orizzonte. EUR 150/m
-> 23.96/g a 15 anni; EUR 250/m -> 39.11/g a 15a e 91.30/g a 20a (P(EUR 50/g) 90%).
Riformula l'obiettivo: EUR 50/g e' UN punto sulla griglia, non l'unico risultato.
Non-linearita': da 15 a 20 anni la rendita piu' che raddoppia a ogni livello.

(5) FREQUENZA = la decisione meno importante. Mensile fino a ~$2/trasferimento, bimestrale
sopra; differenze 1-3% del capitale finale. Verificato che un deposito NON resta
strozzato: col cap dinamico cap = equity/2 = il nozionale massimo richiedibile.

ORDINE DI IMPORTANZA: versare o no (da mai a 16 anni) > quando (6x) > quanto presto si
smette (5 anni = 58% del risultato) > piatto vs crescente (24%) > frequenza (1-3%).

Book, pesi, cron, config INVARIATI. 377 test verdi (+12).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 20:23:46 +00:00
Adriano Dal Pastro e8ce60d41c merge: rivalutazione strategia — 75/25 confermato, nessun cambio 2026-07-26 20:06:23 +00:00
Adriano Dal Pastro 1dd26342ca research: rivalutazione della strategia — 0 cambi, 75/25 confermato per la terza volta
Delle sei misure prodotte oggi solo UNA apriva una decisione: il peso 75/25 fu
confermato il 24/07 con la lente HOURLY, e il 26/07 quella lente e' risultata
pessimistica su ENTRAMBI i lati di SKH01 (uscite +0.081, ingressi +0.048 di Sharpe di
book). Se SKH01 vale piu' di come e' stato pesato, 0.25 poteva non essere piu' l'ottimo.
Contro tirava il LOO de-luckato dello stesso giorno (SKH01 = il meno affidabile dei
cinque). Due correzioni in versi opposti: si misura, non si deduce.

MISURA (path live intra_entry=True, 8 offset, mediana delle differenze APPAIATE):
argmax a w=0.35, e 0.30-0.40 batte 0.25 nell'88% degli offset -> il segnale c'e' ed e'
nel verso previsto dalla correzione di lente. Ma il plateau entro 0.05 di Sharpe e'
[0.25 ... 0.50] e il peso live e' DENTRO, e `weights_tilt_null` FALLISCE
(delta_insample -0.0026, gate_pass False).

IL MOTIVO VERO sta in cio' che la mediana nasconde: il guadagno e' tutto nella coda ALTA.
p10 per peso 1.463 / 1.465 / 1.455 / 1.435 / 1.374 mentre il p90 sale monotono
1.915 -> 2.064. Alzare SKH01 non compra Sharpe, compra dipendenza da quale ancora ti e'
capitata (banda da 0.45 a 0.69). Coerente con altre due misure indipendenti dello stesso
giorno: SKH01 ha la frazione d'ancora piu' grande da restituire (LOO) ed e' 4x piu'
fee-sensibile. Tre misure indipendenti dicono che SKH01 e' la gamba fragile del book e
che 0.25 sta all'estremo prudente della regione robusta.

LA RIVALUTAZIONE CHE CONTA NON E' SULLA STRATEGIA. Ordini di grandezza a confronto:
ottimizzare il peso = +0.030 Sharpe (gate fallito); versare EUR 250/mese invece di EUR 0
= da MAI a 16.2 anni (P entro 20a = 92%); perdere il conto Deribit a p=1% = -18% di
probabilita' di arrivare, ripartendo da zero. Il book e' dentro il suo plateau su ogni
asse misurato: la ricerca ha smesso di essere il vincolo binding. I vincoli binding oggi
sono capitale che entra e conto che non sparisce.

Book, pesi, cron, config INVARIATI. Gate pre-registrati alle loro date (anticiparli
sarebbe selezione sull'hold-out). 365 test verdi (+6).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 20:06:23 +00:00
Adriano Dal Pastro 4450321a81 merge: venue watch — tripwire di fallimento exchange (100bps/4h, zero falsi allarmi in 8 anni) 2026-07-26 19:38:19 +00:00
Adriano Dal Pastro ab5bcace16 feat: VENUE WATCH — tripwire di fallimento exchange, cablato live
Risposta a "trova un sistema di protezione da fallimento exchange" SOTTO IL VINCOLO
della decisione appena presa (100% Deribit fino a $20k). Se non si puo' ridurre
l'ESPOSIZIONE, l'unica leva e' il TEMPO: il modello di rischio del mattino assumeva il
salto a zero istantaneo, ma i fallimenti reali non lo sono (Mt.Gox mesi, FTX ~72h, e
misurato qui: Bitfinex 2018-19 dislocato per 2.324 ore consecutive).

SEGNALE: un venue che gata i prelievi rompe l'ARBITRAGGIO -> il prezzo si stacca dal
consenso e ci resta. E' |scarto|, non il segno (Mt.Gox a premio, un venue in fuga a
sconto: stessa cosa). Consenso = venue USD indipendenti (Coinbase, Bitstamp), mai USDT.
Deribit sta a 3 bps dal consenso in mediana su 8 anni (65.043 ore BTC + 64.541 ETH).

TARATURA CONGELATA: 100 bps persistenti 4h a segno costante. Criterio DICHIARATO PRIMA,
perche' i due ovvi sbagliano in versi opposti (provati entrambi): "minimi bps" -> 25/24h
consuma 24 delle ~72h di FTX; "minime ore" -> 500/2h MANCA FTX (margine 0.6x). Regola:
zero falsi allarmi in 8 anni + margine >=3x sul caso storico piu' debole -> soglia
<=100bps -> poi minima latenza. Margine 3x FTX / 5x Quadriga / 10-20x Mt.Gox, zero falsi
allarmi con crash COVID, maggio 2021, LUNA e novembre 2022 inclusi.

CONTROLLO POSITIVO SUPERATO (un rilevatore tarato per non segnalare e' indistinguibile da
uno rotto): puntato su Bitfinex 2018-19 scatta 22 volte, episodio piu' lungo 2.324h a
+447bps. 22 dove il problema c'era, 0 su Deribit. E la durata risponde alla domanda vera:
un venue gated resta dislocato per settimane, quindi 4h di latenza sono trascurabili.

ECONOMIA: falso allarme = 0.248% atteso (flat 3g misurato sul book reale a ogni data
d'inizio); vero positivo = 100% salvato. Break-even p > (falsi/anno) x 0.00248: a 1 ogni
8 anni serve p > 0.031%. Il valore sta nella SPECIFICITA', non nella sensibilita'.

CABLATO: src/live/venue_watch.py (nucleo puro) + scripts/live/venue_watch.py, in
cron_book.sh PRIMA di book_execute (se Deribit e' in stress l'allarme deve partire anche
quando l'esecuzione fallisce per la stessa ragione). Tre stati OK/ALERT/BLIND — "non
vedo" non e' "va bene". ALLERTA, NON BLOCCA: l'azione e' prelevare (manuale; una chiave
con permesso di prelievo sarebbe essa stessa un rischio) e bloccare non protegge un saldo
che e' a rischio anche stando flat. Runbook pre-deciso nel docstring.

NON COPRE, e non e' un argomento per riaprire il 26/07: un fallimento SENZA finestra
(furto chiavi, sequestro, exit-scam) non lo prende nessun tripwire.

ERRORI CATTURATI IN SESSIONE:
- break-even calcolato sul p5 invece che sulla media (8.3x piu' severo, conclusione
  ribaltata);
- ipotesi meccanica sbagliata: credevo che i crash dislocassero a segno ALTERNATO. Falso,
  sono a segno costante anche loro (perp sotto spot per ore in cascata). A separare sono
  ampiezza e durata, non il segno;
- la prima corsa tronco' il campione da 8 anni a 29 GIORNI per un inner-join con Kraken
  (che serve solo ~700 candele) e la copertura era gia' stampata a video: una diagnostica
  stampata NON e' un controllo. Ora c'e' una guardia che ferma lo script. 2a occorrenza
  in un giorno dopo GTAA01;
- il controllo positivo era finito dentro il ramo `else` -> non girava mai, cioe'
  esattamente il difetto che doveva prevenire.

Book, pesi, config INVARIATI. 359 test verdi (+23).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 19:38:19 +00:00
Adriano Dal Pastro 0ec6f8b761 decision: concentrazione 100% Deribit fino a $20k (decisione dell'operatore)
L'analisi venue-risk di stamattina raccomandava lo split a ~$3k (GTAA01 su IB, 20-25%
fuori dal rischio-exchange). L'operatore ha deciso, DOPO aver visto la tabella della
rovina, di restare concentrato fino a $20k. Registrato con i termini espliciti perche'
non venga ri-litigato alla soglia dei $3k.

ACCETTATO: P(perso TUTTO) resta 10/18/34/64% a p=0.5/1/2/5% invece di 0/0/4/27%.
IN CAMBIO DI: ~EUR 0.08/g di rendita + commissione fissa IB + un secondo venue da
gestire, per proteggere $750 alla soglia dei $3k.

L'argomento dell'operatore REGGE sull'asse su cui ottimizza: sulla probabilita' di
ARRIVARE al capitale-rendita lo split vale +1-3pp (81% -> 83% a p=1%), fatto misurato
nella tabella del §2, non una concessione. L'argomento contro resta scritto: zero e'
ASSORBENTE (andare a zero all'anno 10 di un piano da 16 anni = non arrivarci piu', si
riparte da EUR 0 + versamenti), quindi il valore del non-andare-a-zero non e'
proporzionale alla frazione salvata.

SI RIAPRE a $20k, o PRIMA se cambia il piano (orizzonte/versamenti) o se `p` diventa
stimabile invece che assunto.

CORREZIONE A UN MIO SUGGERIMENTO, verificata nel codice: avevo detto "non lasciare su
Deribit piu' di quanto serve a girare il book". E' inerte — `src/live/book.py:81` fa
`raw = weight * equity * (...)` con equity = saldo reale del conto, quindi prelevare
$100 riduce il nozionale di $100 (1:1), non mette al sicuro $100. Tenere meno saldo a
pari nozionale richiederebbe di scollegare il sizing dal conto e usare il margine =
scambiare rischio-venue con rischio di liquidazione, oggi escluso dal cap a 1.0x.

Agli atti anche: "exchange FDIC" non esiste (FDIC = depositi bancari USD; la
pass-through di alcuni exchange copre solo il contante). Le protezioni reali sono SIPC
(IB: ETF/azioni = GTAA01, non le crypto via Paxos) e segregazione CFTC (CME, taglia
contratti inaccessibile a questa scala).

Book, pesi, cron, config INVARIATI. Nessun cambio di codice.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 19:14:15 +00:00
Adriano Dal Pastro dc60624772 merge: muro come punto fisso — previsione refutata, book deployable a 73.900 2026-07-26 18:58:20 +00:00
Adriano Dal Pastro 3a44171402 research: il muro come punto fisso — la previsione del follow-up era SBAGLIATA
Il follow-up dichiarato stamattina diceva: "i muri usano il book a 2 sleeve da $600
estrapolato a $272k; il book diversificato ha Sharpe piu' alto -> IL MURO VERO E' PIU'
BASSO". Misurato: FALSO. A pari nozionale il muro e' $273.900 contro i $272.061
pubblicati (+1%): l'estrapolazione col book a 2 sleeve era giusta PER CASO.

STRUTTURA: il muro e' un PUNTO FISSO — serve capitale C per girare il book che determina
il muro C, quindi si itera C_{n+1} = muro(book(C_n)). Converge in 1 iterazione perche' il
muro cade SOPRA la soglia XS01 ($117k) e la composizione non cambia; la struttura conta
solo se il muro atterra vicino a una soglia, ma va iterato per saperlo.

BOOK DEPLOYABLE (non il "migliore"): TP01 38 / SKH01 23 / GTAA01 23 / XS01 17. VRP01
escluso per regola permanente (niente short-vol da modello in deploy), XSR01 escluso per
gate pre-registrato 23/10. Costi capital-aware, fattore d'ancora x0.860 misurato su
QUESTO book. Sharpe 1.94, vol 8.9%, CAGR 18.3%.

PERCHE' NON SCENDE: diversificare alza lo Sharpe (1.64 -> 1.94) ma abbassa drift e vol
INSIEME, e la rendita perpetua vive sul DRIFT -> 10.91% -> 10.84%, invariata. Il guadagno
di Sharpe va in meno rischio, non in piu' reddito. E' il fatto gia' misurato il 25/07 §3,
dimenticato scrivendo il follow-up.

E STAVO VIOLANDO UNA REGOLA GIA' CODIFICATA: "un diversificatore a basso CAGR si giudica
a ISO-RISCHIO, mai a iso-nozionale" (25/07 §3). A iso-rischio (leva 1.28x): rendita
13.35%, muro $222.406 = -18% -> replica indipendente del -19% misurato il 25/07 con
macchineria e book diversi. Vale solo se la leva e' disponibile e a costo < uplift: $222k
e' un TETTO, non una stima.

BUG CATTURATO PRIMA DI PUBBLICARE: la prima corsa dava Sharpe 0.95 e muro $854k
("diversificare triplica il muro" — spettacolare e falso). CC.gtaa_banded ritorna la
storia GTAA dal 1996 mentre lo sleeve di produzione tronca a GTAA_BOOK_ACTIVATION; con la
rinormalizzazione per-riga di combine_outer il 75% del campione era GTAA01 DA SOLO al
100%. Preso non da un test ma perche' la somma pesata dei componenti (~18%) non tornava
col drift del combinato (6.8%). Diagnostica decisiva: la copertura per colonna
(TP01 24.6% / SKH01 24.6% / GTAA01 100.0% / XS01 8.6%).

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 18:56:07 +00:00
Adriano Dal Pastro 29626210e6 merge: fee Deribit 1 ago — curva misurata, book poco sensibile (-0.017 Sh/bps), nessuna azione
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 18:32:28 +00:00
Adriano Dal Pastro a937e3766f research: nuovo schema fee Deribit (1 ago 2026) — misurata la curva, nessuna azione oggi
L'annuncio (taker piu' bassi, maker rebate piu' bassi, soglie VIP abbassate, VIP7,
liquidation fee 1%, spot a zero) NON contiene numeri, e la tabella nell'articolo
Insights e' un'IMMAGINE: non letta da fonte primaria. I valori indicativi (base ~5bps
taker / 2bps maker, VIP7 2/0) vengono da un riassunto SECONDARIO ed e' dichiarato.

Quindi misurata la CURVA invece di aspettare il numero — vale per qualunque valore esca.
Le repliche parametrizzate riproducono BIT-EXACT gli sleeve di produzione alla fee
canonica (max|dif| = 0.0), altrimenti la curva descriverebbe un'altra strategia.

 bps/lato   %RT |  TP01 Sh | SKH01 Sh | BOOK Sh   CAGR
      0.0  0.00% |   1.322  |   1.567  |  1.849  21.69%
      3.0  0.06% |   1.303  |   1.495  |  1.799  20.99%
      5.0  0.10% |   1.290  |   1.446  |  1.766  20.53%   <- oggi
     10.0  0.20% |   1.258  |   1.324  |  1.682  19.39%
     15.0  0.30% |   1.226  |   1.200  |  1.597  18.26%

Sensibilita' del book: -0.017 Sharpe/bps, -0.23% CAGR/bps. Anche un RADDOPPIO del taker
costa 0.08 di Sharpe, MENO della banda d'ancora dello stesso book (2.222 -> 1.946): la
fee va messa nella sua scala di grandezza.

SKH01 e' ~4x piu' sensibile di TP01 (-0.69% vs -0.09% CAGR/bps: round-trip discreti vs
posizione continua vol-targeted) -> se il taker salisse, il primo parametro da rivedere
e' il peso 75/25.

REGOLA DECISA IN ANTICIPO (per non decidere col numero davanti): taker <=5bps/lato ->
non si tocca nulla; >10bps/lato -> rivedere il peso di SKH01.

Punti irrilevanti e perche': maker (il book manda ordini market; tocca solo la
raccomandazione T1 gia' non implementata); liquidation fee 1% (live.json da' nozionale
lordo max 1.00x l'equity con disaster-SL -30% -> servirebbe un movimento avverso ~100%);
VIP (a $600 il volume 30g e' trascurabile).

La conclusione sulla liquidation fee poggia sul CAP, non sulla strategia: cablata una
guardia di decisione (test_leva_massima_da_config_resta_sotto_o_uguale_a_1x) che ROMPE
se qualcuno alza il cap, invece di lasciarla valida per inerzia.

AZIONE 1 agosto: leggere il tier reale in Account Settings e applicare la regola sopra.

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 18:32:23 +00:00
Adriano Dal Pastro 0050ac4782 merge: rischio di venue prezzato — con un conto solo, 'un fallimento' = 'perso tutto'
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 17:57:58 +00:00
Adriano Dal Pastro 326229188a research: rischio di VENUE — mai prezzato, e non e' diversificabile dagli sleeve
Domanda dell'operatore: "tutto su Deribit?". Ha scoperto un buco, non un dettaglio.

IL BUCO. Il progetto ha prezzato con ossessione fee, slippage, min-order, pavimento IB,
haircut small-cap, fortuna d'ancora, degrado d'esecuzione, look-ahead, backfill, split
non aggiustati — e MAI la probabilita' che l'exchange sparisca col saldo dentro. E
TP01+SKH01+VRP01 stanno tutti sullo stesso conto: tre sleeve quasi-ortogonali sui
ritorni, PERFETTAMENTE CORRELATI sul fallimento del venue. La matrice di correlazione
del book non lo vede per costruzione.

LIMITE DEI MURI DEL 25-26/07 (dichiarato): book_series gira a alloc=$600 col book a 2
sleeve, quindi portarlo a $272k assumeva gia' "tutto su Deribit" senza dirlo — e
assumeva anche di girare il book da $600 a $272k (falso: a $3k GTAA01, $5k XSR01, $20k
XS01 -> il muro vero e' piu' basso).

LA MISURA (accumulo da $600, 250 EUR/m, 20a, bersaglio $272k, x0.89, jump di venue;
CONC = 100% Deribit vs SPLIT = Deribit 65 / HL 15 / IB 20; bersaglio identico ->
conservativo CONTRO lo split):

  p annua    P(arrivare) CONC / SPLIT    P(perso TUTTO) CONC / SPLIT
  0.5%              87% / 90%                    10% / 0%
  1.0%              81% / 83%                    18% / 0%
  2.0%              69% / 71%                    34% / 4%
  5.0%              42% / 45%                    64% / 27%

Capitale mediano CONC a 20a: $544k (p=0) -> $0 (p=5%).

LA COLONNA CHE CONTA NON E' LA PRIMA. Sulla probabilita' di ARRIVARE la concentrazione
costa 1-3pp; sulla ROVINA fino a 64pp. Motivo strutturale: con un conto solo "almeno un
fallimento" COINCIDE con "perso tutto". Lo SPLIT viene colpito 2.5x piu' spesso ed e'
molto piu' sicuro -> "quante volte vieni colpito" non e' una misura di rischio.

ONESTA': p NON e' stimato (sensibilita', non previsione); i fallimenti sono assunti
indipendenti, ottimistico per Deribit-HL -> la parte solida dello split e' IB, altra
classe di rischio; a $600 lo split e' impossibile, la concentrazione e' forzata.

RISPOSTA: no, ma la domanda ha una DATA. Prima soglia vera ~$3k (GTAA01 su IB). E
converge col 25/07: "max 25% su IB, COSTA ~0.08 EUR/g" era detto su basi di solo
rendimento; sull'asse della rovina quello stesso 25% e' la mossa principale — non e' il
prezzo di un peggioramento, e' il premio di un'assicurazione.

Incluse le aggiunte a r0726_capwall_refresh: drill-down 250 EUR/m e solve_deposit
(10 anni @P=90% = 1.178 EUR/m, $155.923 versati su $272k -> il rendimento fa il 43%,
contro il 77% a 20 anni). Bug catturato: il contatore dei versamenti si congelava al
traguardo mentre il capitale continuava a riceverli -> rapporto gonfiato (46x vs 25x a
30 anni); test di regressione cablato.

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 17:57:53 +00:00
Adriano Dal Pastro ff3ec6795a merge: traiettoria di accumulo col fattore de-luck corretto (€500/m: 19.6a -> 12.4a)
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 17:05:53 +00:00
Adriano Dal Pastro 825bf081f4 research: traiettoria di accumulo ricalcolata col fattore de-luck corretto
Il fattore agisce DUE volte e i due effetti pesano quasi uguale: alza il drift (si
accumula prima) E abbassa il bersaglio (il muro scende da $495k a $272k). Le colonne
li separano invece di sommarli alla cieca.

Mediana degli anni da $600 al capitale-rendita (block bootstrap, 3000 path, 25 anni):

  dep./mese   x0.60 muro $495k   x0.89 muro $495k   x0.89 muro $272k
              (25/07)            (solo drift)       (26/07)
     0        mai                mai                mai
     250      22.4a  (8% <20a)   19.6a  (53%)       16.2a  (91%)
     500      19.6a  (48%)       15.7a  (94%)       12.4a  (100%)
     1000     14.8a  (95%)       12.0a  (100%)       9.0a  (100%)
     2000     10.0a  (100%)       8.5a  (100%)       6.0a  (100%)

VALIDAZIONE: la colonna x0.60 riproduce ESATTAMENTE i numeri pubblicati il 25/07
(500/m -> 19.6a, 1000/m -> 14.8a) -> la replica e' fedele e le altre due colonne sono
confrontabili con quelle.

A 500 EUR/mese: dei ~7 anni guadagnati, ~4 vengono dal drift e ~3 dal bersaglio.

CIO' CHE NON CAMBIA: senza depositi il capitale-rendita non si raggiunge MAI (0% dei
path a 20 anni, a ogni fattore). L'accumulo viene dai versamenti, non dal rendimento:
correggere il x0.6 accorcia i tempi, non crea una via che non c'era.

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 17:05:49 +00:00
Adriano Dal Pastro 75713a5ec4 merge: follow-up SKH01 chiuso — de-luck onesto x0.87-0.91 (non x0.6), muro $495k -> $272k
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 16:55:06 +00:00
Adriano Dal Pastro 842420ce7b research: follow-up SKH01 chiuso — il blocco non esisteva, il de-luck x0.6 era troppo severo
Il follow-up "book sul path live" era fermo da tre sessioni su questa premessa:
"il simulatore compone per-trade a nozionale unitario, LO SLEEVE E' VOL-TARGETED".

LA PREMESSA ERA FALSA. Verificato in tre modi: _skyhook_returns chiama backtest_signals
con leverage=1.0/position_size=1.0; nessun target_vol/vol_target/realized_vol nel
sorgente; sim_equity(canonical) riproduce backtest_signals a max|diff| = 0.0. Il 20.7%
di vol realizzata dello sleeve e' un PRODOTTO della strategia (uscite % asimmetriche +
poco tempo a mercato), non un parametro: SKH01 e' l'unica delle 5 a NON essere
vol-targeted, il contrario di quanto si credeva. Test permanente cablato.

MISURA (ingressi live vs backtest, de-luckata su 8 offset a priori; sanity 120/120 bin
con ingresso ricostruiti):
- il numero del 26/07 era ~4x troppo grande: like-with-like (mediana PER-ASSET) +0.38 su
  3 offset -> +0.097 su 8, e "6/6 non negativi" -> 13/16. Sleeve 50/50: +0.112, 8/8.
- a livello di BOOK lo Sharpe e' una monetina (FULL +0.048, HOLD +0.051) ma il DRIFT e'
  +0.73pp positivo nel 100% delle estrazioni: l'ingresso intra-bin prende un prezzo
  migliore, i falsi ingressi aggiungono churn, vol e ritorno salgono insieme.

IL FATTORE x0.6 DECOMPOSTO E MISURATO:
  (a) fortuna d'ancora sul DRIFT: x0.874 (5-sleeve) / x0.890 (book live). La vol e'
      invariata fra le ancore (7.80->7.76%): la fortuna sta tutta nel drift.
  (b) path live: NON-NEGATIVO ovunque (uscite +0.081 Sh, ingressi +0.73pp, TP01 ~0).
Il x0.6 implicava un residuo x0.687 attribuito al live oltre l'ancora, che nessuna misura
sostiene -> FATTORE ONESTO x0.87-0.91, troppo severo del 31-34%. Il sospetto registrato
il 25/07 ("conta due volte la degradazione SKH01") e' confermato quantitativamente.

MURI DI CAPITALE ricalcolati con la stessa macchineria del 25/07: perpetua 6.00% ->
10.91%, muro per 50 EUR/g $494.758 -> $272.061 (-45%) a leva 1.0. La conclusione
STRUTTURALE non cambia: $272k restano ~453x il conto di oggi.

IPOTESI MIA REFUTATA nella stessa sessione: che la grid timing-luck di SKH01 fosse un
artefatto della lente a chiusura-di-bin. Dispersione LIVE/CANONICO = 1.59x -> il live e'
PIU' disperso. L'audit del 02/07 resta valido com'e'. (Nata su 2 offset, chiusa a 8.)

Trovato per strada: simulate() in r0726_skh_partial_entry.py non era mai chiamata da
main() — i numeri headline di quel diario venivano da una corsa mai committata.

Book, pesi, cron, config INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 16:55:01 +00:00
Adriano Dal Pastro 5e2b4bd308 merge: leave-one-out del book de-luckato — stima onesta FULL 1.95 / HOLD 1.54 / DD 6.85%
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 13:23:40 +00:00
Adriano Dal Pastro b9b2ef1b26 research: leave-one-out del book DE-LUCKATO sulle ancore — la classifica si ribalta
Domanda: "quale sleeve terrei?". Il leave-one-out ovvio e' misurato all'ancora canonica
di tutti e cinque gli sleeve, quindi NON e' credibile: un LOO e' un Delta, ed eredita la
fortuna d'ancora come ogni Delta (lezione 26/07, altlib.anchor_luck_delta).

Metodo: 2000 estrazioni uniformi indipendenti sullo spazio congiunto 24x10x7x23x5 =
193.200 configurazioni; book completo + 5 LOO alla STESSA configurazione; statistica =
mediana delle differenze appaiate. Sanity bit-exact 5/5 (max|dif| = 0.0) contro gli
sleeve di produzione. Quattro repliche ancorate riusate dagli audit 02/07-03/07, solo
la fase di GTAA01 e' nuova (ed e' l'unica coperta da test dedicato).

RISULTATI
- Livello del book: la stima a occhio del 02/07 era ottimista su 3/3 metriche.
  FULL 2.222 (97.0 pctl) -> 1.95 | HOLD 2.364 (99.6 pctl) -> 1.54 [1.11, 1.91] |
  maxDD 6.07% (12.0 pctl) -> 6.85%. Solo 9 estrazioni su 2000 battono l'hold-out canonico.
  La somma delle fortune marginali NON e' la mediana congiunta: sbagliava di +0.82 di Sharpe.
- SKH01 non e' il motore del book: l'ancora regala 2/3 del FULL, 70% dell'hold-out, 80%
  della protezione DD -> de-luckato e' il meno affidabile dei cinque.
- GTAA01 e' l'unico positivo nel 100% delle estrazioni su tutte e tre le metriche e il
  miglior protettore di DD. Ma attribuzione != eseguibilita': sotto $3k resta non deployabile.
- TP01 e' il maggior contributore (+0.390 FULL, 2000/2000) e il canonico lo SOTTOSTIMAVA.
  Il suo hold-out negativo non e' artefatto d'ancora (negativo nel 99.1%): e' la firma
  dell'assicurazione. Uno sleeve difensivo si giudica sul sinistro, non sul premio.
- XS01: protezione DD esattamente zero (positiva nel 43% = moneta) -> diversificatore di
  rendimento, non di rischio. VRP01: 2a conferma di zero fortuna (canonico all'1.8 pctl).

Corretto in sessione: un "pctl 100%" era arrotondamento di 99.55% con %.0f — un percentile
a 0 decimali mente esattamente agli estremi, che sono l'unico posto dove lo si legge.

Book, pesi, cron, config INVARIATI. Non e' un gate sui pesi (resta weights_tilt_null) e
non e' evidenza out-of-sample: e' attribuzione, de-luckata.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-26 13:23:36 +00:00
Adriano Dal Pastro 7453a29699 merge: ondata 26/07-bis — TP01 barra parziale + gate implausible_sharpe/anchor_luck 2026-07-25 22:36:40 +00:00
Adriano Dal Pastro 37be1df838 research: ondata 26/07-bis — TP01 su barra parziale + i 2 gate mai costruiti
0 sleeve nuovi. Book, pesi, cron, config INVARIATI.

T1 — anche TP01 legge una barra giornaliera PARZIALE nel live, ma non conta.
Stesso fatto strutturale di SKH01: resample_tf non scarta il giorno in corso e
current_target prende [-1]; il feed si ricostruisce alle 00:30 UTC, quindi per
tutta la giornata il book vede oggi come 1 barra oraria su 24 (verificato).
Il docstring "ultima barra CHIUSA" era falso: corretto.

Tre path a un grado di liberta' per volta, 24 ancore, differenze appaiate:
  barra parziale   ΔFULL -0.031 (pos 7/24)  ΔHOLD +0.118 (pos 19/24)
  ritardo 1h       ΔFULL -0.004 (pos 11/24 = moneta)
  leva LIVE/MODEL  1.004
-> trascurabile, nessun cambio al live.

All'ancora canonica sembra peggio del vero: a offset 0 la parziale costa -0.230
di hold-out, che e' il MINIMO della banda (mediana +0.118). Speculare alla
lezione del 26/07: li' l'ancora canonica nascondeva un vantaggio, qui inventa
un danno.

REGOLA: la parzialita' dell'ultima barra conta in proporzione a quanto il
segnale pesa la barra piu' recente. Donchian breakout su 230m (la barra corrente
E' il segnale) -> +0.38; TSMOM 30/90/180g -> ±0.03. Non si trasferisce.

T2 — implausible_sharpe e anchor_luck_band codificati in altlib (debito
raccomandato 3 volte e mai scritto), piu' anchor_luck_delta che codifica
l'errore di stamattina (mediana delle differenze appaiate, non differenza
delle mediane).

Il gate ha segnalato VRP01 e il difetto era MIO: perdite contate su tutte le
barre, ma VRP01 e' settimanale su griglia giornaliera (94.2% di zeri) -> "0.96%,
coda assente" su uno sleeve in produzione. Sulle barre ATTIVE e' 16.5%, la forma
giusta di un credit spread a rischio definito. La lezione era gia' cablata il
giorno prima nel monitor DVOLSPREAD ("barre attive, non giorni di calendario").

Applicazione retroattiva 7/7 tutti ok, con controlli positivi obbligatori
superati (firme CC01 e deep-OTM segnalate, rumore Sh 0.62 no).

Replica indipendente del finding d'ancora del 02/07: il gate applicato alla
cieca a TP01 ritrova canonica +0.237 = 92 pctl delle 24, mediana onesta +0.056,
fortuna +0.182 — contro mediana 0.04 misurata il 02/07 con implementazione
separata. L'hold-out onesto di TP01 e' ~+0.05, non 0.31.

NON fatto: il book ricalcolato sul path live, bloccato da incompatibilita' di
lenti (simulatore per-trade vs sleeve vol-targeted). Follow-up dichiarato.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 22:36:40 +00:00
Adriano Dal Pastro 6d0813a399 merge: misura ingressi SKH01 su barra parziale — non e' un difetto 2026-07-25 22:12:42 +00:00
Adriano Dal Pastro c8d31bc944 research(skh): misura dedicata sugli INGRESSI da barra 230m parziale
Chiude il follow-up dichiarato del 26/07 (misura T1). Il live valuta il segnale
a ogni giro orario del cron su una barra 230m mediamente completa a meta'; il
backtest solo a chiusura di bin. Domanda: di che segno e' il saldo.

Confronto di due path identici in tutto (livelli pct-asimmetrici, uscite
intra-barra, cap max_per_day, fee 0.10% RT) tranne quando si valuta l'ingresso.

  ΔSharpe (live - backtest), 3 offset x 2 asset:
    -0.01 / +0.04 / +0.44 / +0.32 / +0.59 / +0.98  -> 6/6 non negativi, mediana +0.38

Falsi ingressi ~5/anno/asset; cannibalizzano il cap 2-3 volte in 7 anni.
Meccanismo: Donchian breakout — aspettare la chiusura del bin fa pagare il
movimento gia' avvenuto (ingresso 0.25-0.26% peggiore), e su livelli percentuali
quello 0.26% vale il 6-13% della distanza dallo SL contro il 2.6-3.3% da quella
dal TP -> asimmetria a favore della sopravvivenza del trade.

Due attacchi superati:
  - il divario NON e' concentrato: togliendo i 5 giorni migliori si ALLARGA
    (ETH@460 35.6x vs 3.0x); e' il backtest il path concentrato;
  - nessun look-ahead intra-bin: troncando i 5m alle sole barre gia' chiuse la
    risposta e' identica in 289/289 osservazioni (test permanente). Serviva
    perche' il self-check valida solo a CHIUSURA di bin.

Verdetto: non e' un difetto da correggere, il verso e' lasciarlo. Ma live e
backtest girano due strategie diverse e la differenza non e' neutra: sommato
alla misura sulle uscite, il path live di SKH01 e' stato modellato in modo
sistematicamente pessimistico su entrambi i lati.

Book, pesi, cron, config INVARIATI.

Due errori di metodo catturati in sessione e codificati come regole:
  - un self-check su eventi rari si campiona sugli EVENTI (il primo dava
    "80/80 OK" confrontando zeri con zeri, con la ricostruzione rotta);
  - un conteggio su segnale grezzo non e' un conteggio di trade (sovrastima
    ~20x dei falsi ingressi ignorando cap e non-overlap del live).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 22:12:42 +00:00
Adriano Dal Pastro 36d3361075 merge: T1 non implementato (declassamento misurato) + sorveglianza freschezza feed SKH 2026-07-25 20:20:06 +00:00
Adriano Dal Pastro 031b71bf54 ops(live): sorveglianza freschezza feed SKH + correzione dei docstring sulla latenza d'uscita
T1 (TP di SKH01 come limit resting on-book) NON e' stato implementato, per misura.
Leggendo il codice di produzione: TP01 e SKH01 tradano lo stesso strumento con una
sola posizione netta Deribit, quindi un ordine on-book al livello di SKH chiuderebbe
anche quota TP01. Misurati i due ostacoli: (A) segno compatibile nel 97% dei trade
che escono in TP = risolvibile; (B) divergenza modello/live apparentemente bloccante.

Ma (B) non esiste: resample_5m NON scarta il bin 230m in corso (21 barre 5m su 46
nell'ultimo bin) e _skyhook_positions ci itera dentro -> il live rileva gia' SL/TP
intra-barra, entro ~1h dal tocco. I docstring che dicevano "usa solo barre chiuse" e
"latenza fino alla chiusura della barra 230m" erano FALSI e hanno guidato tre analisi
(02/07, 24/07, T1). Corretti sul posto.

Conseguenza: la lente `hourly` sottostima il path live di +0.081 Sharpe FULL di book
(23/23 offset, banda appaiata); il live vero sta sopra il canonical sul FULL, e il fix
richiesto sarebbe un declassamento (+0.054 vs +0.081) in cambio di ordini parziali sul
netto in un percorso con soldi veri.

Cablato invece il problema vero trovato per strada: fresh_5m fallisce in SILENZIO
(fallback al certificato, rigenerato 1x/giorno) -> la latenza d'uscita di SKH01 passa
da ~1h a ~1 giorno senza segnalazione, e nessun controllo esistente scatta (il gate di
staleness guarda il feed di TP01). Stesso schema del feed-freeze del 14/07.

  * livefeed.feed_age_minutes: pura, eta' dalla CHIUSURA della barra, None = non
    misurata, clamp sugli skew d'orologio
  * book_report espone skh_feed_age_min (max fra gli asset)
  * book_execute stampa lo stato e allerta su Telegram sopra skh_feed_max_age_min (30m)

Scelta dichiarata: ALLERTA, NON blocca. Bloccare fermerebbe anche TP01 (nettato sullo
stesso strumento) per un guasto di rete; forzare SKH flat chiuderebbe posizioni buone
su un glitch.

Follow-up dichiarato: la stessa barra parziale tocca gli INGRESSI (ent[n-1] da breakout
non confermato). Disaccordo in 1 bin su 112, ma con 3 entry nel campione la taglia non
e' stimabile. E' un cambio di strategia, non di strumentazione -> misura dedicata prima.

Strategia, pesi e cadenza del cron INVARIATI. Nessun ordine inviato. Suite 266 verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 20:20:01 +00:00
Adriano Dal Pastro 4b2de1ce87 merge: forward-monitor DVOLSPREAD cablato nel cron con gate pre-registrato 2026-07-25 20:05:33 +00:00
Adriano Dal Pastro 841f48c319 ops(live): cabla il forward-monitor DVOLSPREAD nel cron + gate pre-registrato
Chiude la lezione (c) dell'ondata 26/07: "un lead in forward-monitor senza
monitor e senza scadenza e' un lead perso" — DVOLSPREAD era in limbo da 35
giorni. Ora ha config congelata, monitor nel cron e gate con data.

Config congelata = la cella scelta IN-SAMPLE (zwin=180 k=2.0 lw=0.6 zw=1.1
tgt=0.17 svw=60), NON quella pubblicata dall'agente: quella era 83a/729
sull'hold-out ma 471a/729 in-sample e fallisce il deflated-Sharpe (0.947),
la congelata lo passa (0.953). Riusa make_book di r0726_dvolspread_gate,
nessuna reimplementazione.

Strumentazione specifica: il book va flat quando manca il DVOL, quindi un feed
rotto produrrebbe zeri che contati come evidenza direbbero "nessuna perdita"
invece di "nessuna misura". Contabilita' a 3 stati (attive / flat-da-segnale /
flat-senza-dato), finestra misurata in barre ATTIVE, e guardia che esce 1 se
FROZEN diverge dallo stato salvato.

Gate pre-registrato: kill 2026-10-24 se Sharpe < -0.50; decisione 2027-01-24
solo se Sharpe>0 E marginale ADDS E deflated-Sharpe>=0.95 E weights_tilt_null;
veto d'integrita' se barre attive <80% (si estende, non si decide su dati
mancanti). La soglia su Sharpe e' debole di proposito: con ~180 barre
SE(Sharpe)~1.4, una soglia alta sarebbe finta precisione.

Inception 2026-07-25, apertura +0.184 = $111/gamba (cap $300).
Book/pesi INVARIATI. Suite 255 verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 20:05:30 +00:00
Adriano Dal Pastro 444c251e3b merge: ondata 2026-07-26 — degrado SKH01 de-luckato, DVOLSPREAD promosso, XSR01 crypto-specifico 2026-07-25 19:51:58 +00:00
Adriano Dal Pastro 2c3882b60c research(wave): ondata 3 filoni — esecuzione SKH01, DVOLSPREAD, XSR01 fuori dal crypto
Tre questioni che il progetto aveva lasciato aperte e decidibili oggi.

T1 — ESECUZIONE SKH01. Testato l'unico meccanismo che non e' un cron: ordini
resting on-book (TP=limit al livello per costruzione + fee maker, SL=stop-market).
A offset 0 recupera il 94% del degrado, ma l'audit 02/07 aveva de-luckato i
numeri headline di SKH01 e NON il degrado. Sulla banda appaiata dei 23 offset il
degrado recuperabile e' +0.054 Sh di book, non -0.35 di sleeve.

Errore di metodo corretto in sessione: mediana(A)-mediana(B) fra offset confronta
offset diversi; serve la mediana delle DIFFERENZE appaiate. Col fix il verdetto
si ribalta: solo TP a limite = +0.054 FULL / +0.061 HOLD, positivo in 19/23 e
21/23 offset; lo SL on-book PEGGIORA (mediana -0.010, positivo in 11/23) perche'
cristallizza la perdita mentre l'exit ritardata incassa il rimbalzo.
Raccomandazione NON eseguita: TP a limite si, SL strategico on-book no.

T2 — DVOLSPREAD esce dal limbo (fermo dal 21/06). Passato ai due gate che allora
non esistevano. La griglia dichiarata "72 celle" ne contiene 729: valutate tutte.
Plateau reale (729/729 hold-out positivo). Selection-on-holdout confermata ma
mite: cella pubblicata 83a/729 sull'hold-out, 471a/729 in-sample. Cella onesta
FULL 0.68 / HOLD 0.69 (non 0.93) e DSR 0.953 PASS; la pubblicata fallisce 0.947.
Promosso a forward-monitor coi parametri onesti, NON nel book (hold-out attivo
1.6 anni, DSR sul filo, weights_tilt_null mai affrontato).

T3 — XSR01 non generalizza. Meccanismo congelato su 9 settoriali (1998+) e 28 ETF
(30 anni), versione DEMEANATA (il test del 25/07 era a coppie). Lordo +0.24
p=0.193 e -0.14 p=0.747 vs null a fee zero. Il risultato che conta e' l'ampiezza:
il demean fa 4.5->37.4 (8x) sul crypto ma 5.3->6.2 (1.2x) sulle azioni, perche'
sul crypto il residuo-vs-BTC lascia un enorme fattore comune e sulle azioni il
residuo-vs-SPY e' gia' indipendente. XSR01 e' crypto-specifico; NON e' falso.
Soglie del gate 23/10 non toccate.

Book/pesi/cron INVARIATI. Suite 245 verdi.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 19:51:52 +00:00
Adriano Dal Pastro 8b4c698ad9 merge: lente wick accoppiata — follow-up 25/07 chiuso, raccomandazione funded 0.50x->0.75x 2026-07-25 19:30:10 +00:00
Adriano Dal Pastro 4cb82dc474 research(prop): lente wick ACCOPPIATA — chiude il follow-up dichiarato del 25/07
La scala di conti funded era giudicata con due lenti a un ordine di grandezza di
distanza su P(>=50 EUR/g): 20.7% close-only vs 1.6-2.5% wick indipendente. Il
difetto era dichiarato (gap estratto indipendente dal rendimento del giorno) ma
il recon accoppiato esisteva solo per il book 75/25.

Qui si generalizza: sleeve TP01/SKH01 separati a risoluzione oraria (minimo
intraday esatto per qualsiasi vettore di pesi) + XS01 accoppiato dagli OHLC
giornalieri HL (recon = sleeve ufficiale a max|delta|=0.0).

FINDING: la calibrazione del wick era giusta, l'errore era l'INDIPENDENZA. Le
marginali coincidono (p50 -0.17pp identico) ma il gap e' ~3x piu' profondo nei
giorni che finiscono BENE (-1.58pp vs -0.48pp), perche' un giorno brutto chiude
sul minimo (m==R nel 26% dei giorni). Il breach si valuta sul minimo -> la lente
indipendente raddoppia i breach da daily-loss (2.0-2.9x, misurato sui giorni
storici). close-only non e' conservativa ma CIECA: 0.00% di breach ovunque.

Verifiche: (1) 1h vs 5m identici (p99 -3.06 vs -3.14pp) -> il caveat di
risoluzione del 24/07 e' trascurabile; (2) riconciliazione col 24/07 RISOLTA
(63.2% vs 58% sulla stessa finestra: non era la finestra, era la lente);
(3) bound severo su XS01 non ribalta config B.

Decisioni: funded 0.75x (non 0.50x — massimizza il payout a 3 anni, $2674 vs
$1230); scala P(>=50/g) ~6% con P(zero) 52-65%; ordine fra politiche invariato
a tutte e 3 le lenti. Book/pesi/cron INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 19:30:03 +00:00
Adriano Dal Pastro 8831c3ff38 merge: fix GTAA01 — costo IB a pavimento fisso + esecuzione a banda 2026-07-25 17:25:06 +00:00
Adriano Dal Pastro 607cd94ecd fix(gtaa): costo IB reale (pavimento fisso) + esecuzione a banda — lo sleeve era cieco al capitale
DIFETTO. src/portfolio/gtaa.py modellava il costo come 2bps PROPORZIONALI e il modulo si
dichiarava "eseguibile a basso capitale, switch mensile/basso turnover". Entrambe false:
il vol-target e' CONTINUO (l'esposizione cambia ogni giorno, su 6 gambe) e IB non ha una
fee proporzionale ma un PAVIMENTO FISSO per ordine, min(max($0.35, $0.0035/az), 1% del
controvalore) = ~$530/anno indipendenti dal capitale.

Il modello vecchio era quindi CIECO AL CAPITALE: dava Sharpe 0.64 sia a $50.000 sia a $600.
Alla taglia grande era sostanzialmente giusto (0.64 vs 0.59-0.66 reali); a $600 la realta'
e' -0.55 di Sharpe e -3.5%/anno di CAGR. L'errore era tutto concentrato dove lo sleeve
verrebbe realmente deployato.

FIX. Il modulo ora:
  * modella la commissione IB reale (ib_commission);
  * esegue a BANDA + CADENZA (settimanale, $50/gamba) — config scelta sul PLATEAU del sweep
    (weekly/monthly x banda 25-100 -> Sh 0.45-0.64 a ogni capitale), non sull'argmax
    in-sample (banda $50 daily a $600 = cella isolata che crolla a banda 100);
  * prende il CAPITALE allocato come parametro: gtaa_returns(capital=...);
  * dichiara la soglia di deployabilita': GTAA_MIN_CAPITAL=$3.000 + gtaa_is_deployable();
  * espone gtaa_rebalance_plan(held, capital) per l'esecutore — salta le gambe il cui
    nozionale non supera la banda (un ordine da $12 costa $0.35 = 2.9%).
sleeves.py dichiara esplicitamente il capitale assunto (GTAA_DEFAULT_CAPITAL=$10.000 allocati
= book ~$50k al peso 20%) invece di nasconderlo.

IMPATTO SUL BOOK (misurato sostituendo la sola gamba GTAA, non citato):
  GTAA01 standalone  Sh 0.64 -> 0.61   CAGR 3.76% -> 3.65%
  book 5 sleeve      FULL 2.22 -> 2.22  HOLD 2.36 -> 2.38  maxDD 6.2% -> 6.0%
Trascurabile alla taglia assunta: il fix conta per il DEPLOY (a $600-2k passa da -3.5%/anno
a +3.0%/anno). PESI INVARIATI -> nessun weights_tilt_null richiesto.

CORREZIONE A UN ERRORE DI ANALISI DELLA SESSIONE. Il diario citava il modello vecchio a
"Sharpe 0.77 / CAGR 5.5%": artefatto di annualizzazione: la serie GTAA grezza ha ~252 barre
/anno (soli giorni di borsa) e metrics() annualizza a 365 con years=n/365.25 -> Sharpe x1.20
e CAGR x1.45. Le righe per-capitale erano gia' su calendario 365, quindi era falsata solo la
riga di riferimento. Corretti diario, CLAUDE.md e r0725_capcurve.py.
LEZIONE: una serie su giorni di borsa non si passa a metrics() senza to_daily().

Test: 221 pass (+4 in tests/test_gtaa_sleeve.py: pavimento non proporzionale, dipendenza dal
capitale + soglia, senza-banda-e-distruttivo, piano che salta le gambe sotto banda).
Smoke: scripts/live/paper_combo.py gira invariato.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 17:25:06 +00:00
Adriano Dal Pastro 3266f3a09a merge: ondata rendita 2026-07-25 — curva capitale, muro della rendita, asimmetria funded, HyroTrader 2026-07-25 17:18:24 +00:00
Adriano Dal Pastro 6f64845aa9 research(hyro): HyroTrader nello specifico — consistency 40% refutata, DD 6% e' il vincolo
Addendum all'ondata rendita, su richiesta dell'operatore ("e hyrotrader").

CONSISTENCY 40%: ipotesi REFUTATA. Avevo previsto una tagliola (SKH01 ha P&L a scalino,
TP01 fa strappi di trend). Misurato: costo ~0pp a ogni leva e in entrambe le lenti,
perche' il book accumula il 10% in 130-300 giorni -> nessun giorno si avvicina al 40%
del cumulato. Prima di dichiararlo ho dovuto PROVARE che il controllo funziona (un
"costo 0" puo' essere un bug): su un book con profitto concentrato in 1-2 giorni la
regola porta P(pass) da >90% a <5%. Due iterazioni di test prima di avere un
discriminante valido (strappi ripetuti si diluiscono; sim_eval fa block-bootstrap,
non replay).

IL VINCOLO VERO E' IL maxDD 6% STATICO. Config A (book live TP01/SKH01) ha maxDD 9.5%
> 6% = strutturalmente incompatibile a leva piena: intraday a 1.0x sopravvive l'1.4%.
Config B (+XS01) ha maxDD 6.2% e Sharpe 1.13.

RACCOMANDAZIONE: config B a leva funded 0.50x (intraday P(vivo) 71% vs 32% a 0.75x;
E[payout] €7.69 vs €8.66/g — la sopravvivenza COMPONE su piu' anni, un conto bustato
smette di produrre per sempre). EV del biglietto $100k positivo in entrambe le lenti
(+$6.789 close-only, +$1.166 intraday), con ~69% di perdere la fee nella lente
pessimista. Cap $200k/trader => ~€15-30/g max: per €50/g servono piu' firm.

DISCREPANZA DICHIARATA col 24/07 (P(vivo) A@0.75x: 58% loro, 10% mio): il mio wick e' a
estrazione indipendente (piu' severo) e la finestra 2024+ e' quella dove A e' debole.
La direzione concorda (meno leva e' meglio); sul LIVELLO il numero del 24/07 (recon MTM
vero) e' piu' affidabile del mio.

Piu' l'addendum "10k su IB" al diario (analisi gia' committata in ea6743d).

Test: 217 pass (+3: consistency morde/non-morde, DD statico binding).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 17:10:26 +00:00
Adriano Dal Pastro ea6743d6b0 research(rendita): curva capitale->book eseguibile, muro della rendita, asimmetria funded
Ondata "rendita passiva" (2° filone del 2026-07-25). Book live, pesi, config e cron
INVARIATI: questa sessione non tocca nulla del path di esecuzione.

1) DIFETTO DI ESEGUIBILITA' su GTAA01 (5° sleeve del book attivo). gtaa.py modella 2bps
   proporzionali e lo sleeve e' documentato "switch mensile/basso turnover": entrambe false.
   Il vol-target ribilancia OGNI GIORNO su 6 gambe e IB ha un pavimento FISSO per ordine
   (min(max($0.35, $0.0035/az), 1% valore)) = ~$530/anno indipendenti dal capitale.
   A $600: CAGR -3.5% / Sharpe -0.55 (vs +5.5%/0.77 modellato); negativo fino a ~$3k.
   Con banda $50 + cadenza settimanale (plateau, non argmax) torna a Sh 0.52 / CAGR 3.0%.
   -> Sharpe onesto di GTAA01 ~0.55-0.64, non 0.77.
   REGOLA NUOVA: il costo di un venue va modellato nella sua FORMA (fisso vs proporzionale),
   non solo nel livello. Controprova su Deribit (proporzionale): TP01 realistico = modellato
   da ~$500 in su.

2) LA RENDITA NON E' capitale x CAGR. Il muro del 24/07 (EUR 122k) ignorava il rischio di
   sequenza. Prelievo perpetuo (P(cap a 20a >= cap iniziale) >= 90%) sul path live
   de-luckato: 5.98% -> $497k; banda onesta $232k-$497k (il de-luck x0.6 sopra il path live
   rischia di contare due volte la degradazione SKH01). Invariante di lente: la rendita
   perpetua vale ~45-55% del CAGR -> ogni muro calcolato come target/CAGR sbaglia di ~2x.

3) DIVERSIFICARE NON CREA REDDITO a pari nozionale (5.98% -> 6.35%); libera BUDGET DI
   RISCHIO: a iso-rischio (vol 15%) 7.51%/$395k -> 9.25%/$321k. L'ipotesi "piu' capitale ->
   piu' sleeve -> CAGR super-lineare" e' REFUTATA nella forma forte (curva Sharpe piatta da
   $600 a $200k).

4) ASIMMETRIA CAPITALE-PROPRIO vs FUNDED. Su conto funded il capitale e' $100k -> gli sleeve
   STAT-MODE per taglia (XS01) diventano eseguibili, e le regole prop passano sul DRAWDOWN,
   non sul CAGR. Aggiungendo XS01: P(pass) HYRO 44.4->54.7%, funded P(vivo 1a) 18.9->57.6%.

5) LA VIA: i 600 euro come BIGLIETTO. Scala di conti funded, 36 mesi. Problema mai studiato:
   N conti sullo STESSO book bustano INSIEME -> serve sleeve diversi su conti diversi.
   Vince il MISTO, non gli estremi; il book live attuale e' la politica PEGGIORE.
   Verdetto in banda: P(arrivare a 50 EUR/g in 3 anni) 2-21%, P(bruciare i 600) 33-78%
   -> scommessa a coda destra, non una rendita.

6) ADDENDUM "10k su IB": allocazione fra venue. 94% su IB piu' che dimezza il reddito
   (EUR 0.93/g vs 2.16/g). La leva che convertirebbe lo Sharpe in reddito e' chiusa dai
   costi (Reg-T 2x + margine 5.5%) -> vince tutto-Deribit a 1.33x. GTAA01 sui 10k rende
   EUR 0.50/g sopra la liquidita' ferma, pagati con un maxDD del 10%.

Bug catturato in sessione: base di prelievo funded aggiornata giornalmente come HWM mobile
-> payout $230/anno invece di ~$7.000; regole vere = max-loss STATICO dal saldo iniziale.
Test di regressione cablato.

Test: 214 pass (200 preesistenti + 14 nuovi in tests/test_capcurve.py).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 17:05:16 +00:00
Adriano Dal Pastro 7b567c8435 merge: staleness-gate bloccante + report Telegram giornaliero
Protezione di capitale su un fallimento gia' materializzato (acquisto ETH del
2026-07-14 su feed fermo da 6 giorni) e fine del silenzio Telegram a libro flat.
Strategie, pesi e sizing INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 10:05:47 +00:00
Adriano Dal Pastro 71b39c2c86 ops(live): staleness-gate bloccante + report Telegram giornaliero
Presa in carico operativa del conto Deribit (delega dell'utente). Nessun cambio a
strategie, pesi o sizing: il libro resta TP01 0.75 + SKH01 0.25.

1) STALENESS-GATE (protezione di capitale, era un follow-up mai cablato)
Il 2026-07-14 alle 14:00 UTC il book ha COMPRATO ETH $75 con l'ultima barra del
feed certificato ferma al 2026-07-08: feed congelato da 6 giorni (diario
2026-07-15-feed-freeze). I due gate esistenti non potevano vederlo — il conto ERA
online e la posizione ERA leggibile: proteggono dai problemi di CONTO, non da un
feed morto. Il diario raccomandava un alert; qui il gate e' BLOCCANTE, coerente
con gli altri due ("non opero a cieco"), col disaster-SL on-book come rete su
eventuali posizioni gia' aperte.
- config/live.json: max_data_age_days = 2;
- book_execute: _data_age_days() + blocco PRIMA di costruire DeribitTrader
  (nessuna sessione autenticata aperta su dati morti) + alert Telegram con il
  comando di sblocco; data illeggibile => trattata come stantia;
- letto con cfg.get(default): una config priva della chiave ricade sulla soglia
  sicura invece di sollevare KeyError dentro il percorso con soldi veri;
- tests/test_book_staleness_gate.py: 8 casi, incluso il funzionale che riproduce
  la situazione del 14/07 (online + posizione leggibile + ordine pronto) e
  verifica che DeribitTrader NON venga costruito.
- tests/test_book_live.py: i 3 report finti avevano last_data="2026-07-01"
  hardcoded -> ora data fresca calcolata. Quei test riguardano skh_error /
  pos_error / eq_fallback, non la staleness: con la data fissa sarebbero marciti
  al superamento della soglia.

2) REPORT TELEGRAM GIORNALIERO (scripts/live/telegram_daily.py, in cron_daily.sh)
Gli alert esistenti scattano solo su ordine o errore: con il libro flat — stato
normale e corretto col trend giu' — significava silenzio per settimane,
indistinguibile da un sistema morto. Il report dice ogni giorno dove sta il conto,
perche' non opera e quanto manca perche' operi (con la convenzione TP01 corretta:
media dei SEGNI, quindi servono 2 orizzonti su 3, non basta il piu' breve).
Sola lettura: un test verifica che il modulo non possa inviare ordini.

Stato al commit: equity $596.92, flat e a target, disaster-SL -30% verificato
(placed @ $1,308.7 sull'ultima posizione). TP01 0.00 su entrambi: accensione a
BTC $78.680 (+22,7%) / ETH $2.370 (+27,2%).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 10:05:47 +00:00
Adriano Dal Pastro 8a2fede2d5 merge: ondata 2026-07-25 — XSR01 in forward-monitor, 2 refutazioni, fix split feed equity
Filone 'trova nuove strategie'. Book e pesi INVARIATI; il conto live non e' toccato.

- fix DATO sul libro live: split non aggiustati IWM/EFA (2005-06-09) che la
  certificazione non vedeva (soglia maxret>50% vs split 2:1 = esattamente -50%).
  GTAA01 FULL Sh 0.61->0.64, IS 0.49->0.54; OOS e maxDD invariati -> il difetto
  sottostimava lo sleeve, nessuna decisione presa va rivista.
- MAT01 (trend su 18 ETF multi-asset) SCARTATO: a pari volatilita' il minor DD si
  inverte -> de-levering. GTAA6 e' gia' al soffitto d'ampiezza.
- STATARB-EQ (12 coppie ETF, 28.5 anni) SCARTATO: il meccanismo non si trasferisce
  alle azioni; il lordo e' -0.17 e il resto e' turnover.
- STATARB-MULTI: ETH/BTC e' al 58° pctl fra le 50 coppie -> per il gate 27/09
  l'ipotesi 'fortuna di una coppia' e' refutata. Addendum pre-registrato al gate.
- XSR01 CANDIDATO NUOVO in forward-monitor (gate 2026-10-23): cross-sectional
  residual dollar-neutral su 50 alt HL, Sharpe netta 1.82, DSR 0.985, corr ~0 a
  tutti e 5 gli sleeve; fuori dal book per storia corta, tilt-null fallito e
  margine di costo sottile.

Da questo merge il cron giornaliero avvia l'accumulo della finestra forward XSR01.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 09:50:29 +00:00
Adriano Dal Pastro ec1501caa6 docs: diario ondata 2026-07-25 + CLAUDE.md — XSR01, 2 refutazioni, fix split equity
Diario docs/diary/2026-07-25-mat01-statarb-generalization.md (6 sezioni):
MAT01 scartato col null de-levering a pari volatilita'; STATARB-MULTI
(ETH/BTC non e' un outlier: 58° pctl) e STATARB-EQ (non si trasferisce alle
azioni, il lordo e' -0.17 e il resto e' turnover); lo split non aggiustato di
IWM/EFA con impatto quantificato su GTAA01; l'addendum pre-registrato al gate
del 27/09; e XSR01 col suo scettico e le sue tre debolezze dichiarate.

Registrati anche i due errori di metodo miei corretti in sessione (null statico
con look-ahead; null a fee piene contro un segnale permutato ad alto turnover):
entrambi avrebbero prodotto numeri piu' belli e sbagliati.

CLAUDE.md: nuove voci XSR01 (candidato in monitor, gate 2026-10-23), ondata
2026-07-25, e il difetto SPLIT-NON-AGGIUSTATI con la regola nuova — ogni soglia
di certificazione tarata su un valore tondo va controllata contro il difetto che
genera esattamente quel valore.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 09:48:23 +00:00
Adriano Dal Pastro b8c9430bd7 feat(research): XSR01 "Cross-Sectional Residual" — candidato nuovo in forward-monitor
Primo candidato da molte ondate a superare marginale-ADDS, deflated-Sharpe 0.95,
tre null avversariali e il test di lag, con corr ~0 a TUTTI e 5 gli sleeve attivi.

COS'E'. Il meccanismo congelato di STATARB-RESID (W=45, sgn=+1, residuo OLS
causale su BTC, z-score, tanh, vol-target 20%) applicato ai 50 alt HL, con
posizioni DEMEANATE cross-sezionalmente ogni giorno. Il demeaning annulla
ALGEBRICAMENTE la gamba BTC comune — sum(p_i-p̄)(r_i-r_btc) = sum(p_i-p̄)r_i —
quindi non e' un paniere di coppie ma una strategia cross-sectional
dollar-neutral, e l'ampiezza effettiva passa da 4.5 a 37.4.
NB: non e' nato da un'idea nuova ma dalla DIAGNOSI di un fallimento (l'ampiezza
effettiva 4.5 indicava un fattore comune da togliere).

NUMERI (2.6 anni): Sharpe netta 1.82 (lorda 2.70), maxDD -2.6%, vol 2.3%.
GATE: marginale ADDS (robust_oos + beats_noise_null + non-hedge +
has_insample_edge); deflated-Sharpe 0.985 PASS; corr TP01 0.060 / XS01 -0.019 /
VRP01 -0.001 / SKH01 0.001 / GTAA01 0.071; book a w=15% HOLD 2.36 -> 2.51,
DD invariato.
SCETTICO (r0725_statarb_demean_skeptic.py): 3 null A FEE-NEUTRALE (permutazione
cross-sezionale / casuale / temporale a blocchi) centrati a ~0.01, candidato
lordo 2.70 sopra il MASSIMO di 300 estrazioni (p<0.004); lag 1.82/1.19/0.81/0.51
a +0/1/2/3g = decadimento dolce di segnale lento, non firma di look-ahead; non
ridondante con XS-momentum semplice (corr 0.17-0.29).
Nota di metodo: i null vanno confrontati A FEE ZERO — permutare un segnale ne fa
esplodere il turnover, quindi a fee piene il null perderebbe per COSTO invece che
per assenza di informazione (p-value trionfale e falso).

NON NEL BOOK, 3 motivi dichiarati: (a) storia 2.6a monoregime e CRESCENTE
(Sh 2024 1.03 / 2025 1.98 / 2026 3.11) -> edge recente; (b) weights_tilt_null
FALLITO (gate_pass=False a 10% e 15%); (c) margine di costo sottile — 1.82 a
0.05%/gamba, 0.93 a 0.10%, NEGATIVA a 0.20%, turnover 38.5% del lordo/g su 50 alt
anche illiquidi con slippage NON modellato (rischio #1).

ESEGUIBILITA': ticket/gamba $1.73 a $600 (sotto min-order $5 -> STAT-MODE oggi),
$5.76 a $2000, $14.41 a $5000 -> diventa reale a ~$5k, non ai ~$20k di XS01.

CABLATO: scripts/live/paper_xsr.py (config CONGELATA, 3 libri MODELED $2000 /
REAL $600 / REAL $5000 con min-order per gamba, stato append-only) in
cron_daily.sh; gate PRE-REGISTRATO a forward-day 0 (r0725_xsr_deploy_gate.py):
decisione 2026-10-23, deploy solo se Sharpe>=1.0 E haircut di eseguibilita' a
$5000 <=40% (se sfonda -> RITIRO a prescindere dallo Sharpe).
tests/test_paper_xsr.py: 7 casi che bloccano config, dollar-neutralita',
causalita' dello step, min-order e la trappola dei timestamp tz-aware
(astype int64 -> epoche 1970, gemella di quella dell'ondata 2026-07-01).

Book e pesi INVARIATI.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 09:48:11 +00:00
Adriano Dal Pastro 9af6693e4f research: MAT01 e generalizzazione STATARB — 2 refutazioni pulite + addendum al gate 27/09
MAT01 (r0725_mat01_multiasset_trend.py, r0725_mat01b_regime.py) — SCARTATO.
Allargare il trend difensivo da 6 a 18 ETF multi-asset-class a meccanismo GTAA
CONGELATO: MAT18 perde 3/4 finestre disgiunte e, a PARI VOLATILITA', il suo
minor drawdown si INVERTE (-20.6% vs -15.4%) -> era solo de-levering. Terza
occorrenza del null de-levering dopo VRP-DD e TP01xDVOL. Corr->crypto invariata
(0.110 vs 0.116): zero guadagno di diversificazione.
Risultato positivo conservato: la curva d'ampiezza e' monotona (mediana OOS 0.44
a k=1 -> 0.80 a k=18, DD -16.0% -> -6.9%, satura a k~10-12), ma GTAA6 sta gia' al
95° pctl dei 6-subset casuali — e non e' cherry-picked (contiene TLT, il peggiore
dei 18) -> niente piu' ampiezza da raccogliere su quello sleeve.

STATARB-MULTI (r0725_statarb_multi.py) — il meccanismo congelato (W=45, sgn=+1)
su tutte le 50 coppie alt/BTC, out-of-pair-sample. REGGE: 82% Sharpe>0, 0/50
degeneri (mono 53%), perm p<0.05 nel 18% (atteso 5%). E ETH/BTC e' al rango
22/50 (58° pctl): la coppia scopritrice NON e' un outlier -> per il gate 27/09
l'ipotesi "fortuna di una coppia" e' refutata. NON e' uno sleeve: ampiezza
effettiva ~4.5 (corr media 0.204, gamba BTC condivisa), paniere IC95%
[-0.12, 1.72] con t 1.31.
Errore di metodo corretto in-sessione: il primo null statico usava
sign(mean(segnale)) sull'intero campione = look-ahead; rifatto causale + a priori.

STATARB-EQ (r0725_statarb_eq.py) — SCARTATO. Stesso meccanismo su 12 coppie ETF
a priori, 28.5 anni, ampiezza effettiva 9.9: paniere Sharpe -1.00 (t -5.33),
negativo in 4/4 decadi. Ma la lettura sta nel LORDO (-0.17, non -1.00): due terzi
sono drag di turnover -> non esiste strategia specchio. Il segno lordo dice che
sulle azioni il residuo REVERTE mentre sul crypto CONTINUA: meccanismo
plausibilmente crypto-specifico. Il gate 27/09 non puo' appoggiarsi
all'argomento "fenomeno universale".

r0724_statarb_deploy_gate.py: addendum PRE-REGISTRATO oggi (forward-day 26 di 90,
64 giorni prima della decisione) — riporta anche lo Sharpe della statica
"sempre short ETH vs BTC" a pari vol-target sulla stessa finestra. Le soglie del
2026-07-24 NON sono toccate: e' diagnostica non binding. Lettura odierna
(26 barre): STATARB +5.70 vs benchmark -4.98, posizione corrente LONG lo spread
= opposta alla statica.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 09:47:47 +00:00
Adriano Dal Pastro 741bbc2c09 fix(data): split non aggiustati nel feed equity — difetto sul libro live, riparato alla fonte
IWM ed EFA avevano uno split NON aggiustato il 2005-06-09 (IWM 2:1 = -49.5%,
EFA 3:1 = -66.5%): IB ADJUSTED_LAST non li aveva aggiustati.

La certificazione non li vedeva per un punto cieco STRUTTURALE: l'unica guardia
sui salti era `maxret > 50% -> SPIKE?` e uno split 2:1 fa esattamente -50%, cioe'
cade sul filo della soglia (IWM passava a 49.5% con status OK).

IWM e' una delle 6 gambe di GTAA01, sleeve in PRODUZIONE. Impatto misurato:
GTAA6 FULL Sharpe 0.61 -> 0.64, IS (<2015) 0.49 -> 0.54; OOS 2015+ e maxDD
INVARIATI (l'artefatto e' nel 2005, fuori hold-out) -> il difetto SOTTOSTIMAVA
lo sleeve: nessuna decisione presa va rivista.

Discriminante split-vs-crollo: NON il rapporto (SLV 2026-01-30 ha rapporto
1.3994, a 4bps da 1.4, ma e' un crollo vero: GLD -10.3% lo stesso giorno) ma il
RANGE INTRADAY — lo split apre gia' al nuovo livello con range normale (IWM:
open 47.00, range 1.7%), il crollo si muove DENTRO la barra (SLV: range 33%).

- src/data/eq_splits.py: detect_unadjusted_splits() a 3 condizioni congiunte
  (|ret|>20% AND rapporto ~ fattore comune AND range intraday <5%) + repair_splits()
  con split multipli componibili;
- riparazione in LETTURA in src/portfolio/gtaa.py::_close (produzione) e
  scripts/research/eqlib.py::load_eq (ricerca);
- fetch_ib_equities.certify(): nuovo status SPLIT-NON-AGG + elenco split rilevati;
- tests/test_eq_splits.py: 8 casi, inclusi il falso positivo SLV e un crollo -50%
  esatto con range grande.

Regola nuova: ogni soglia di certificazione tarata su un valore tondo va
controllata contro il difetto che genera esattamente quel valore.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-07-25 09:47:25 +00:00
Adriano Dal Pastro d606cd3548 docs(diary): snapshot stato paper book a chiusura sessione — book +0,94%/35g risk-off, STATARB +4,4% (gate 27/09), promemoria trigger attivi
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 23:37:03 +00:00
Adriano Dal Pastro 05d069f336 chore(cron): cabla i monitor read-only decisi alla merge — cc01_regime_watch + snapshot stablecoin in cron_daily; snapshot opzioni 0DTE 2x/g (07:55+08:05 UTC)
Crontab utente aggiornato (2 righe nuove per cron_opt_snapshot.sh). Tutti read-only:
nessun ordine, book live invariato. Smoke-test OK (0DTE: 160 righe; CC01: QUIET
BTC +8.4%/ETH +7.5% ann. 30g).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 23:19:47 +00:00
Adriano Dal Pastro 636be89b2b research(live): follow-up SKH chiuso — peso 0.25 e cron orario CONFERMATI de-luckati sul path live; + snapshot point-in-time stablecoin (sblocco WATCH a 12 mesi)
- r0724_skh_live_weight.py: sweep w 0-0.50 sul path hourly x 23 offset; w*=0.25
  (argmax mediana-IS di banda, plateau 0.20-0.30); w=0.30 passa weights_tilt_null
  solo a off0 (ancora fortunata), fallisce a offset mediano -> INVARIATO.
  Cadenza 230m = rumore (+0.01/+0.02 Sh med); il degrado live e' il fill-al-livello
  (~+0.35 Sh) che nessun cron recupera. Book e cron INVARIATI.
- r0724_stable_snapshot.py: cattura giornaliera point-in-time supply stablecoin
  (DefiLlama, tokenless, idempotente) -> data/external/stable_snapshots/ (gitignored).
  Criterio di rivisita del lead STABLE: >=12 mesi di serie propria.
- CLAUDE.md: bullet SKH01 aggiornato (follow-up chiuso).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 23:08:23 +00:00
Adriano Dal Pastro 00996640fb research(cases): 3 agenti live sui 3 case — PM<->Deribit SKIP (gap=spec non alpha), HLP SKIP/WATCH (carry ex-evento 0.2%/a), 0DTE capture avviata
PM: 34 binarie riconciliate vs daily options; il gap 11pp si decompone in basis USDT
(+4-5pp ATM), tempo 8h (-+5pp) e replica su book morti; residuo tail 2-3pp sotto costi;
trade coperto reale: lock /bin/bash.1-5, P(conflitto gambe) 2-22%, margine SM domina -> SKIP.
HLP: serie daily trovata (wHLP): Sharpe 0.69 non ~2, +12% 2026 = 1 evento, ex-evento
+0.2%/a, coda JELLY = inventario ereditato troncato da voto discrezionale, Kelly f*=0
-> SKIP/WATCH con trigger meccanici. 0DTE: fee cap binding = drag 2-3x weekly, IV<RV
al front stanotte; snapshot pipeline scritta e primo capture su disco; decisione
pre-registrata a 90g di serie. Book INVARIATO.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 22:46:59 +00:00
Adriano Dal Pastro 4c1961d77b research(hunt-web): sintesi caccia strategie via web — 10 famiglie nuove 0 slot; lead-lag JEDC = reversal travestito (rank-corr -1.000), MAX DSR 0.41
3 agenti web (~50 fonti) + 3 ondate empiriche in una notte. Convergenza indipendente
ricerca<->empirica: il factor zoo crypto si riduce a liquidity/momentum (gia' nel book).
XS su HL: lead-lag all-others e' matematicamente l'inverso del momentum proprio (check
di degenerazione da riusare); MAX segno instabile L7<->L30. HLP probe: crash-long reale
(corr book -0.19, +10.4% nel crash ott-25) ma decay 79->12%/anno + coda JELLY fuori
serie -> ALLOCATION-WATCH. Pista nuova prossima ondata: Polymarket<->Deribit (gap 11pp,
arXiv 2606.19517, spec-mismatch da riconciliare prima di credere). Book INVARIATO.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 22:24:57 +00:00
Adriano Dal Pastro b65f067f69 research(premium): ondata premi cross-venue auto-calcolati — CBPREM morto, KIMCHI d30 ucciso dallo scettico (spike+lag)
CBPREM (Coinbase vs feed cert, 2015->): HEDGE, hold -0.46. KIMCHI (Upbit/ECB, 2017->,
ancora 00:00 UTC verificata): EARNS_SLOT=True al marginal scorer (ADDS, robust_oos,
uplift + ogni anno) ma DSR 0.891 -> scettico obbligatorio: niente plateau
(d15/30/45/60 = 0.44/1.07/0.51/0.24) e lag +1g azzera (hold 0.74->0.14) = parameter
luck. Lezione codificata: EARNS_SLOT con DSR<0.95 -> sempre plateau+lag skeptic.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 22:23:16 +00:00
Adriano Dal Pastro 2320fa9cec research(onchain): prima ondata on-chain/sentiment — 0/6 slot; l'on-chain tradabile e' prezzo travestito (corr TP01 0.5-0.8)
6 famiglie mai testate (NET Liu-Tsyvinski, MVRV, exchange-supply, hash ribbons, F&G,
stablecoin-supply-growth) su segnali CoinMetrics community + alternative.me + DefiLlama,
ritorni SOLO dal feed certificato, study_family_honest su 32 celle. EXS hold-out -0.58
(claim outflow=bullish decaduto), HASH=HEDGE, FNG corr 0.82 (trend travestito), MVRV
DILUTES. Unico lead: STABLE thr=10% (DSR 0.998, ADDS persistente) ma robust_oos=False
+ caveat VINTAGE (storia DefiLlama ricostruita) -> WATCH, no paper. Regola nuova:
classificare il rischio-vintage di ogni fonte esterna prima del backtest.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 22:15:05 +00:00
Adriano Dal Pastro 5c48a8322a research(goal50): MC prop INTRADAY wick-aware — leva eval 1.5x refutata, funded ottimo a 0.75x, P(perdere fee) ~56%
Recon MTM 1h del book Deribit (TP01 pesi daily + SKH01 230m exit-al-livello SL-first,
fee incluse). Validata: leg TP corr 0.9997 / log-total +0.833 vs 0.827; leg SKH +0.548
vs +0.513; Sharpe MTM 1.62 vs 1.77 sleeve (delta = attribuzione a scalino di SKH).
I wick tagliano 6-37pp di P(pass): de-luck 1.0x HYRO 44.7% / FTMO 59.9% / Breakout 26.6%
(declassata). Funded sweep: leva ottima 0.75x (HYRO P(vivo) 58% vs 20.5% a 1x), atteso
~EUR 14.5/g a 100k. EV biglietto resta positivo ma sottile (de-luck +491/+1048/+2197 USD).
Bug tz-naive/aware nel reindex catturato dalla sanity (TP01 spariva, corr 0.43).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 21:55:23 +00:00
Adriano Dal Pastro 2e7178487d research(goal50): R2 prop-firm + roadmap finale — 50eur/g in mesi NON esiste via legale; stack onesto 18-36 mesi
- MC aggiornato alle regole VERE (HYRO 10/6/4, BREAKOUT 10/6/3, FTMO 10/10/5):
  de-luck P(pass) 55-68% a leva 1-1.5x, mediana 68-137g; funded 100k de-luck
  P(vivo) 69%, atteso blended onesto 250-450 eur/MESE (attriti fuori-MC: carry,
  recycling bust, controparte non regolata, cap industria 200k).
- Roadmap: prop = unico canale che cambia scala in mesi (8-15 eur/g);
  stack 24 mesi top-decile 30-60 eur/g, mediana 10-25; fisco 33% = muro x1.5.
- Book live INVARIATO.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 21:02:45 +00:00
Adriano Dal Pastro acfba63420 fix(test): test_paper_advance bug latente — factor divideva via (1+tail[0]), passava solo con combo[-500]==0
Pre-esistente su main (fallisce anche li'), emerso con l'avanzare dei dati.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 20:58:52 +00:00
Adriano Dal Pastro 870428e559 docs(goal50): diario R3 — monetizzazione track record: 0 in mesi, stack legale 18-36 mesi (Darwinex/eToro/OKX EU); family&friends remunerato = art.166 TUF
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 20:57:48 +00:00
Adriano Dal Pastro 7ebb1b8c37 feat(goal50): CC01 regime watch (funding 30g HL, trigger 10/15% ann.) + diario R1 yield/basis
R1 (web): carry al fondo del ciclo (BTC 0-4%, ETH negativo), Aave 4-5% = pavimento,
0k -> 2.5-4 eur/g; MiCA lascia a IT esattamente Deribit+HL; fisco 33% dal 2026
(muro capitale x1.5). Watcher read-only, oggi: BTC +8.4% / ETH +7.4% 30g = QUIET.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 20:57:13 +00:00
Adriano Dal Pastro ddc980a097 research(goal50): matematica onesta del target 50eur/g + gate deploy pre-registrato statarb
- r0724_goal50_math: muro capitale (73-228k), leva=rovina, Monte Carlo prop-firm
  sui ritorni reali del book (P(pass) 56-86%, funded 100k mediana 31-42eur/g),
  vault TVL 1-2M. Unica via 'da mesi' = moltiplicare nozionale gestito.
- r0724_statarb_deploy_gate: regola di deploy PRE-REGISTRATA a fwd-day 25
  (decisione 2026-09-27, Sh>=0.5, haircut<0.5pp, 1 proroga max) — anti
  selection-on-forward.
- diario roadmap (sezioni web-research da completare).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-24 20:55:23 +00:00
Adriano Dal Pastro 7534b08be0 research(weekend): ondata ven->lun SCARTATA 4/4 — famiglia calendario SATURA; weekend = 38% del gross TP01 (mai de-esporre)
4 agenti (drift/cond/intra/overlay), 375 trial: il drift weekend e' beta B&H,
i gate condizionali sono TP01 re-timed, l'intraday weekend e' moneta simmetrica
(CME-gap morto anche lordo). Fatto strutturale: TP01-weekend-flat = danno certo
(dSh -0.46, P=1.000) -> ogni proposta "risk-off weekend" parte REFUTED salvo
null de-levering. Chiusa la famiglia calendario su BTC/ETH (SEA+expiry+event-clock
+weekend). Book/pesi INVARIATI. Diario 2026-07-17-weekend-window.md.

gitignore: + data/live/ (log esecuzioni book live, stato runtime del conto reale)

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-18 15:03:44 +00:00
Adriano Dal Pastro 67f7b89e4c chore(live): ritira paper_trend inerte -> Old/ — sostituito da paper_portfolio
Il paper trader standalone TP01 (paper_trend.py) era inerte dal 2026-06-19
(n_bars=0), non in cron, e sostituito da paper_portfolio (TP01+XS01, gira ogni
giorno). Archiviato in Old/scripts/live/ e stato congelato rimosso.

Book live INTATTO: shadow.py legge PAPER_STATE con guardia .exists() -> degrada
a FALLBACK_CAPITAL=2000 (identico allo stato congelato) e paper_pos=None. Dry-run
di book_execute identico prima/dopo (conto online, HOLD su BTC/ETH).

- git mv scripts/live/paper_trend.py -> Old/scripts/live/paper_trend.py
- rm data/paper_trend/ (state inerte, gitignored)
- CLAUDE.md: 3 riferimenti -> paper_portfolio + nota di ritiro
- live_trend.py + shadow.py: hint/commento fallback legacy aggiornati

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-17 15:42:29 +00:00
Adriano Dal Pastro 9fa3e6a0be fix(feed): backup rebuild non-fatale — copy2→copyfile, il .bak non abortisce piu' il feed live
Il feed BTC/ETH del book era congelato 7 giorni (2026-07-08 -> 07-15): rebuild_history.py
usava shutil.copy2 per il .prebuild.bak; copy2=copyfile+copystat e copystat (os.utime/chmod
con valori espliciti) richiede la PROPRIETA' del file, non basta il group-write. I .bak sono
root:adriano, il cron gira come adriano -> EPERM ogni notte, abortendo PRIMA della scrittura
del feed (data/raw/*.parquet fermo a Jul 8). Il book ha ri-girato ogni ora su barra vecchia
(TP01 1d non ri-valutato); nessuna perdita (segnale fresco == tenuto) ma cieco 7g.

Fix: backup best-effort = shutil.copyfile (solo contenuto, no copystat) in try/except OSError.
Un .bak difensivo non deve mai poter bloccare la scrittura del feed live.

Verificato: rebuild rigirato -> feed a 2026-07-15, audit cross-venue BTC 1.9/ETH 2.0 bps,
file ora adriano:adriano (auto-sana), book dry-run legge ultima barra 2026-07-15 -> HOLD.

Diario: docs/diary/2026-07-15-feed-freeze-rebuild-copystat.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-15 18:37:42 +00:00
Adriano Dal Pastro b691f48f43 docs(diary): incident 2026-07-09 — "BOOK LIVE conto offline" = cert Traefik di default
Traefik auto-upgrade (latest+Watchtower -> 3.7.7) ha scartato il resolver ACME
per acme.json a 660 (3.x pretende 600) -> cert self-signed su tutto il VPS ->
DeribitRead SSLError -> book online=False. Zero trade persi (target flat, gate
di sicurezza OK). Fix: chmod 600 acme.json + restart; pin traefik:3.7 nel compose.
Diario con diagnosi, verifica end-to-end e runbook.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-09 20:09:41 +00:00
Adriano Dal Pastro 822aa1307e research(crt): video-claim "CRT top-down 74% win rate" SCARTATO — il 74% e' un knob, non un edge
Meccanizzato e falsificato il claim ICT/SMC top-down (H1 setup CRT -> M15/M5
conferma -> entry, uscita parziale+BE+runner) su BTC/ETH certificati.

- Setup H1 CRT gia' triplo-refutato (onda 2026-07-02); qui testato l'angolo nuovo:
  la gestione d'uscita e il "74% WR".
- WR reale 30-37% a RR 1.5-2, SOTTO il null gambler's-ruin 40% -> il ritest tocca
  il target meno di una moneta (conferma "il ritest e' informazione negativa").
- Il 74% si fabbrica avvicinando il target: sweep rr1 0.5->2.0 = WR sale, expectancy
  R INVARIANTE e negativa (-1.2..-3.3R netto). DSR 0.000; a fee 0 ancora negativa
  -> non morte-per-fee, l'edge lordo non c'e'.
- Non eseguibile pulito a $600 (3-4 ordini/trade, alcuni sub-min-order).
- Regola candidata: convertire ogni claim "WR X%" da schema parziale+BE in
  expectancy R netto fee (WR ~= 1/(1+rr1), non un merito).

Nessuna modifica a src/config/live/tests. Book e pesi INVARIATI.
Diario: docs/diary/2026-07-07-crt-topdown-74winrate.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-08 06:02:38 +00:00
Adriano Dal Pastro cf7de40dc0 feat(live): cap/asset dinamico = equity/2 — operazionalizza la decisione frontier (inerte a $600)
Il cap notional per-asset non e' piu' fisso a $300: con max_notional_per_asset_frac
in config diventa equity/2, cosi' cresce col capitale e un deposito futuro non resta
strozzato (frontiera 2026-07-03). Guardrail: dinamico SOLO con equity reale fidata;
su fallback/offline si torna al cap fisso (protezione downside quando E e' ignota).
Live dry-run: cap $299 a equity $598 -> inerte oggi. Suite 172 passed (+4 test).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-03 09:42:13 +00:00
Adriano Dal Pastro eef200cf14 research(frontier): frontiera onesta del book — il 6% e' un miraggio di regime, gira gia' alla vol nativa
Misura (non ricerca segnali) della frontiera CAGR/DD/P-rovina vs
target-vol, pesata per confidenza per-sleeve, a 2k/5k. 7 agenti (3
filoni + refuter fat-tail + scettico), sanity bit-exact dei due book.

Reframe decisivo: il "6% attuale" NON e' un target, e' la vol realizzata
in risk-off; a lambda=1 il book LIVE 2-sleeve gira gia' a ~11% vol/9.4%
DD -> "saltare a 10%" e' assumere non-risk-off, non aggiungere leva.

- Target-vol fidato book LIVE (TP01+SKH01, unico eseguibile <20k):
  ~10% (banda 8-11%, lambda ~0.9). Scale-invariante: stesso % a 2k/5k.
- P(rovina-50%) e' la metrica SBAGLIATA (slack a 22%); il vincolo che
  morde e' P(DD>30%), super-lineare. Muro onesto ~12% (gap-through SKH
  reale non nei rendimenti modellati; 2-sleeve 4x crash-sensibile).
- Vol differenziata-per-confidenza REFUTATA: taglia la diversificazione;
  la bassa fiducia va nel DE-MEAN (haircut media), non nella leva.
- Reward onesto (HOLD<<FULL): ~EUR 0.3-0.7/g@2k, 0.8-1.8/g@5k; warm-up
  vs 6% risk-off = ~+EUR 0.2/g@2k. EUR 50/g resta ~130k (capitale+tempo).
- UNICA azione config (proposta, NON applicata): cap $300 -> equity/2,
  altrimenti a 5k il cap raffredda paradossalmente il book sotto il punto
  fidato (6% vol ceiling).

config/live.json NON toccato. Book invariato. 168 test verdi.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-03 08:43:59 +00:00
Adriano Dal Pastro 116abf5203 docs(diary): snapshot stato completo del progetto (2026-07-03)
Foto d'insieme dopo il blocco di ricerca 1-3 luglio: book live
(TP01+SKH01 flat, $598), portafoglio research 5-sleeve (de-luckato
HOLD ~2.0), anchor-audit completo 4/4, edge morti da non ri-testare,
~10 gate anti-illusione codificati, mappa capital-scaling 2-5k,
aperti/prossimi passi. Punto di riferimento unico dello stato.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-03 07:16:17 +00:00
Adriano Dal Pastro 26f8d27a61 research(wave-0703): migliora+proteggi VRP01 — 7 filoni, 0 miglioramenti, anchor-audit VRP01 chiuso (4/4 sleeve)
Goal: migliorare la strategia short-vol (famiglia Albimarini/VRP01) e
proteggerla dai DD. Workflow 26 agenti (7 filoni + 2 lenti avversariali
+ scettico incrociato). Esito: NON migliorabile; la protezione DD si
compra SOLO con la size.

- Griglia 288 strutture: nessuna batte VRP01 (DSR 0.000; meta' griglia
  = 3a occorrenza "0-perdite/Sharpe implausibile" dopo CC01/ALB-A).
- 4 overlay DD (exit-spike/SL-MTM/ala-coda/cooldown): 4/4 REFUTED dal
  null de-levering — la protezione crash vive gia' nel gate IV-rank.
- Gate nuovi: 4o fallimento su 4 (l'alpha e' il binario IV-rank>0.30).
- Sizing: 12% deploy ~ 0.27 Kelly onesto (anti-rovina); disambiguazione
  unita' obbligatoria vs 12% peso book (0.014 Kelly, fattore 19x).
- Gate term-structure VIX/VXV su SPX (dSh +0.90, DSR 0.992) = confound
  di modello al 100% -> nuova regola: riprezzare term-structure-consistent
  prima di credere a un gate vol su strutture BS-flat.
- ANCHOR-AUDIT VRP01 CHIUSO: primo sleeve SENZA luck (fase canonica =
  peggiore delle 7 -> numeri di ammissione conservativi). Audit anchor
  ora completo su 4/4 sleeve ancorati.

Book/pesi INVARIATI. Nessun nuovo sleeve. 168 test verdi.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-03 07:05:19 +00:00
Adriano Dal Pastro 76120b59c2 research(wave-0702bis): ondata video-claims — Elliott 3/3 e Albimarini 2/2 scartati, mappa capital scaling 2-5k
Sei agenti, nessun sopravvissuto:
- ELL-A range-cycle: rumore (0/24 Bonferroni; nessuna cella weekly regge
  a tutte le 7 ancore). Lezione pandas: resample("7D", origin) IGNORA
  origin -> usare "168h" per le bande d'ancora weekly.
- ELL-B Fibonacci: l'edge apparente e' la POSIZIONE dei livelli, non i
  numeri (null location-matched: pctl 0.39-0.68); confluenza FAIL 4/4.
- ELL-C canale: Donchian travestito (non batte il Donchian equivalente,
  DSR 0.685, IS 1.40 -> HOLD -0.87; target 1.618 = caso; anchor-luck 4h).
- ALB-A diagonale: il condor stessa-scadenza la batte a ogni f; senza
  gate IV-rank tutte le strutture perdono (3a conferma: l'alpha del VRP
  e' il gate); fee-negativa su Deribit a qualsiasi size; 2o caso
  "0-perdite = Sharpe implausibile" dopo CC01.
- ALB-B claims: 82%/PF 5.16/"420%" consistente con zero skill (P=20-45%,
  78.6% delle finestre 6-mesi lo produce); replay con code reali =
  rovina 1998/2002/2020; la diagonale passa il 12-40% della perdita naked.
- Capital scaling 600->2-5k: unico vincolo binding = cap $300/asset
  (a 5k book al 49% del target) -> AL DEPOSITO alzare a equity/2;
  min_order $5 lasciare; XS01 ~20k confermata; aspettativa onesta
  de-luckata 2k ~EUR 0.6-0.8/g, 5k ~EUR 1.4-2/g.

Nessun nuovo sleeve, book live invariato. 168 test verdi.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-02 23:31:38 +00:00
Adriano Dal Pastro a74cc69583 research(anchor-audit): timing-luck confermato su XS01 e SKH01 — 3/3 sleeve ancorati, book de-luckato HOLD ~2.0
Chiude il pendente dell'ondata timing 2026-07-02. Due audit indipendenti
(sanity replica bit-exact, ancore a priori, zero tuning per-fase, bootstrap):

- XS01 (10 fasi ciclo H=10): fortuna nel DD (15° pctl: 10.8% vs 15.5% tipico,
  29% peggiore) e FULL (85°), non nell'hold-out (65°); P(spike)~0.91-0.94.
  Lens onesta = ensemble di fase FULL 1.25 / HOLD 1.31 / DD 11%. Ammissione
  @15% regge, i numeri 1.50/1.71/11% no.
- SKH01 (23 offset griglia 230m/690m): canonico = 93-98° pctl di OGNI metrica,
  minHold/blend/book-HOLD = massimo dei 23; il gate DD<30% (criterio di
  selezione V2-DD) fallisce in 15/23 offset. Regge: uplift blend positivo a
  tutte le 23 fasi (min +0.18) + corr ~0.08 -> ADDS ridimensionato. Path live
  reale (cron orario + exit software): book FULL 1.46->1.19 / HOLD 1.64->1.15 /
  DD 18->25%, gap-through-stop nei crash (sl2% -> -11/-23%).
- Book 5-sleeve: HOLD 2.46 eredita ~+0.10/+0.17/+0.5 di fortuna d'ancora
  (TP01/XS01/SKH01) -> stima de-luckata HOLD ~1.9-2.1, FULL ~2.0-2.2, DD ~6%.

Nessun cambio operativo (pesi/book live invariati; ogni cambio passa
weights_tilt_null). Narrativa aggiornata (CLAUDE.md, docstring skyhook).
Follow-up: anchor_luck_band() in altlib, cadenza 230m, peso SKH live.
168 test verdi.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-02 22:34:35 +00:00
Adriano Dal Pastro 73d74c5e53 research(wave-0702): ondata timing + CRT — 8 filoni, 0 nuovi sleeve, finding anchor timing-luck TP01
Goal: "altre strategie su Deribit con timing differenti". 8 filoni multi-agente + scettico:
- event-clock bars, expiry calendar Deribit, clock lenti/bande, regime-speed: SCARTATI
- CRT (Candle Range Theory) base/multi-TF/contesto: SCARTATA 3/3 (DSR~0, ritest =
  informazione negativa; sottoprodotto: FOLLOW>FADE sui livelli prior-day ogni anno,
  conferma il lead prevday)
- FINDING (confermato da scettico indipendente): hold-out 0.31 di TP01 = migliore delle
  24 ancore orarie (mediana 0.04, banda [-0.13,+0.30]) -> narrativa corretta in CLAUDE.md
  e docstring: l'hold-out non risolve l'edge di ritorno, regge il taglio DD a ogni ancora.
  Tranching K=2/4 = solo varianza della stima, no deploy a $600. Audit d'ancora pendente
  su XS01/SKH01. Book live e portafoglio INVARIATI. Test 168/168.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-02 22:12:22 +00:00
Adriano Dal Pastro e6657fcb16 feat(portfolio): GTAA01 promosso a 5° sleeve @20% — FULL 2.12→2.24, HOLD 2.21→2.46, DD 7.8→6.2%
Il diversificatore strutturale validato il 2026-06-22 (trend difensivo equity
6-ETF su IB, 30y storia, OOS 2015+ indipendente dall'hold-out crypto, corr al
book ~+0.10) era rimasto in paper_combo senza mai essere valutato come sleeve.
Valutazione onesta (r0701_gtaa_5th_sleeve): uplift positivo in-sample e su
TUTTE le finestre disgiunte (+0.05/+0.19/+0.25), multi-cut +0.21..+0.25,
plateau monotono w10-30% — passa dove EW-STR era morto. Ingresso @20% (IS-best
30%, scelta strutturale dichiarata). Convenzioni: weekend equity=0 (capitale
IB fermo, non riciclato), attivazione all'era book 2019-03. Il book live
Deribit (TP01+SKH01) NON cambia. Suite 168/168.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-01 23:31:38 +00:00
Adriano Dal Pastro 491411ac77 research(wave-0701): 6 filoni multi-agente — 0 nuovi sleeve, pesi confermati, gate weights_tilt_null
Ondata onesta su angoli non coperti: funding-TS (chiude il filone funding su 3
lati), breadth alt (non-ridondante ma DSR 0.43, rivisitabile con storia),
XS-residmom (REDUNDANT), pesi+guardia-DD (EW-STR refutato dallo scettico come
selezione-sull'hold-out di 2° ordine, firma best-of-15), VRP-refine (filone
esaurito), stagionalità-XS (morta allo step statistico).

Lezione codificata: weights_tilt_null + combine_outer in src/portfolio
(ogni cambio-pesi vs null di tilt casuali cap-respecting + delta in-sample>=0);
5 test nuovi, suite 165/165.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-01 23:21:59 +00:00
Adriano Dal Pastro ccf5e38101 feat(dashboard): banner alert operativi del book live (SKH/posizione/equity)
Il dashboard non mostrava nessuno dei tre segnali di health introdotti nei
commit 31369b3 (skh_error) e 5670469 (pos_error/eq_fallback): finivano solo su
Telegram + log cron, invisibili a chi guarda il monitor. pos_error/eq_fallback
erano gia' in shadow_report (usato dal dashboard) ma ignorati dal template;
skh_error non era nemmeno recuperato (il dashboard usa shadow_report, non
book_report).

Fix:
- _alerts_banner(): helper puro (verde "nessun alert" se pulito, rosso con una
  riga per errore) che rispecchia i tre alert di book_execute.
- build(): raccoglie pos_error/eq_fallback dallo shadow gia' fetchato + skh_error
  da book_report(offline=True) (feed certificato, nessuna rete extra).
- html(): renderizza il banner in cima alla sezione ① LIVE.
- tests/test_dashboard.py: +4 (verde, 3 alert, parziale, chiave-ignota).

Suite 160/160. Render end-to-end verde (conto sano $598.06 flat). Chiude la
copertura: i 3 pattern di errore silenzioso ora visibili su log + Telegram + dashboard.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-01 22:47:35 +00:00
Adriano Dal Pastro 567046953d fix(book): gate fail-safe posizione + diagnostica equity — niente errori silenziosi nel path live
Terza+quarta chiusura del pattern "eccezione ingoiata -> stato safe silenzioso"
in src/live, dopo skh_error (31369b3). Emerse durante la verifica del gate SKH01.

Opzione A (gate fail-safe posizione):
- shadow._positions: se la read della posizione reale Deribit lancia, assume flat
  MA ora ritorna un pos_error esplicito (prima solo una note mai propagata).
- Propagato shadow_report -> book_report -> book_execute: se ONLINE ma posizione
  IGNOTA, l'esecutore NON opera a cieco (return + alert), come gia' per 'online'.

Opzione B (diagnostica equity, no halt):
- shadow._equity/shadow_report: se ONLINE ma equity reale non leggibile, il book
  ripiega su paper_cap (~$2000) invece del conto reale (~$598) -> sovradimensiona
  ~33%, ma l'hard-cap $300/asset limita il downside. Nuovo flag eq_fallback ->
  book_execute stampa warning + alert Telegram MA prosegue (niente gate: la scelta
  e' solo diagnostica, l'hard-cap gia' protegge).

Test: +8 (4 gate A, 4 diagnostica B). Suite 156/156. Path live pulito
(skh_error/pos_error/eq_fallback = None). Diario 2026-07-01-book-live-error-surfacing.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-01 22:39:59 +00:00
Adriano Dal Pastro 31369b358c fix(book): esponi skh_error nel book live — niente flat SKH silenzioso
book_report scriveva skh_error in un dict locale MAI incluso nel return ->
r.get("skh_error") era sempre None. E book_execute non lo leggeva comunque.
Risultato: se il feed SKH (fresh_5m) fallisse, il book forzava SKH a flat in
silenzio, indistinguibile da un flat legittimo -> entry SKH reale mancato,
nessun alert.

Fix:
- src/live/book.py: skh_error come variabile esplicita, esposta nel dict di
  ritorno (None normalmente). Il fail-safe (SKH->flat, TP01 indipendente sul
  suo feed certificato) resta invariato.
- scripts/live/book_execute.py: emette la riga di log + alert Telegram quando
  skh_error e' presente.
- tests: book_report cattura-e-flagga l'errore; book_execute lo fa emergere
  (log + notify). Suite 148/148.

Contesto: verifica del gate SKH01 dopo 193 run flat dal 06-23 (gate SANO —
335/341 entry storici, shorta i crash; flat legittimo: ultimo entry 06-06
chiuso ~06-08 pre-arming). Questo chiude il rischio latente scoperto durante
la verifica.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-01 22:26:02 +00:00
Adriano Dal Pastro 88f5f5a02a docs(memory): CLAUDE.md — completa il log dei filoni 2026-06-29 (1ª ondata A/C/D)
Aggiunge il bullet riassuntivo dei filoni della prima ondata del 29-06 (gia' nei diari
ma mancanti dal log curato in CLAUDE.md): A DVOL-direzionale=HEDGE, B intraday ERM=falso
positivo (gia' coperto dal gate), C xsec-v2 low-vol=debole/STAT-MODE, D macro-gate=ridondante.
Memoria curata ora completa per la sessione 2026-06-29.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-29 21:29:37 +00:00
Adriano Dal Pastro ee82e0a056 feat(dashboard): box forward-monitor STATARB-RESID (lead ortogonale+eseguibile)
Aggiunge il forward-monitor STATARB-RESID al dashboard accanto a PREVDAY (sezione
③·c FORWARD-MONITOR): carica data/paper_statarb/state.json, mostra doppio libro
MODELED/REAL-$600, ret/maxDD/fill-haircut, posizione spread corrente e giorni forward.
Warn aggiornato: LEAD sotto deflated-Sharpe -> forward per confermare l'edge, non deploy.

Smoke-test html() OK (box presente, dati live). Test 146/146.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-29 21:20:56 +00:00
Adriano Dal Pastro c52e0ab3f8 feat(forward): cabla STATARB-RESID nel forward-monitor PAPER (lead ortogonale ETH/BTC)
Forward-monitor del LEAD dello sweep 2026-06-29 (relative-value ETH/BTC, dollar-neutral 2 gambe),
il primo stream insieme ORTOGONALE (corr->book 0.027, beta-mkt 0.013) ED eseguibile a $600.

- scripts/live/paper_statarb.py: forward-only, doppio libro MODELED($2000)/REAL-$600 (haircut fill),
  riusa il segnale ESATTO di orthogonal_signals.py (niente reimplementazione). Config CONGELATA
  W=45 sgn=+1.
- Cablato in scripts/cron_daily.sh accanto a paper_prevday. Stato runtime in data/paper_statarb/
  (gitignored).
- test tests/test_paper_statarb.py (frozen config + advance forward/idempotente + haircut $600 basso).

Correzione di etichetta (verificata): la cella vincente e' sgn=+1 -> NON mean-reversion ma
relative-MOMENTUM sul residuo (dislocazioni ETH-vs-BTC continuano a 1d; sgn=-1 perde -1.4 IS).
Diario + CLAUDE.md aggiornati. Test 146/146. Nessun deploy, forward-only.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-29 20:58:29 +00:00
Adriano Dal Pastro cff5fa2bf5 research(sweep): 5 thread paralleli — 0 nuovi sleeve, STATARB-RESID LEAD ortogonale+eseguibile
Ricerca onesta su aree inesplorate (harness altlib+xsec_v2_nonmom, tutti i gate incl.
study_family_honest anti-selection-on-holdout). Branch main, nessun impatto live, test 143/143.

1 XSEC low-risk cousins (MAX/idio-vol/Amihud) -> 1 LEAD (IVOL), STAT-MODE, DSR 0.37<0.95
2 XSEC momentum-structure vs XS01            -> tutto REDUNDANT (sostituire XS01 distrugge hold)
3 Meta-allocazione dinamica (4 sleeve)       -> pesi fissi vincono (gia quasi risk-parity)
4 Segnali ortogonali ETH/BTC (2 gambe)       -> STATARB-RESID + DVOLSPREAD LEAD
5 1-gamba a segnale (MACD/RSI/Supertrend/...) -> 0/12 earns_slot (trend=TP01, MR morta, hedge)

LEAD principale STATARB-RESID (mean-rev residuo ETH-b*BTC, OLS rolling, 2 gambe): primo stream
INSIEME ortogonale (corr->book 0.027, beta-mkt 0.013) ED eseguibile a $600 (haircut ~0, NON
STAT-MODE) -> cadono i 2 muri di XS01/opzioni. Resta solo il muro dell'edge (Sharpe 0.84,
DSR 0.929 same-sign <0.95). Causalita+fee verificate dal coordinatore. Forward-monitor, non sleeve.

Soffitto direzionale ~1.3 riconfermato. Diario 2026-06-29-strategy-search-5threads.md, CLAUDE.md agg.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-29 20:50:33 +00:00
Adriano Dal Pastro 02d875b07b merge(research): equity IB screeners + 4 filoni crypto 2026-06-29 + gate selection-on-holdout
Ricerca onesta, branch separato (nessun impatto sul book live). Test 119/119 verdi.

Equity (IB/Yahoo):
- scalping 'sottoquotate' su IB + check dati dalla rete (forward, edge non provato)
- screener short 'fond/news neg ma prezzo su' (forward, edge non provato)

Crypto BTC/ETH + universo HL (harness altlib, causale, fee 0.10% RT, marginal vs TP01):
- A DVOL direzionale  -> LEAD hedge/DD-dampener, NON sleeve
- B Intraday ERM      -> falso positivo: earns_slot da selezione-sull'hold-out + coda 2026
- C Cross-sectional non-mom (low-vol HL) -> DEBOLE/forward-monitor (deflated-Sh 0.13) STAT-MODE
- D Macro regime-gate -> RIDONDANTE col trend (corr->TP01 0.989), SCARTATO

Harness indurito (LESSON 4 in altlib): deflated_sharpe + select_cell_insample +
study_family_honest -> chiude il punto cieco "selection-on-holdout".
2026-06-29 20:09:18 +00:00
Adriano Dal Pastro b4ec92734c research(intraday): de-bias del lead ERM (filone B) — falso positivo + gate selection-on-holdout
L'analisi di robustezza affonda lo "earns_slot=True" di ERM: era prodotto da
selezione-sull'hold-out + coda 2026 + multiple-testing non corretto.
  A) deflated-Sharpe FAIL: 0.00 (tutti 122 trial) / 0.16 (no-TOD) / 0.24 (solo-ERM) << 0.95
  B) selezione in-sample-only -> ALTRA cella (long-flat, corr->TP01 0.53) = NEUTRAL, no slot
  C) ensemble del plateau (no cherry-pick) -> ADDS ma robust_oos=False -> no slot
  D) uplift FULL solo +0.10, negativo 2021/2022; uplift HOLD +0.30 concentrato nel 2026
=> ERM SCARTATO come sleeve. Conferma ennesima del soffitto BTC/ETH-direzionale ~1.3.

Lezione CODIFICATA in altlib (LESSON 4, test in tests/test_harness_realism.py):
  - deflated_sharpe()       Bailey & Lopez de Prado, PASS >= 0.95
  - select_cell_insample()  scelta cella col solo Sharpe pre-HOLDOUT (no peeking)
  - study_family_honest()   gate combinato: earns_slot[cella in-sample] AND DSR>=0.95
Regola: una strategia direzionale grid-searched si giudica con study_family_honest,
non chiamando study_marginal sulla cella a max hold-out. Verificato end-to-end su ERM
(earns_slot_honest=False). Chiude il punto cieco gemello di CC01.

Diario aggiornato (verdetto downgrade), CLAUDE.md aggiornato. Test 119/119 verdi.
Nessun impatto live (branch separato).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-29 20:04:36 +00:00
Adriano Dal Pastro aad69f9790 research(crypto): 4 filoni 2026-06-29 — ERM lead sub-daily (forward), 3 scartati/deboli
Ricerca onesta su BTC/ETH + universo HL, branch separato (nessun impatto live).
Harness condiviso altlib (causale, fee 0.10% RT, marginal vs TP01, day-boundary,
haircut $600). Test 19/19 verdi.

- A DVOL direzionale  -> LEAD hedge/DD-dampener, NON sleeve (buy-the-fear; is_hedge).
- B Intraday ERM 8h   -> LEAD forte / forward-monitor: earns_slot=True, ADDS oltre
                         SKH01 (TP01+SKH+ERM 60/25/15 FULL 1.88/HOLD 1.46/DD 8.9%).
                         Caveat: plateau hold-out single-row, multiple-testing non
                         deflazionato, exec 8h. Controllo TOD = FAIL atteso.
- C Cross-sectional non-mom (low-vol HL) -> DEBOLE/forward-monitor (deflated-Sh 0.13,
                         storia 2.5a, non eseguibile $600) STAT-MODE.
- D Macro regime-gate -> RIDONDANTE col trend (corr->TP01 0.989), SCARTATO.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-29 19:48:36 +00:00
Adriano Dal Pastro a158d0e2ae research(equity): screener short 'fond/news neg ma prezzo su' (forward, edge non provato)
Goal chiarito: short su titoli con fondamentali/notizie negativi ma prezzo in salita.

Gate dati (v2.0.0): NON backtestabile -> fondamentali da rete = snapshot correnti,
applicarli a prezzi passati = look-ahead. Come la term-structure: solo screener forward.

Costruito screener da dati di rete tokenless: fondamentali strutturati Yahoo
(quoteSummary via crumb: recommendationMean/surprise/revGrowth/sell-skew) + sentiment
headline + momentum 1m/3m. SHORT cand = (fond/news neg) AND prezzo su. Run live oggi:
nessun candidato (mercato in flessione ampia -> gamba 'prezzo su' non scatta).

Intuizione chiave: shortare la FORZA combatte momentum + PEAD; il rialzo 'malgrado'
brutte notizie spesso prezza info che i fondamentali trailing non hanno -> e' la
versione contrarian/rischiosa dell'anomalia. La versione pulita = short su fondamentali
deboli quando il prezzo CONFERMA (scende), non quando diverge.

Eseguibilita': borrow/squeeze/perdita illimitata/PDT 5k/IB instabile/00 -> non deployabile.

- scripts/research/eq_fundnews_short.py (+ forward log data/raw/fundnews_short_screen.parquet)
- tests/test_eq_fundnews_short.py (scoring puro offline)
- docs/diary/2026-06-26-equity-fundnews-short.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 19:51:22 +00:00
Adriano Dal Pastro e28176efef research(equity): scalping 'sottoquotate' su IB + check dati dalla rete
Goal: comprare azioni IB quando sottoquotate, con verifica incrociata dei dati.

1) CHECK DATI DALLA RETE (il pezzo richiesto): IB certificato (eq_*, ADJUSTED) vs
   Yahoo adjclose (sorgente rete indipendente, tokenless). Tutti CONCORDE <=1.2bps
   sui rendimenti. Teaching: un confronto naif (adjusted vs grezzo) falso-allarmava
   4/6 ticker a 30-52bps = TUTTO stacco dividendo -> ogni divergenza va SPIEGATA
   prima di gridare 'feed sporco' (v2.0.0). Strumento riutilizzabile (validatore feed
   / pre-trade price-check).

2) Scalping 'sottoquotate': NON testabile (no dati intraday) ne' eseguibile (PDT rule
   5k blocca il day-trading; IB instabile). Versione testabile = swing MR (Connors
   RSI2<10 + MA200, exit MA5): Sharpe modesto (SPY 0.75/0.70) ma NON batte il buy&hold
   (B&H hold 0.81), expo 13%, CAGR 2-5%, fee-sensitive. Niente edge schierabile.

- scripts/research/eq_meanrev_ib.py
- tests/test_eq_meanrev.py (incl. network check)
- docs/diary/2026-06-26-equity-meanrev-network-check.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 19:42:14 +00:00
Adriano Dal Pastro 8d559c6f33 merge(research): gamma-scalp + cash-carry + TP01×DVOL + vol-termstructure
Analisi onesta di 5 angoli (tutti su dati certificati, leak-free, netto fee,
scoring marginale vs TP01, vincoli eseguibilita' a $600):
- gamma scalping (scalp+opzioni)  -> SCARTATO (specchio del VRP, perde ogni freq)
- funding cross-sectional (FC01)  -> gia' morto (DILUTES)
- cash-and-carry (CC01)           -> premio reale ma Sharpe artefatto, STAT-MODE -> lead
- TP01 x DVOL vol-targeting       -> non migliora (de-levering, non timing)
- calendar-vol / term-structure   -> dato storico non pubblico -> forward logger (gia' su main)

Zero impatto sul codice live: solo script di ricerca + test + diari + note CLAUDE.md.
Il forward logger era gia' stato cablato in cron su main (555977d).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 19:28:54 +00:00
Adriano Dal Pastro 555977d987 feat(research): forward logger della vol term-structure + cron giornaliero
La storia per-scadenza non e' pubblica su Deribit -> calendar-vol non backtestabile
ora (data-first gate). Unica via: costruire il dato in avanti. Aggiunto logger
idempotente (interpola ATM IV a tenor fissi {7,30,60,90,180}g -> data/raw/vol_term_*)
+ wrapper cron giornaliero. SOLO ricerca forward: non tocca il book live ne' i dati
certificati. Analisi completa (gamma scalp/cash-carry/dvol/feasibility) sul branch
research/gamma-scalp-options.

- scripts/research/log_vol_termstructure.py + probe_vol_termstructure.py
- scripts/cron_vol_term.sh
- tests/test_vol_termstructure.py

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 19:27:15 +00:00
Adriano Dal Pastro 8c3868cb31 research(vol): calendar-vol non backtestabile — data-first gate + forward logger
Angolo term-structure DVOL / calendar-vol. Scan di fattibilita' PRIMA del backtest:
la storia per-scadenza NON e' pubblica su Deribit (DVOL solo 30g; trade-history IV
solo per strumenti vivi; il front rotola/espira -> serie continua front-vs-back
irricostruibile). Per la metodologia (niente edge senza OOS su dati certi) -> STOP,
niente backtest su uno snapshot.

Unica via legittima: costruire il dato IN AVANTI. Aggiunto logger forward idempotente
che interpola l'ATM IV a tenor fissi {7,30,60,90,180}g e accumula data/raw/vol_term_*.
Seminati i primi snapshot (oggi: contango lieve su BTC/ETH). Non auto-cablato in cron.

- scripts/research/probe_vol_termstructure.py (scan fattibilita')
- scripts/research/log_vol_termstructure.py (forward dataset builder)
- tests/test_vol_termstructure.py (interpolazione offline)
- docs/diary/2026-06-26-vol-termstructure-feasibility.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 19:18:59 +00:00
Adriano Dal Pastro 9d586eeb58 research(tp01): DVOL vol-targeting non migliora TP01 (de-levering, non timing)
Angolo ESEGUIBILE (tocca il book live): DVOL (vol implicita forward-looking) come
denominatore del vol-target invece della realizzata. Finestra comune 2021-2026.

Le varianti DVOL abbassano DD (12.3->9.2%) ma anche Sharpe FULL (0.75->0.70) e CAGR.
Controllo decisivo: realized @ vol-tgt 15% eguaglia quel DD (9.4%) a Sharpe piu' alto
(0.75) -> il taglio di DD del DVOL e' solo DE-LEVERING, replicabile meglio con un
target_vol piu' basso. Hold-out +0.06 = single-window (storia DVOL <5y), sotto la
soglia multi-cut. Gate DVOL-spike ridondante col trend (TP01 gia' flat nei crash).

Lezione: per meno DD sul live la leva e' target_vol, non un overlay DVOL.

- scripts/research/tp01_dvol_overlay.py (realized/dvol/blend/max/derisk + controllo target_vol)
- tests/test_tp01_dvol_overlay.py
- docs/diary/2026-06-26-tp01-dvol-overlay.md
- CLAUDE.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 18:56:56 +00:00
Adriano Dal Pastro 69e3517f1b research(carry): cash-and-carry CC01 — premio reale, Sharpe artefatto, non deployabile
Provato l'angolo basis/cash-and-carry (l'altro proposto; il funding cross-sectional
FC01 era gia' SCARTATO 2026-06-22). Delta-neutral long-spot/short-perp -> r=funding,
zero esposizione prezzo.

Premio di funding REALE (~+8-14%/anno aggregato, positivo ogni anno in-sample,
ortogonale a TP01). MA Sharpe modellato 11-13 = ARTEFATTO: rischi di coda fuori
dal dataset (manca il 2022; procyclico +23% 2024 -> +1.7% 2026; liquidazione/slippage
non modellati). Il mark-to-market della base (premium col) sgonfia solo 13->11 ->
il basis-from-data non e' il rischio vero. NON eseguibile a $600 (spot+perp, funding
HL non Deribit) -> STAT-MODE. LEAD da rivedere a scala, non uno sleeve.

Sottoprodotto: CC01 passa ogni gate del marginal scorer -> punto cieco (manca un
gate 'Sharpe implausibile -> rischio nascosto').

- scripts/research/cash_carry_hl.py (CC-static/gated, BTC-ETH + 19-major, basis MtM, reality-check)
- tests/test_cash_carry.py (lock del fatto economico, non dello Sharpe)
- docs/diary/2026-06-26-cash-carry-hl.md
- CLAUDE.md: riga nella sintesi di ricerca

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 18:46:14 +00:00
Adriano Dal Pastro cf72e395d3 research(options): gamma scalping (long-vol) — SCARTATO
"Scalping BTC/ETH con copertura in opzioni" = gamma scalping, lo specchio
esatto del VRP01 (long straddle ATM + delta-hedge -> incassa RV-IV).

Esito: perde ogni anno / ogni variante / ogni frequenza (Sharpe -3 a -6).
Diagnostica strutturale: a 1d IV>=RV (paghi il VRP); a 1h RV>IV gross ma il
rehedge orario paga 24x la fee di hedge -> variante peggiore. Marginale vs TP01
= DILUTES, non e' nemmeno un hedge. Muro eseguibilita': opzione BTC min $5968 >> $600.

Schiacciato tra due muri: rehedge lento = premio, veloce = fee -> nessuna
frequenza vince. Il VRP01 (lato short, gated) resta l'unico edge opzioni.

- scripts/research/options_gamma_scalp.py (harness: naked/cheap/rich, 1d+1h, diagnostica RV-IV)
- tests/test_gamma_scalp.py (lock della conclusione)
- docs/diary/2026-06-26-gamma-scalp-options.md
- CLAUDE.md: riga nella sintesi di ricerca

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-26 18:36:48 +00:00
Adriano Dal Pastro db738bce3b feat(live): arma il BOOK DERIBIT (TP01+SKH01 nettati in software)
Estende l'esecuzione live da TP01-only al book Deribit-only completo. TP01 e SKH01
tradano lo STESSO strumento (una sola posizione netta per conto su Deribit) -> netting
in software: un solo ordine/asset verso il target netto.

- src/live/book.py: target NETTO per asset = clamp(0.5*E*(0.75*tp_frac + 0.25*skh_sign), ±cap).
  Riusa current_target (TP01, causale) + _skyhook_positions (segno L/S, book 230m) + conto reale.
- src/live/execution.py: rebalance_signed() — reconcile CON SEGNO (long/short, flip via close+open,
  reduce reduce_only). La close resta sempre permessa (si esce da qualunque posizione).
- src/live/livefeed.py: fresh_5m() — feed 5m certificato + coda recente EFFIMERA da Deribit pubblico
  (stesso simbolo inverse, in-memory, NON scrive su disco -> dati certificati intatti; fallback al
  certificato su errore). Solo SKH01 ne ha bisogno (e' a 230m); TP01 e' giornaliero.
- scripts/live/book_execute.py: executor doppio-gate (config + --execute), disaster-SL on-book sulla
  posizione netta, log in data/live/book_executions.jsonl. Feed SKH fresco (live_feed=True).
- scripts/cron_book.sh + crontab ORARIO: book idempotente ogni ora (riconcilia al netto corrente);
  rimossa la riga live_execute.py (TP01-only) dal cron daily per non far collidere i due.
- config/live.json: ARMATO (execution_enabled=true). cap/asset $300 split 75/25, disaster-SL -30%.
  Tutto flat all'arming -> nessun ordine finche' un segnale non arma.
- tests/test_book_live.py: 20 test (sizing 75/25, cap, flip/close/reduce, parita' pesi backtest,
  gate-safety, reconcile con trader fittizio, merge/dedup feed + fallback, loader onorato). 76/76 pass.

CAVEAT: exit SKH SOFTWARE (latenza fino a fine barra 230m; solo disaster-SL on-book); TP01 scende a
peso 0.75 (max $225/asset); SKH01 resta research-grade (equity daily-step, margine DD ETH sottile).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 21:43:27 +00:00
Adriano Dal Pastro 25a22fc7c1 feat(dashboard): riordino LIVE→trades→storico + trade/anno contati
- dashboard riorganizzata in 3 sezioni: ① LIVE (mainnet sola lettura) in
  alto, ② TRADES ESEGUITI (reali) + frequenza operativa al centro,
  ③ STORICO (backtest/forward simulato) in fondo (COMBO/BOOK/FORWARD come ③·a/b/c).
- book_trade_frequency() in sleeves.py: trade/anno CONTATI sui dati certificati
  (cache di modulo, una volta per processo). SKH01 round-trip BTC ~37 / ETH ~43
  -> ~75/anno combinato; TP01 turnover ~7x/anno. Card "trade/anno" + blocco freq.
- fix: collisione var `pos` nel ramo shadow-online (-> shpos) che avrebbe rotto
  la tabella posizioni se il conto fosse leggibile dal container.
- fix: turnover TP01 nan (disallineamento groupby) -> groupby posizionale, 7.2x/anno.
- 56 test pass.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 21:18:52 +00:00
Adriano Dal Pastro eeac97dde4 feat(dashboard): Deribit-only book panel (TP01+SKH01) + accumulation forecast
New section showing the executable Deribit-only book (TP01 75% + SKH01 25%): combined
FULL/HOLD Sharpe+DD, plus the reinvest-winnings accumulation projection (historical &
conservative CAGR, €5k→5y/10y, conservative €/day run-rate). Reuses the already-computed
sleeve daily series (no extra heavy compute). Honest caveats (bull sample, no leverage,
SKH01 not live, ~€177k for €50/day).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 20:43:47 +00:00
Adriano Dal Pastro c8a390d6b7 feat(portfolio): reproducible accumulation forecast for the Deribit book
scripts/portfolio/forecast_deribit_book.py — projects the Deribit-only book (TP01+SKH01)
forward by pure compounding (reinvest winnings), monthly-aligned, NO external contributions
(not a PAC). Deterministic @historical & @conservative CAGR + Monte-Carlo block-bootstrap
(median/p10/p90), plus €/day run-rate @conservative. Parametric (--capital/--years/--cons-frac).
Honest caveats baked in (bull-crypto sample, no leverage, SKH01 not live, conditional projection).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 20:42:14 +00:00
Adriano Dal Pastro 384b9cb0af feat(skyhook): pos_fn introspection for SKH01 sleeve (current open trade / flat)
_skyhook_positions(): replays the non-overlap entry+exit logic (TP/SL/max_bars) to the last
closed 230m bar and reports, per asset, the current OPEN trade (dir/entry/sl/tp/bars_in) or
'flat'. Wired into skyhook_sleeve(pos_fn=...) so the Deribit book report & web dashboard show
Skyhook's live position. Causal (closed bars only). +1 test. Currently flat/flat.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 20:32:14 +00:00
Adriano Dal Pastro 160ad300be feat(portfolio): Deribit-only executable book (TP01+SKH01) + periodic rebalancing
- deribit_book_sleeves(): TP01 75% + SKH01 25% — the two directional BTC/ETH legs on
  ONE venue (Deribit), both since 2019. Excludes XS01 (Hyperliquid/stat-mode) & VRP01
  (modeled options). FULL Sharpe 1.78 / HOLD 1.17 / DD 9.4% (research).
- rebalance_sim(): realistic PERIODIC rebalancing (drift between dates, turnover cost at
  Deribit-taker ~5bps/side) vs the idealized continuous rebalance of combined_daily.
  period=1 + cost=0 reduces to continuous (tested).
- run_deribit_book.py: report — continuous vs weekly/biweekly/monthly rebal, per-year,
  accumulation €2k & $600-real, min-order $5 note. Finding: turnover is LOW (0.2-0.4x/yr),
  so monthly rebal (€7,919) ~= continuous (€7,938) — cost is negligible; daily would be
  sub-min-order fiction at $600 -> use >= weekly.
- +2 tests (rebalance_sim continuity & cost). Full suite green.

TP01 is the only live-armed leg; SKH01 is the candidate 2nd leg (validate execution code first).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 20:26:53 +00:00
Adriano Dal Pastro 50e2adf837 merge(skyhook): SKH01-V2-DD strategy + 4-sleeve portfolio + dashboard
Brings the Skyhook line into main:
- SKH01 dual-TF regime+breakout engine (BTC/ETH, causal, honest harness)
- 2 multi-agent research waves -> SKH01-V2-DD (asymmetric %-exits, standalone
  maxDD <30%, minHold +1.26, marginal ADDS vs TP01)
- wired as 4th portfolio sleeve @25% effective: FULL Sharpe 1.68->2.13, DD 14->8%
- dashboard shows the 4-sleeve view; tests 25 pass

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 16:42:15 +00:00
Adriano Dal Pastro 7eb0f67956 feat(dashboard): show SKH01 sleeve in 4-sleeve portfolio view
active_sleeves() already feeds the per-sleeve table & combined metrics, so SKH01
appears automatically. Manual touch-ups: title/docstring -> +SKH01; position label
is now sleeve-aware (the None fallback used to mislabel every pos-fn-less sleeve as
XS01's "book 19 gambe" — now XS01/SKH01/VRP01 get correct labels); footer note adds
SKH01 (quasi-orthogonal @25%, FULL Sharpe 1.68->2.13, DD 14->8%, research/forward-monitor).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 16:41:52 +00:00
Adriano Dal Pastro 8d1fe173f7 feat(portfolio): wire SKH01-V2-DD sleeve @25% effective -> 4-sleeve book
Add Skyhook (SKH01_V2_DD) as a portfolio sleeve. Effective weight 25%: the three
existing sleeves scaled into the remaining 0.75 keeping their 55:25:20 ratio
(TP01 41.25% / XS01 18.75% / VRP01 15% / SKH01 25%).

_skyhook_returns(): 50/50 BTC+ETH daily series of the dual-TF regime+breakout engine
(causal, net 0.10% RT), same convention as the marginal lens.

Portfolio impact (run_portfolio.py), 3-sleeve -> 4-sleeve:
  FULL Sharpe 1.68 -> 2.13 (+0.45), FULL maxDD 14.3% -> 7.8% (halved)
  HOLD-OUT Sharpe 1.63 -> 2.30 (+0.67), HOLD-OUT maxDD ~3.5% (flat)
  Positive every year 2019-26 (annual DD <=7.8%) vs buy&hold 50/50 FULL Sh 0.93 / DD 76%.

Skyhook is quasi-orthogonal (corr ~0.09 to TP01) so it lifts Sharpe AND cuts DD.
Research portfolio (fixed weights, no real rebalancing cost at $600; Skyhook daily
Sharpe is the step-marked lens convention) -> forward-monitor, not deploy.
Tests: 25 pass (skyhook 8 + portfolio 7 + vrp 4 + trend 6). Diary + CLAUDE.md updated.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 16:22:15 +00:00
Adriano Dal Pastro de72e3ce1f feat(skyhook): SKH01-V2-DD — asymmetric %-exits cut standalone DD <30% (2-wave agent research)
Second agent wave (skyhook-improve-v2, 14 DD-reduction families, each adversarially
verified by 2 skeptics) beats the prior winner on the only unmet goal (DD<30%).

Winner = ASYM_LS -> promoted to engine as SKH01_V2_DD:
  same signal (ptn_n=45, vola[35,95], vol_lo=0, exit-bars 24/16) but exits switched
  from ATR to FIXED-PCT ASYMMETRIC — long sl4%/tp10%, short sl2%(tighter)/tp8%.
  The tight short %-SL caps the per-trade loss that forms the maxDD in vol spikes.

Verified (sk.study, independent re-run): standalone maxDD BTC 21.4% / ETH 27.4% (<30%),
minFull +0.99, minHold +1.26, causality 0/400 both assets, fee-surviving to 0.40%RT,
marginal vs TP01 ADDS (corr 0.09, in-sample edge, robust_oos, multicut, clean-year +0.57),
blend 0.75*TP01+0.25*SKH uplift_hold +0.87; blend 50/50 full 1.84/hold 1.59/DD 10.7%.
Plateau (not knife-edge); both skeptics holds_up=high, killer=null.

Engine: per-direction short exit overrides (exit_mode_short/sl_*_short/tp_*_short),
backward-compatible (None -> symmetric, V1/intermediate-winner unchanged). +3 tests (8/8 pass).

Lessons: DD is cut by changing the exit MECHANISM (%-SL, L/S asymmetry, ensembles), NOT by
entry-only kill-switch / vol-target / cadence. PATTERN_CONF killed as overfit (knife-edge).
PCTL_DD unverified (rate-limit) and ENS_PARAM/TPSL_DD recency/hedge-loaded -> forward-monitor.
NOT yet wired to live sleeves: re-verify blend@0.25 + causality on execution code before deploy.

Includes both waves' research scripts (runs/SKH_* wave 1, runs/SKH2_* wave 2).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 16:10:38 +00:00
Adriano Dal Pastro 8e46a62e67 docs(skyhook): diario porting SKH01 + V1 (sintesi onda agenti in aggiornamento)
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 14:47:41 +00:00
Adriano Dal Pastro c7c07f4c35 test(skyhook): demo anchors + dual-TF alignment + causality + V1 robustness (5 pass)
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 14:46:47 +00:00
Adriano Dal Pastro 2d8faf3896 research(skyhook): inline lever-scout -> shorts essential, regime gate matters, ptn_n=55/vol_lo=40/wider-stops lift hold-out
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 14:35:35 +00:00
Adriano Dal Pastro 64d98a070d feat(skyhook): SKH01 dual-TF regime+breakout engine + honest eval harness
Porting onesto del sistema ES Skyhook su BTC/ETH certificati:
- src/strategies/skyhook.py: 690m(segnale)+230m(exec) da 5m; BuzVola/BuzVolume
  Chande 0-100 (ancore demo verificate); Donchian breakout HTF; regime gate;
  composer; entries asimmetrici (uscitalong/short + stop/profit ATR) per backtest_signals.
- scripts/research/skyhook/skyhooklib.py: study (FULL/HOLD/fee-sweep/per-anno BTC&ETH),
  causality guard (0 mismatch), marginal-vs-TP01.
Baseline: BTC FULL Sh +0.91/+581%, ETH +0.64/+255%, fee-surviving, ma HOLD-OUT debole -> da migliorare.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 14:33:54 +00:00
Adriano Dal Pastro 237ca8da13 research(report): resoconto PROTETTO (soft-guard DD -4%) anno-per-anno -> combo + TP01 + GTAA singoli
Report che mette combo (TP01+GTAA 50/50), TP01 e GTAA sulla stessa griglia giorni-di-borsa
(esposizione 1x, come dentro al combo), applica la guardia-DD -4% a ciascuna serie e tira fuori
per anno: NL (net liquidation da $2000), DD intra-anno, rendimento, Sharpe + riga TOT con CAGR.
Combo protetto: CAGR +9.1% / DD 5.8% / Sh 1.38 (2022 -1.8%); baseline +11.3% / 8.4% / 1.48.
Aggiunto data/paper_combo/ al .gitignore (stato paper runtime, come gli altri paper dir).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 14:16:59 +00:00
Adriano Dal Pastro 856a02fcc5 research(stops): SL classici vs soft-guard -> il soft-guard vince (lo SL duro whippa nel grind)
Goal 'prova anche SL'. Test equo (trigger/re-entry sul NAV mercato). soft-guard -4% Sh 1.38/DD 5.8%
resta il migliore; trail-stop -6% valido ma inferiore (1.34/6.6%); -4% whipsaw (1.07, inMkt 42%);
stop mensile/vol inutili. Per un DD da grind, de-risk parziale > uscita totale.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 13:09:43 +00:00
Adriano Dal Pastro 010d1f0733 feat(combo): paper combo NUDO vs PROTETTO (guardia-DD -4%) affiancati + dashboard
paper_combo traccia forward entrambe le versioni; dashboard mostra nudo + protetto. Guardia-DD:
de-risk 0.4x a DD>-4%, ri-rischia a -1.6% (backtest MaxDD 8.4->5.8%, 2022 -4.4->-1.8%). Opzioni
escluse (non aiutano il grind). Container ricostruito.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:59:07 +00:00
Adriano Dal Pastro 1c15c3c1be research(tail-hedge): protezione DD combo (incl. opzioni) -> vince la guardia-drawdown
Goal: sleeve/overlay protettivo per il combo (TP01+GTAA), anni tipo 2022, valutare opzioni.
Diagnosi: DD combo 8.4% e' grind-lento (2022 -4.4%), non crash -> il doppio trend gia' taglia i crash.

Test (tail_hedge_lab.py): guardia-DD -4% -> MaxDD 8.4->5.8%, 2022 -4.4->-1.8%, Sharpe 1.48->1.38,
CAGR 9.2%. Vol-target NON aiuta (2022 non e' vol-spike). OPZIONI (put/put-spread LONG su BTC/ETH,
premio BS su DVOL): sempre-on ~50%/anno -> con budget 3%/y effetto ~nullo, e nel grind 2022 sanguinano;
pagano solo nei crash secchi (stress -30%: put +25% netto). -> black-swan insurance cara, fuori
bersaglio per il 2022. A leva: guard rende il 2x sopportabile (2022 -10.9%), il 3x resta margin-call.

RACCOMANDAZIONE: aggiungere guardia-drawdown di portafoglio (no premio); opzioni solo eventuale
micro-hedge black-swan. Costo onesto del guard: -2.1pp CAGR per dimezzare il MaxDD.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:55:14 +00:00
Adriano Dal Pastro 3a3bdd5c7b research(report): sim leva 1x/2x/3x combo vs TP01 (DD reale + margin-call), da 2k/5k
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:44:54 +00:00
Adriano Dal Pastro f983cc2447 research(report): resoconto anno-per-anno combo/TP01/GTAA da $2k (PnL/MaxDD/NumTrades)
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:37:23 +00:00
Adriano Dal Pastro 389573e517 feat(dashboard): pannello COMBO cross-venue (TP01 Deribit + GTAA IB)
Aggiunge alla dashboard la sezione "COMBO DEPLOYABLE — cross-venue (paper)": equity paper forward
del blend 50/50 TP01+GTAA (da data/paper_combo/state.json) + posizioni azionabili IB correnti
(gtaa_weights: peso ETF + cash, asof). Nota onesta: paper rischio-zero, Sharpe ~1.5 ottimistico, il
robusto e' la diversificazione (corr 0.21, DD dimezzato); XS01/VRP01 esclusi (STAT-MODE).
Container ricostruito (codice baked nell'immagine).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:32:19 +00:00
Adriano Dal Pastro 3b552a92da feat(combo): paper-trade cross-venue TP01 (Deribit) + GTAA (IB), forward-only
L'unica cosa vera/deployabile della ricerca: diversificazione TP01+GTAA (corr 0.21, blend Sharpe ~1.5,
DD dimezzato). Si va in PAPER cross-venue.

- src/portfolio/gtaa.py: GTAA sleeve di prima classe (trend difensivo TSMOM vol-target 12% su
  SPY/QQQ/IWM/TLT/GLD/HYG). gtaa_returns() Sharpe 0.64; gtaa_weights() = pesi ETF correnti azionabili.
- scripts/live/paper_combo.py: tracker forward-only blend 50/50 TP01+GTAA (crypto compoundato su grid
  giorni-di-borsa), mostra posizioni azionabili su entrambi i venue. Solo gambe eseguibili.
- fetch_ib_equities.py --only: refresh mirato dei 6 ETF GTAA per il cron.
- cron_daily.sh: up gateway IB + refresh ETF GTAA + avanza paper_combo (dipendenza cross-venue gestita).

Init 2026-06-23: TP01 flat (risk-off), GTAA SPY13/QQQ8/IWM9/TLT17/GLD2/HYG17/cash34. Catena
gateway->refresh->paper testata end-to-end. PAPER (rischio zero), valida l'operativita' cross-venue.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:26:51 +00:00
Adriano Dal Pastro 09c8bb7de8 research(cross-market): oltre SP500 (bond/commodity/indici esteri) -> niente, artefatto di confine UTC
Esteso il test crypto-lead a ZN(bond), ESTX50/DAX(Europa), NKD(Nikkei) via futures orari IB
(commodity GC/CL/HG bloccate da subscription). Test non-sovrapposto crypto[T-8h->T]->future[T->T+6h].

ES/NQ/RTY niente (gia'); ZN negativo; NKD debole (~overnight drift). ESTX50/DAX SEMBRANO fortissimi
(t_crypto 7.8, Sharpe 2.5, 3/3 anni) MA e' artefatto di confine UTC: picco a coltello a T=00:00,
morto a T=1h; GAP di 1h uccide l'effetto (Sharpe 2.45->-0.52); tutto l'edge nella singola barra
00:00->01:00 (Sh +2.93) vs ora dopo (-1.02). Firma esatta di day_boundary_robust (CLAUDE.md).

VERDETTO: nessuna anticipazione crypto->mercato sfruttabile, ne' SP500 ne' altro. Sempre co-movimento
contemporaneo (risk-beta) o artefatto di confine. Resta valido solo il diversificatore TP01+GTAA.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 12:12:16 +00:00
Adriano Dal Pastro c4bc336a53 research(cross-market): futures overnight non-sovrapposto -> edge ~0 su SP500, soffio su small-cap
Test ONESTO dell'idea "monitor Deribit/trade IB": entra mid-notte sul future indice, cattura il moto
SUCCESSIVO (finestre non sovrapposte, no look-ahead). Dati: ES/NQ/RTY orari da IB (fut_*_1h, ~3y).

RISULTATO: ES (S&P500) nessun edge (Sharpe ~0/neg, t_crypto 0-1.5); NQ momentum del future non crypto;
RTY (small-cap) unico con t_crypto incrementale 2.0-2.7 e crypto che aggiunge oltre il moto proprio del
future, ma Sharpe 0.4-0.5, 24 config (multiple-testing), 2.3y, per-anno incoerente (2026 negativo).

VERDETTO: l'idea NON da' edge tradabile, men che meno su SP500. Il forte crypto<->equity e' co-movimento
contemporaneo (risk-beta), non anticipazione: imposta una finestra causale non-sovrapposta e svanisce.
Il "Sharpe 5" del gap era look-ahead. RTY -> forward-monitor al piu'. Coerente col soffitto del progetto.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 11:51:15 +00:00
Adriano Dal Pastro 55c337144e research(cross-market): "monitor Deribit/trade IB" gap = LOOK-AHEAD, edge tradabile ~0
L'idea (segnale crypto overnight -> trade indice IB) sembrava Sharpe 3.6-5.9 ma e' look-ahead:
la finestra segnale crypto [P21:00->D13:00] e il gap equity [Pclose->Dopen] coprono le stesse ore.
All'entrata (D13:00, pre-open) il gap e' gia' avvenuto -> non catturabile con l'ETF.
Decomposizione (net 2bps, sqrt252): OVERLAP gap Sh ~3.6-4.0 (artefatto) vs TRADABILE intraday
Sh -0.03..0.25 (reale, ~0, muore a costi). Conferma/rafforza "non deployabile" del workflow.
Resta possibile solo la versione futures mid-overnight (finestre non sovrapposte) -> serve dato
intraday ES/NQ, non in cache.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-23 11:23:18 +00:00
Adriano Dal Pastro d916520f2c research(cross-market): sweep 65-agenti crypto->mercati IB -> fenomeno gap robustissimo ma NON edge
Goal: >=50 agenti, migliore soluzione, diversi mercati e timing, su piu' anni.
Setup: 26 ETF certificati (IB) + BTC/ETH 1h; harness parametrizzato (lead overnight crypto ->
gap/intraday equity, t-incrementale, Sharpe IS/OOS, hit per-anno); workflow 416 config = 52 sweep +
12 verifica avversariale + 1 sintesi = 65 agenti.

RISULTATO: cluster fortissimo crypto-overnight -> GAP apertura equity (tutti i target risk-on).
Migliori: ETH->IWM/QQQ/XLK gap (Sh OOS 2.4-2.5, t 17), BTC->QQQ gap (Sh OOS 2.31, t 15, 9/9 ANNI).
Regge stress 10bps e OOS recente. MA due killer (verificatori concordi):
  1. NON tradabile via ETF (gap gia' all'open) -> serve future overnight (MNQ/MES), fuori dal
     capitale $0.5-2k (margin/liquidazione);
  2. e' RISK-BETA non alpha: finestra-lead ~contemporanea al gap (stesso shock macro), forza solo
     negli anni alta-vol (2022), beta implicito ~37%.
Unico ETF-tradabile (ETH->XLE intraday) crolla a 10bps (0.48->0.15), t 2.38 sotto Bonferroni/416.

VERDETTO: nessun edge proprietario deployabile a basso capitale. Migliore FENOMENO da forward-monitor
= BTC->QQQ gap overnight (9/9 anni). Coerente col soffitto del progetto. Valore: aver classificato il
fenomeno (risk-beta overnight) invece di scambiarlo per alpha.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 22:32:28 +00:00
Adriano Dal Pastro d2d535cf6a research(cross-market): crypto x mercati IB -> trovata ANTICIPAZIONE weekend-crypto -> lunedi' equity
Goal: cercare correlazioni/anticipazioni crypto<->IB. Dati cache (BTC/ETH Deribit 1h->1d; ETF eq_*).

(1) Correlazione contemporanea: crypto = risk-on (BTC ~0.32 SPY/QQQ/IWM, 0.25 HYG, 0.13 GLD, ~0 TLT).
(2) Lead-lag GIORNALIERO: NIENTE (picco k=0, rumore a |k|>=1) -> nessuno anticipa l'altro al daily.
(3) EFFETTO WEEKEND (anticipazione pulita): crypto Sab+Dom (equity chiuso) anticipa il lunedi'.
    GAP lunedi' corr +0.22/0.24 (SPY/QQQ/IWM/HYG), hit 59-62%, si RAFFORZA OOS22+ (+0.30/0.36).

Validazione avversariale:
  (A) INCREMENTALE vs venerdi': beta weekend-crypto significativo (QQQ gap t=+4.7, intr +2.9; SPY
      +4.4/+2.0; IWM +4.7/+2.7), friday_eq NON signif. -> info crypto-specifica, non momentum equity.
  (B) TRADABILE (entro Mon open, esco close, net 4bps): QQQ hit 60%, Sharpe 1.46 (OOS 1.33), long-flat
      OOS 1.91 ~+9%/yr; SPY/IWM piu' deboli ma OOS positivi.

VERDETTO: prima anticipazione cross-mercato reale. Crypto = proxy 24/7 risk-sentiment; lunedi' equity
recupera la direzione del weekend. Caveat: capacita' bassa (~52 lun/anno), tattico non cornerstone;
gap catturabile via futures IB (MNQ domenica sera) da validare. Coerente su 3 ETF (no cherry-pick).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 21:55:01 +00:00
Adriano Dal Pastro 67850b0dd8 research(equities): valida combo DEPLOYABLE TP01+GTAA (le due gambe eseguibili)
Combo onesto/eseguibile a basso capitale: TP01 (Deribit, gia' armato) + GTAA vt12 (IB), senza
XS01/VRP01 STAT-MODE. Finestra 2019-2026, TP01 compoundato sui giorni di borsa.

RISULTATO: corr TP01<->GTAA +0.21; blend 50/50 Sharpe 1.48 (40/60 e risk-parity 1.52) > best solo
1.25, maxDD 14%->8%. DIVERSIFICA anche da deployable.
CAVEAT: 2022 negativo (-2.64, trend whipsaw su entrambe), anni boom gonfiano l'assoluto (recenti
~0.95) -> il dato robusto e' il +0.27 di diversificazione, non il livello. Costo deployability:
crypto-pieno+GTAA 1.81 vs 1.48 (i ~0.33 persi = XS01/VRP01 non eseguibili). Cross-venue Deribit+IB.

Migliore config rischio-aggiustata EFFETTIVAMENTE eseguibile trovata post-reset. Non risolve EUR50/g
(capitale). Prossimo: paper-trade GTAA su IB (forward-only) per validare l'esecuzione cross-venue.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 21:48:35 +00:00
Adriano Dal Pastro 437cf11199 research(equities): EQ-GTAA01 trend multi-asset + COMBO cross-mercato (diversifica il crypto)
(1) GTAA: trend difensivo long-flat su SPY/QQQ/IWM/TLT/GLD/HYG (EW sugli asset disponibili).
  GTAA lf vt12%: Sharpe 0.64 (OOS 0.89), maxDD 15% (8% sui 6-asset 2016+), corr SPY 0.64.
  Migliore sleeve equity: rischio-aggiustato > mono-SPY, DD bassissimo, diversificatore migliore.
  Difensiva (CAGR basso). Bear DD: GFC 14% vs 55%, COVID 10% vs 34%.

(2) COMBO cross-mercato: crypto (TP01+XS01+VRP01) x equity (GTAA vt12), finestra 2019-2026.
  corr crypto<->equity = +0.17 (bassissima). blend 50/50 Sharpe 1.81 > crypto solo 1.60 >
  equity 1.12; maxDD dimezzato 14%->7%. DIVERSIFICA: primo miglioramento STRUTTURALE del
  rischio-aggiustato complessivo della ricerca post-reset (diversificazione vera, non alpha).

CAVEAT: finestra crypto corta/favorevole (Sharpe assoluti ottimistici), cross-venue Deribit+IB,
XS01/VRP01 STAT-MODE -> il combo deployable reale e' ~TP01+GTAA. Non risolve EUR50/g (capitale).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 21:42:42 +00:00
Adriano Dal Pastro c9b89739c1 research(equities): EQ-TREND01 trend difensivo su SPY = edge difensivo REALE (analogo TP01)
Il cross-section e' morto (EQ-MOM01), ma il trend DIFENSIVO time-series su SPY regge — stesso
tipo di TP01 nel crypto. TSMOM multi-orizzonte / SMA-200 long-flat, causale, netto fee, OOS 2015+.

RISULTATO: Sharpe 0.54->0.62/0.65, maxDD DIMEZZATO (55%->~27%; nei bear lenti piu': GFC 19% vs
55%, dot-com 26% vs 49%, COVID 17% vs 34%). Plateau robusto (0.56-0.65), fee-robusto (0.48 a
0.10%/lato), basso turnover, eseguibile a $0.5-2k (switch mensile SPY/cash). SMA-200 = piu'
semplice E migliore.

CAVEAT: e' risk-management non alpha (CAGR -2/3pp); i tagli grossi sono in-sample (OOS 2015-26
quasi tutto toro -> ha seguito SPY a beta minore, ma COVID dimezzato). long-bonds TLT non convince.

Lezione cross-mercato confermata: il valore robusto e' ridurre il rischio (trend long-flat), non
battere il buy&hold. Prossimo: trend multi-asset/GTAA + diversifica la sleeve crypto?

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 21:37:37 +00:00
Adriano Dal Pastro 03267b8fc3 research(equities): EQ-MOM01 momentum settoriale -> NON batte SPY
Primo backtest del fronte equity. Momentum cross-sectional settoriale (9 SPDR, 1998-2026),
causale, netto fee, OOS 2015+, giudicato marginale vs SPY buy&hold (il baseline equity).

VERDETTO: nessun edge. Long-short Sharpe -0.08 (alpha cross-sectional MORTO su 27y,
decadimento post-2000 noto). Long-only ~= SPY (corr 0.85, uplift marginale ~0.00) = SPY a
beta piu' basso. Plateau stabile ~0.50 vs SPY 0.51; sugli 11 settori (2018+) peggio (0.69
vs 0.82). L'unico beneficio (maxDD 55->39%) e' del vol-target, non del momentum.

Coerente col progetto: il relative-value momentum e' morto anche in equity (come ortho wave
nel crypto). Prossimo angolo: TS-trend difensivo su SPY (analogo equity di TP01) per tagliare
il drawdown, non per battere il CAGR.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 21:33:38 +00:00
Adriano Dal Pastro 1c0b5f1869 research(equities): apre il fronte azioni/ETF via IB — dati certificati + cache su disco
Branch dedicato. Disciplina v2.0.0: prima il dato certificato, poi la strategia.
IB paper (gnzsnz/ib-gateway) da' storia daily ADJUSTED_LAST (div+split) profonda.

- ib_equities_probe.py: sonda fattibilita' dati (profondita', adjusted, subscription).
- fetch_ib_equities.py: FETCH+CERTIFY universo -> data/raw/eq_<sym>_1d.parquet (ms epoch,
  namespace dedicato). RIPARTIBILE (salta i parquet gia' scritti) -> niente refetch da IB.
  Certifica: integrita', gap lunghi, sanita' ritorni, sanita' adjustment.
- eqlib.py: harness ricerca equity. Legge la CACHE su disco (lru_cache) MAI da IB; universi
  (11 settori SPDR + 9 classici 1998+ + broad), panel allineato, riusa lo scorer indurito altlib.

UNIVERSO CERTIFICATO (17, data/raw/eq_* gitignored = cache locale):
  9 settori classici dal 1998-12-22 (27.5y) + XLRE(2015)/XLC(2018) + SPY(1996,30y)/QQQ/IWM/
  GLD(2004)/HYG(2007)/TLT(2016). Tutti integri (monotoni, no dup, no spike>50%, gap-lunghi 0).
  Start comune: 9 classici 1998, 11 settori 2018.

Prossimo passo: prima ricerca = momentum cross-sectional settoriale, gauntlet onesto.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 21:29:11 +00:00
Adriano Dal Pastro 61180637eb research(funding-carry): FC01 cross-sectional su HL -> fragile, NON regge + infra IB paper
Onda "nuova ricerca mirata". Unico meccanismo non coperto dalle 2 ondate: carry da
funding (cashflow perp, delta-neutral). Scan dati: price-clock gia' FAIL (intraday),
Deribit ccxt 0 righe, Cerbero solo candele -> fonte = API pubblica Hyperliquid.

- fetch_hl_funding.py: 19 major, funding orario reale dal 2023-05, certificato
  (0 gap, cov 98-100%, ann +1.0% APT .. +21.6% NEAR). backoff anti-429.
- funding_carry_hl.py: book dollar-neutral short-alto-funding/long-basso, causale come
  XS01, vol-target 20%, fee 0.05%/lato. Giudizio: marginal_vs_tp01 indurito + overlap XS01.

VERDETTO: il premio esiste (carry >> anti) ma il book NON regge il gauntlet.
  FULL -0.12, HOLD -0.50, DILUTES vs TP01, in-sample edge <0.5, no multicut.
  Jackknife universo: FULL oscilla [-0.39,+0.30] togliendo UN asset -> FRAGILE/overfit.
  (preview a 17 asset era +0.62 ADDS: fortuna, mancavano NEAR/AAVE). corr XS01 -0.19
  (ortogonale, non re-skin). Meccanismo: carry-vs-momentum, gli alto-funding pompano.
  -> NON entra in portafoglio, fetcher NON in cron. Diario completo.

Infra IB (thread parallelo): gateway paper gnzsnz/ib-gateway (127.0.0.1:4002, READ_ONLY)
in docker-compose + ib_probe.py. Esito dati basis CME micro: backtest NON fattibile
(ContFuture back-adjusted, scaduti=1 barra). IB ok per esecuzione/forward, non ricerca.
.env.ibgw gitignored (credenziali paper), template in .env.ibgw.example.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-22 20:56:18 +00:00
Adriano Dal Pastro 745ba7d066 research(portfolio): simula PREVDAY come overlay tail-hedge su TP01+XS01+VRP01 (NON deploy)
Simulazione d'impatto (registry di produzione invariato): riscala i 3 sleeve attivi a (1-W) e
aggiunge PREVDAY a peso W; sweep W {0,5,10,15,20%}. A 10%:
 - FULL Sharpe 1.68->1.88 (+0.20), maxDD 14.3%->9.9% (-31%): la gamba short ammortizza i crash storici.
 - HOLD-OUT Sharpe 1.66->1.97 (+0.31), ret +16.7->+19.0% (DD gia' bassissimo 3.4%).
 - 10% ~ ottimo di DD: oltre, lo Sharpe sale ma il maxDD smette di scendere (solo piu' rischio short).
 - per-anno: migliora/pareggia quasi ovunque; costa solo nel toro 2021 (premio hedge), paga nel bear 2022.

Caveat: tutto IN-SAMPLE (i guadagni assumono che l'edge persista -> e' cio' che il forward-monitor
verifica); outer-join gonfia il peso effettivo 2019-20 -> l'hold-out e' il read pulito a 10%. PREVDAY
resta FORWARD-MONITOR. Lo script e' il riferimento per ri-valutare l'overlay a forward maturo.

Diario: 2026-06-21-prevday-overlay-portfolio.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 20:01:20 +00:00
Adriano Dal Pastro 043f141bf1 research(intraday): PREVDAY block-bootstrap -> coda-fortuna vs persistente (blocker #2/#3)
Chiarimento: il "top-5 giorni = 76-83%" del diario era sulle gambe REVERT scartate, non su PREVDAY
(breakout). Test su PREVDAY stesso + gamba short (= tutto il valore). Block bootstrap circolare 20g B=3000.

[A] Concentrazione: PREVDAY-full NON e' piu' coda-fortuna di TP01 (top5 22% vs 19%; 14.3% dei giorni
per il 50% del gain vs 8.0% -> piu' distribuito). MA la gamba short e' tail-dipendente (top5=130% del
netto: togliendo i 5 giorni migliori va in perdita; sono i giorni-crash).

[B] Bootstrap: full robustissimo (uplift mediana +0.28, 99% dei resample >0); hold-out regge con coda
piu' larga (uplift mediana +0.53, 93% >0, 5deg pctl appena negativo per hold-out corto + short
tail-dipendente).

Verdetto: #3 tail-luck DECLASSATO per PREVDAY-full, CONFERMATO per la gamba short (payoff grumoso, su
<10 giorni-crash/anno); #2 null-corr-zero RIDIMENSIONATO (uplift genuinamente positivo, era efficienza
relativa). Sintesi trilogia: PREVDAY = tail-hedge legittimo e bootstrap-robusto, eseguibile a taglia
reale, payoff concentrato sui crash -> candidato overlay tail-hedge, non sleeve-alpha. Forward-monitor.

Diario: 2026-06-21-prevday-bootstrap.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 19:56:11 +00:00
Adriano Dal Pastro b388c462e8 research(intraday): PREVDAY turnover-reduction (no free lunch) + long-only probe (e' un HEDGE)
La fee (~2.6%/anno) viene dai ~70 flip/anno, non dal churn sub-dollaro (da fill_haircut). Sweep
delle leve che riducono i flip a livello di segnale (buffer k, anchor multi-giorno, min-hold):
 - allargare buffer/anchor taglia fee e turnover ma l'uplift hold-out del blend cala monotono
   (k0.30->0.50->0.75 = upl 0.56->0.40->0.00); anchor multi-giorno tutto peggio (conferma anchor=1).
 - min_hold=24h e' l'unico ritocco quasi-gratis (upl 0.56->0.60) ma peggiora il DD -27%->-32%.
 - la config congelata e' gia' sulla frontiera efficiente turnover<->edge -> nessun cambio.

Bonus blocker #1: long-only vs long-short. long-only ha Sharpe standalone PIU' ALTO (1.55 vs 1.23)
ma corr a TP01 +0.64 e blend uplift solo +0.09. TUTTO il valore di portafoglio e' la gamba SHORT
(decorrelazione 0.64->0.15, uplift 0.09->0.56). PREVDAY non e' alpha: e' un HEDGE di regime-down
(costa nel toro, paga nell'orso 2022/2025-26), additivo alla flat-stance di TP01. Restano i blocker
null-corr-zero e tail-luck. Forward-monitor invariato; eventuale ruolo = overlay di tail-hedge.

Diario: 2026-06-21-prevday-turnover-and-hedge.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 19:45:54 +00:00
Adriano Dal Pastro 8514c096ea research(intraday): fill-haircut PREVDAY a basso capitale -> blocker d'esecuzione BENIGNO
Stima SUBITO (invece di aspettare il forward-monitor) quanto il fill reale a $600 erode il lead
PREVDAY, replicando i due libri di paper_prevday.py su tutto il path 1h (2019-03 -> 2026-06):
 - MODELED (continuo) vs REAL-$C (skip ribilanciamenti < $5 min-order), sweep C {600,2k,20k}.
 - HAIRCUT $600 = +0.01 Sharpe (FULL e HOLD): saltare il 98.4% dei micro-ribilanciamenti del
   vol-target non costa nulla (trade infinitesimi: fee risparmiata e tracking-error entrambi
   trascurabili; fee-drag 2.49% -> 2.39%). L'uplift hold-out del blend 80/20 regge +0.56 -> +0.55.

Conseguenza: dei 4 blocker no-deploy, il #4 (fill a basso capitale) e' SMONTATO. Restano i 3
strutturali (hedge-shaped, fallisce il null a corr-zero, tail-luck). PREVDAY resta forward-monitor.
Lezione: eseguire eval_weights_smallcap PRIMA di scartare un lead per 'fill irreale'.

Diario: 2026-06-21-prevday-fill-haircut.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 19:41:20 +00:00
Adriano Dal Pastro b5db59bea9 feat(dashboard): mostra il forward-monitor PREVDAY (lead ortogonale a TP01)
Nuova sezione "FORWARD-MONITOR — lead paper (non deploy)" nel dashboard, tra PAPER e LIVE:
legge data/paper_prevday/state.json e mostra i due libri (modeled €2k nominale vs real-$600
con min-order $5), ret/maxDD di entrambi, il fill-haircut, le posizioni correnti BTC/ETH e
i giorni/flip forward. Nota esplicita: LEAD in osservazione, NON deployato.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 19:27:27 +00:00
Adriano Dal Pastro 5cce7acfe1 live(monitor): prevday-breakout in FORWARD-MONITOR (paper, non deploy)
Il lead ortogonale a TP01 sopravvissuto all'onda intraday entra in forward-monitor (stesso
trattamento di XS01 STAT-MODE / STA05), NON in esecuzione reale.

- src/strategies/prevday_breakout.py: segnale CONGELATO (params fissi anchor=1, k=0.30, simmetrico,
  vol-target 0.20/30/2.0), self-contained. Bit-identico all'agent di ricerca (max diff 0.0):
  BTC full Sh 1.18/hold 0.92, ETH 1.09/1.42; marginal ADDS, earns_slot, corr_hold -0.01, non-hedge.
- scripts/live/paper_prevday.py: forward-only paper, traccia DUE libri — MODELED ($2000 continuo)
  e REAL-$600 (salta i ribilanciamenti < min-order $5) -> il gap = haircut di fill reale che lo
  scettico aveva segnalato. Inizializzato forward-only da oggi.
- cron_daily.sh: avanza il monitor ogni giorno.
- test: param congelati + causale + bounded + long-short. Suite intera verde.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 15:37:41 +00:00
Adriano Dal Pastro d5dd6f4b72 harness(causality): guardia look-ahead + calendar-artifact self-policing nel lab intraday
- altlib.causality_ok(target_fn, tf): online-consistency guard (ricalcola il target su un
  prefisso, la coda deve combaciare col full). eval_weights shifta la posizione ma non vede
  una feature non-causale (finestra centrata/shift(-k)/stat full-sample) -> questa sì.
- intra_score integra DUE gate prima/dopo lo scoring: causality (leak -> LEAK, squalificato)
  e day_boundary_robust (ARTIFACT-RISK -> fuori dagli slot). Effetto sul leaderboard intraday:
  open_drive + weekly_seasonality + overnight -> CAL-ARTIFACT (da soli, niente skeptic);
  prevday_range_breakout resta (ROBUST). earns_slot 10 -> 8.
- +2 test (causal-ok / leak), suite intera verde.

Il lab intraday ora auto-becca leak e artefatti-calendario che ieri richiedevano 3 scettici.
Chiude la 3a lezione harness dell'onda intraday.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 15:22:58 +00:00
Adriano Dal Pastro 4ae3b42442 harness(realism): codifica le 2 lezioni dell'onda intraday (day-boundary + small-cap fills)
Due gate nuovi in altlib.py (test tests/test_harness_realism.py, suite intera verde):

1. day_boundary_robust(target_fn, tf): shifta il confine del giorno UTC e ri-misura l'uplift
   marginale. INVARIANT (segnale di prezzo, spread 0) / ROBUST (effetto calendario vero, resta
   positivo) / ARTIFACT-RISK (uplift si inverte = etichettatura). Riproduce da solo il verdetto
   degli scettici: open_drive +0.23@00:00 -> -0.33@+8h = ARTIFACT-RISK; prevday_breakout = ROBUST.
   Decoupling chiave: il segnale vede il clock shiftato, il backtest usa il calendario reale.

2. eval_weights_smallcap(df, target, capital=600, min_order=5): salta i ribilanciamenti di
   nozionale < min_order (la finzione del micro-trading sub-dollaro che eval_weights costa come
   fee proporzionale su un overlay vol-target), riporta lo Sharpe haircut reale vs modellato.
   Vale per ogni sleeve a $600, TP01 incluso.

CLAUDE.md aggiornato (sezione HARNESS REALISM). La pipeline di falsificazione ora becca da sola
artefatti-calendario e finzioni-fee, oltre a hedge/regime-luck/leakage gia' codificati.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 14:44:20 +00:00
Adriano Dal Pastro 24565974c0 research(intraday): asse intraday/microstruttura — lead più vicino al reale ma NON deployabile
16 agenti su segnali low-turnover intraday (sessione/funding, reversione post-evento, breakout
range del giorno prima) su feed certificati 1h/15m, giudice = marginal scorer indurito + fee-sweep.
Lab: intra_score.py (wrappa study_marginal a TF scelto + turnover/fee), meta_intra.py (corr-TP01 +
per-cut), verify_intra.py (walk-forward + in-sample-null + drop-one + fee-stress).

Esito: 10/16 "earns_slot" -> 5 genuinamente ortogonali (corr<0.4). Combo dei 5: Sharpe 1.80, corr
0.17, leak-free, passa walk-forward (+0.30/+0.37 dove l'ortho dava -0.07), pre-2025 uplift +0.28,
drop-one e fee-robusto. Sembrava IL lead.

3 scettici: (1) open_drive = ARTEFATTO etichettatura UTC (shift confine 4h -> uplift negativo);
prevday_range_breakout REGGE (unico onesto, eseguibile). (2) combo fallisce il null a corr-zero
(20-24° pctl: aggiunge meno del rumore), è HEDGE (corr -0.57..-0.80 a Sharpe-TP01) + tail-luck
(80% PnL in top-5 giorni delle gambe revert). (3) robust-plateau ma null-pctl 0.20 = diversificazione
di stream ortogonale, non timing-alpha; + finzione fee micro-ribilanciamento a $600.

Verdetto: niente in live, resta solo TP01. Lead forward-monitor: prevday_range_breakout. Lezioni
harness da codificare: test shift-confine-giorno (artefatti calendar), fee discretizzata a piccolo
capitale, causality guard nel lab intraday. Diario 2026-06-21-intraday-microstructure.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 14:20:19 +00:00
Adriano Dal Pastro 62d3b23cc6 harness(marginal): indurisci marginal_vs_tp01 con la lezione dell'onda ortho (17/18 -> 1)
Lo scorer fisso-HOLDOUT + jackknife-mese era ingannabile: 17/18 book relative-value "ADDS"
su una sola finestra 2025 (ETH-bleed dove TP01 è debole). Tre gate nuovi in
altlib.marginal_vs_tp01:
  1. persistenza multi-cut (uplift a più date di taglio, non solo 2025) -> robust_oos
  2. has_insample_edge: Sharpe standalone PRE-holdout >= 0.5 (la basket faceva 0.29).
     null_pctl_* (vs asset-rumore corr-zero) restano come CONTESTO (diversification math).
  3. is_hedge: low-corr che paga solo quando TP01 è debole = hedge, non alpha.
Verdetti nuovi HEDGE/NOISE; earns_slot = ADDS + robust_oos + has_insample_edge + not hedge.

Effetto: sull'onda ortho 17/18 "ADDS" -> 1 (dvol_spread, unico con edge in-sample reale 0.57);
gli altri 16 -> NOISE/HEDGE. Un sleeve sintetico Sharpe~1.3 scorrelato resta ADDS (non rigetta
i diversificatori veri). +5 test (noise/hedge/single-regime/high-Sharpe-uncorr/in-sample-edge);
suite 37 passed. CLAUDE.md aggiornato.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 12:50:26 +00:00
Adriano Dal Pastro 0adc69a357 research(ortho): caccia all'ortogonale a TP01 — relative-value BTC/ETH reale ma NON deployabile (hedge mono-regime)
18 agenti su book market-neutral a 2 gambe BTC/ETH (eseguibili a $600, a differenza di XS01),
giudicati sul MARGINALE vs TP01 (altlib.marginal_vs_tp01), non sullo Sharpe assoluto.

Lab: ortholib.py (eval_book leak-free a 2 gambe + causalità + eseguibilità@600), ortho_score.py
(giudice), meta_ortho.py (corr mutua + persistenza multi-cut), sleeve_rv.py (curated, SELECTION-
BIASED, non deployare).

Esito: 17/18 "ADDS" -> gonfiato dall'hold-out corto fisso-2025 (finestra ETH-bleed dove TP01 è
debole). Diagnosi orchestratore: collassano a 8 bet (corr 0.43); persistenza multi-cut e selezione
walk-forward smascherano i 2025-only (kalman/xs2). Scettico indipendente: basket selection-free ha
uplift pre-2025 +0.027 = 49° percentile di asset-rumore corr-zero (matematica di diversificazione,
non segnale); corr(Sharpe-TP01, uplift) -0.87 (è un HEDGE dei drawdown di TP01); muore a 0.30% RT.

Verdetto: NIENTE in live. Resta solo TP01. Lezione: lo scorer marginale va indurito (multi-cut +
null-asset-rumore + distinguere hedge da alpha). Diario 2026-06-21-ortho-tp01-relative-value.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 12:35:48 +00:00
Adriano Dal Pastro 1afb1014c9 research(blind): 52 agenti ciechi su curve anonime BTC/ETH — orchestratore valuta PnL/maxDD, niente di nuovo regge
Flotta di 52 subagenti "esperti di segnali" su storico BTC/ETH ANONIMIZZATO (Series A/B
rebased a 100, calendario sintetico, split 70/30) — non sanno cosa siano. Ognuno scrive un
signal(df)->position causale (script o ML), tunato solo sul train. Orchestratore valuta su
PnL e maxDD nel test held-out.

Harness cieco leak-free (riusabile):
- make_blind.py: export anonimo + overlay; blindlib.py: evaluator con shift della posizione +
  GUARDIA DI CAUSALITA' online (squalifica ogni look-ahead, ML incluso); blind_eval.py CLI;
  score_all.py giudice OOS; verify_top.py (corr-al-trend, fee-stress, jackknife).
- 52/52 passano la guardia (zero leak su tutta la flotta).

Esito OOS (benchmark buy&hold: -7% PnL, 68% DD):
- top = macd (+21%, DD 11%, Sh 0.84), accel, vol_of_vol, regime_switch, rf, obv — tutti
  trend/vol-regime. Sharpe OOS ~0.84 decade dal train ~1.4. Mean-rev e ML in fondo.
- 3 scettici indipendenti: REFUTED. regime-luck (top-5 bar = 67-102% del PnL); trend-redundancy
  (HAC alpha t=+0.9..+1.5, nessuno >1.96 — TSMOM travestito); overfit (accel/vov knife-edge).

Verdetto: ri-conferma CIECA e indipendente del soffitto direzionale ~1.3. macd = classe-TP01,
forward-monitor non deploy. Diario 2026-06-21-blind-signal-fleet.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-21 07:05:04 +00:00
Adriano Dal Pastro f5d30d88b9 docs(claude): aggiorna l'header allo stato LIVE armato di TP01 + capitale reale ~$600
L'header v2.0.0 RESET diceva ancora 'esecuzione DISABILITATA / nessun trading live'
(stato del 2026-06-19), superato dall'arming del 2026-06-20: TP01 e' ARMATO/LIVE su
Deribit mainnet (config/live.json execution_enabled=true + cron live_execute.py --execute),
cap $300/asset, disaster-SL -30%, alert Telegram, capitale reale ~$600. Stato corrente
flat (target risk-off). Solo TP01 eseguito; XS01/VRP01 restano paper/STAT-MODE.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 21:43:17 +00:00
Adriano Dal Pastro 9612560479 research(xsec): sweep cross-sectional su Hyperliquid (43 script/257 config) + verifica avversariale
Nuova harness condivisa xslib.py (panel HL certificato, score per-asset causale, book
long-k/short-k vol-targeted leak-free) + 43 script in runs/ su 11 famiglie (MOM/REV/VOL/
DIST/LIQ/VAL/STRUCT/UNIV). Scoring = earns_slot (full>0 AND hold-out>0 AND marginal ADDS
al portafoglio live AND corr XS01<0.6, con jackknife drop-one-month).

Find: 42/257 config earns_slot=True, ma TUTTE con corr TP01 -0.2..-0.4 e PnL ~solo 2025.
Verify (verify_survivors.py, 3 scettici deterministici):
 - S1 redundancy: cluster low-vol = UNA scommessa (XV01=XU02=1.00, XV02/XV03 r 0.44-0.67);
   XM09/XL02/XS06b/XR02 distinti (corr media off-diag +0.20).
 - S2 short-beta: cluster low-vol carica 0.44-0.70 su short-market -> NON market-neutral,
   e' un tilt short-alt-beta di regime. XM09(0.08)/XR02(-0.21) NON short-beta.
 - S3 per-anno: cluster low-vol decade (XV01/XU02 2026 -0.09); XL02 morto (2025 -0.14,
   2026 -0.43); XM09 (0.82/0.50/0.74) e XR02 (0.84/0.40/2.68) positivi in tutti e 3 gli anni.

Esito: nessuna sleeve nuova. Cluster low-vol RIGETTATO (regime-bet), XL02 RIGETTATO (overfit).
2 LEAD genuini (XM09 trend-gated x-sec momentum, XR02 reversal vol-gated) -> forward-monitor,
non deployabili (panel 2.5y regime unico + STAT-MODE esecuzione). Portafoglio live invariato.

Incluso anche options_vrp_managed.py (A/B VRP01 hold-to-expiry vs gestione attiva del doc
credit-spread): la gestione attiva DISTRUGGE l'edge (combo FULL managed Sh -1.29 vs HtE +0.96,
il delta-exit taglia i vincenti) -> scartata, VRP01 resta hold-to-expiry.

Diari: 2026-06-20-xsec-strategies-sweep.md, 2026-06-20-vrp-active-management.md.
gitignore: data/paper_portfolio/ (stato runtime paper) + scripts/research/xsec/runs/out/ (output rigenerabile).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 21:36:57 +00:00
Adriano Dal Pastro 5ac4e16af8 research(alt): sweep 104 strategie alternative su Deribit (153 agenti) + marginal scorer
Ondata di ricerca onesta a largo spettro su BTC/ETH+DVOL certificati: 104 ipotesi
distinte (11 famiglie), un agente-finder per ipotesi, verifica avversariale a 3
scettici sui promettenti, sintesi (153 agenti totali). Esito: NIENTE di nuovo regge
-> conferma del soffitto strutturale ~1.3 BTC/ETH-direzionale; lo stack
TP01+XS01+VRP01 resta imbattuto.

- altlib.py: harness condiviso vettoriale leak-free (eval_weights/study_weights,
  fee-sweep, both-asset + hold-out 2025+). Riproduce i numeri canonici di TP01.
- MARGINAL SCORER (study_marginal/marginal_vs_tp01): Sharpe INCREMENTALE vs baseline
  TP01 (corr, blend uplift OOS, alpha residua) + jackknife OOS (clean-year +
  drop-best-month). earns_slot = abs!=FAIL & ADDS & robust_oos. Smaschera gli overlay
  su TSMOM con PASS assoluti fasulli (CMB04, VOL11, ...) e il falso positivo KAMA
  (ADDS ma muore al jackknife).
- runs/*.py (104) script riproducibili per ipotesi; wf_altstrat.js workflow.
- Verdetto: 0 candidati deployabili; 2 LEAD fragili (VOL08, STA05_LS) da forward-monitor.
- test_marginal_scorer.py blocca baseline + invarianti. Suite: 32 verde.

Diario: docs/diary/2026-06-20-alt-strategies-100agent-sweep.md

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 19:50:39 +00:00
Adriano Dal Pastro bf84bc91e2 feat(live): alert Telegram su esecuzione ed errori
src/live/notifier.py (stdlib, no-op se non configurato): legge TELEGRAM_BOT_TOKEN/CHAT_ID da env o
.env(.mainnet) gitignored. live_execute.py invia alert su: ordine eseguito (✅), ordine non
verificato (⚠️), disaster-SL piazzato/fallito (🛡️/⚠️), conto offline, e qualsiasi eccezione (🛑).
Nessun alert nei giorni flat/HOLD (no rumore). Config gia' presente in .env -> alert attivi.

Test config: uv run python -m src.live.notifier "msg". Test 28/28.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 16:09:09 +00:00
Adriano Dal Pastro 3cba5bb9d0 feat(dashboard): mostra i disaster-SL attivi nella sezione LIVE
Lo shadow espone i bracket disaster-SL aperti (open_orders filtrati per label DISASTER_LABEL,
centralizzata in deribit.py): asset, stop price, size. La sezione LIVE li mostra
("disaster-SL attivi (-30%): ..." o "nessuno (flat)"). Test 28/28.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 16:05:18 +00:00
Adriano Dal Pastro e5e2d3ec9b feat(live): disaster-SL on-book con lifecycle completo (idempotente) nel loop di esecuzione
ensure_disaster_sl(): garantisce UN solo STOP_MARKET reduce_only a ~-30% coerente con la posizione,
ad ogni run del loop, per asset:
- flat  -> cancella i bracket orfani;
- long  -> assicura lo stop (size = posizione, prezzo al tick);
- gia' coerente (1 bracket, amount~=, stop entro 5%) -> lascia com'e' (niente churn ne' gap di
  protezione fra cancel e place).

- deribit.py: open_orders (merge type all+trigger_all), disaster_stop_price.
- execution.py: cancel_order + ensure_disaster_sl.
- live_execute.py: gestione bracket ogni run, gated come l'esecuzione. Validato armato: flat ->
  disaster-SL 'flat' (cleanup), zero ordini. Test 28/28.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 15:47:30 +00:00
Adriano Dal Pastro 4650aa71a2 feat(live): ARMA l'esecuzione di TP01 (execution_enabled=true) + cabla al cron giornaliero
execution_enabled=true: con --execute il loop invia ordini REALI. Aggiunto al cron_daily.sh (00:30
UTC, dopo il refresh dati) lo step live_execute.py --execute. Validato armato: TP01 flat -> HOLD,
zero ordini. Da qui TP01 opera da solo sul conto reale al prossimo ENTRY del segnale.

NB: il loop NON piazza ancora il disaster-SL on-book (metodo presente, lifecycle bracket da cablare
prima del primo ENTRY). Rischio posizione comunque limitato dal cap $300/asset (~1x, no leva).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 15:41:03 +00:00
Adriano Dal Pastro bc9e322d0d feat(live): loop di esecuzione GATED di TP01 (execution_enabled + --execute, default OFF)
scripts/live/live_execute.py porta il conto reale al target di TP01 (min(0.5*frazione*equity,
cap/asset)): apre/riduce/chiude via DeribitTrader.rebalance_to(). DOPPIO GATE: config/live.json
execution_enabled=true (master, default false) E flag --execute; senza entrambi e' dry-run.
Reconciliation post-ordine + log in data/live/executions.jsonl. TP01 flat -> 0 azioni.

- execution.py: rebalance_to() (open/reduce/close al target); MAX_AMOUNT alzato a tetto hard
  anti-fat-finger (~$630/$430 su conto ~$600), il sizing operativo lo decide config max_notional.
- config/live.json: master switch + cap/asset $300 + min ordine $5 + disaster_sl_pct.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 15:37:51 +00:00
Adriano Dal Pastro a3d6b97db6 fix(dashboard): sezioni PAPER/LIVE evidenti (barra colorata) + Cache-Control no-cache
Le sezioni erano testo grigio poco visibile e il browser cacheava la pagina ('non vedo differenza').
Ora: header PAPER con barra verde, LIVE con barra rossa + sfondo rosso-tenue (separazione netta);
risposta HTTP con Cache-Control no-cache/no-store -> niente pagina stantia.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 15:36:21 +00:00
Adriano Dal Pastro cddea50c5a feat(live): conto USDC -> strumenti lineari; entrata/uscita da Old; dashboard LIVE separato da PAPER
Correzione post-micro-test (il conto e' USDC, non BTC/ETH):
- deribit.py: INSTRUMENT -> BTC/ETH_USDC-PERPETUAL (lineari, gli unici eseguibili sul conto USDC);
  notional_to_amount gestisce i lineari (amount in base-coin = notional/price); + quantize_price;
  trade_history (read-only) per i trade reali. build_rebalance_order passa il prezzo.
- shadow.py: sizing col prezzo; espone live_trades (trade reali eseguiti su Deribit).

Entrata/uscita verificate (logica presa da Old/src/live/execution.py):
- execution.py: open() market verificato (state=='filled' + trade, fill/fee reali, filled_amount
  autorevole), close() market reduce_only (le CHIUSURE si tentano SEMPRE, senza cap), disaster-SL
  STOP_MARKET reduce_only. Cap di size SOLO sulle aperture. Fill dataclass.
- microtest.py: usa open()/close(); safe-close se l'apertura non e' verificata.

Dashboard: sezione PAPER (backtest+forward) separata da sezione LIVE (conto reale Deribit: shadow
TP01 + Trades REALI eseguiti). Test 27/27.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 15:15:45 +00:00
Adriano Dal Pastro c00f6016df feat(live): micro-test esecuzione REALE su Deribit mainnet (USDC linear) — round-trip validato
Primo ordine reale post-reset, a rischio ~0 ($6 notional, leva 0.011x). Scoperto che il conto e'
USDC -> strumento eseguibile = perp LINEARE BTC_USDC-PERPETUAL (l'inverse BTC-PERPETUAL fallisce
'not_enough_funds'). Round-trip BUY/SELL reduce_only verificato: fill reali, fee reali (0.0064 USDC),
posizione tornata a FLAT, costo totale $0.0071.

- src/live/execution.py  : DeribitTrader (estende DeribitRead) con market order + verifica posizione,
  GUARDRAIL hard (solo BTC_USDC-PERPETUAL, amount <= 0.0002 BTC). Niente leva per-ordine (Deribit non
  la accetta: l'esposizione la decide la SIZE).
- scripts/live/microtest.py : runner round-trip, default DRY-RUN, --live per inviare. Pre-flight ABORT
  se posizione preesistente; chiusura reduce_only; verifica ritorno a FLAT.
- src/live/deribit.py    : aggiunti spec contratto LINEARI USDC (BTC/ETH_USDC-PERPETUAL).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 15:06:53 +00:00
Adriano Dal Pastro 715f197cf2 feat(dashboard): lista trades TP01 (entry/exit dal segnale causale)
Nuova sezione "Trades TP01" nella dashboard: eventi ENTRY long / EXIT flat dedotti da
target_series sui dati certificati (data, asset, transizione di posizione, prezzo). In
src/live/shadow.tp01_trades(): account-independent (gira anche offline nel container),
ricalcolata a ogni render -> storico + forward. Empty-state se TP01 non ha mai mosso.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 14:18:46 +00:00
Adriano Dal Pastro bec2fb2089 chore(dashboard): monta .env.mainnet read-only nel container per lo "Shadow live"
Il token mainnet (sola lettura) abilita conto/posizioni REALI nel box Shadow della dashboard.
Montato a runtime, NON nell'immagine (.env.mainnet resta dockerignored). Solo letture: nessun
endpoint di trading e' raggiungibile da src/live/deribit.py. Verificato: conto reale $598.07 letto
dal container, TP01 flat -> 0 ordini.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 14:02:26 +00:00
Adriano Dal Pastro 9c48cdd884 feat(live): SHADOW MODE TP01 su Deribit mainnet (sola lettura) + dashboard 3-way
Validazione esecuzione di TP01 a RISCHIO ZERO: gira il loop live contro dati/conto/posizioni REALI
del mainnet, costruisce gli ordini di ribilancio esatti e li STAMPA invece di inviarli. Niente
testnet (e' la causa del reset v2.0.0: feed farlocco) -> shadow su mainnet reale + micro-test a
size minima come unica via per il fill (passo successivo).

- src/live/deribit.py  : client Deribit mainnet SOLA LETTURA (ticker/conto/posizioni via Cerbero MCP)
  + costruttore ordini deterministico (notional->contratti, step BTC $10/ETH $1, quantizzazione,
  delta vs posizione). Nessun metodo di trading, by design.
- src/live/shadow.py   : shadow_report() condiviso CLI+dashboard (niente drift); degrada con grazia
  se il mainnet non risponde.
- scripts/live/live_trend.py : CLI shadow (--no-net offline, --equity override). Verificato su
  mainnet reale: conto $598.07, posizioni flat, TP01 flat -> 0 ordini, parita' col paper OK.
- src/live/dashboard.py : box "Shadow live" + titolo/note al 3-way (TP01+XS01+VRP01).
- tests/test_live_shadow.py : 9 test deterministici (quantizzazione, sizing 50/50, entry/exit/None,
  parita' live==backtest). Suite 26/26.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 14:01:12 +00:00
Adriano Dal Pastro 9ed2ea4b13 fix(fetch_hyperliquid): taglia il backfill sintetico di cerbero MCP (vol=0) — universo 52->51
Cerbero MCP padda il periodo pre-quotazione su HL con barre SINTETICHE (volume 0, prezzi
copiati da Binance -> matchano cross-venue e non sono flat): asset listati dopo lo START
(es. AXS 83%, ALGO/SAND 37%) passavano i gate flat+cross-venue ed erano certificati PULITO
pur non essendo negoziabili. E' il caso v2.0.0 (edge su un book che non c'era).

Fix: il VOLUME e' il rivelatore del backfill -> (1) taglio del run iniziale a volume 0
(serie nativa), (2) gate storia nativa >=365g reali (AXS scartato), (3) gate vol=0 interno,
(4) cross-venue/flat ricalcolati solo sulle barre reali, (5) parquet scartati rimossi.

Verificato direttamente su cerbero MCP mainnet. I 19 major di XS01 hanno 0 backfill ->
strategia live invariata. Diario 2026-06-20-cerbero-backfill-fix.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 11:53:55 +00:00
Adriano c6236ed5d9 feat: integra VRP01 come sleeve del portafoglio (put credit spread + gate IV-rank)
src/portfolio/sleeves.py: _vrp_combo_returns + vrp_sleeve, self-contained in src/
(pricing BS + gate causali inline, DVOL da data/raw). Settimanale->giornaliero col
lump sul giorno di scadenza (preserva lo Sharpe annualizzato, peso costante).

Registry: TP01 0.55 / XS01 0.25 / VRP01 0.20 (TP01 resta maggioranza; VRP e' un
lead modellato, non deploy pieno). TP01+VRP01 monotono: FULL 1.30->1.44, HOLD
0.31->0.40 a peso 20%. Scorrelato a TP01 (+0.01).

Test tests/test_vrp_sleeve.py (5 pass). CLAUDE.md + diario aggiornati.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 11:24:40 +02:00
Adriano 75e1aacd19 research: analisi strategie FinanceOld + VRP v2 (defined-risk spread + gate IV-rank)
Analisi 4 progetti FinanceOld. Solo il filone opzioni-VRP backtestabile sui dati
certificati (funding-arb senza dati storici; Polybot ticks corrotti/3gg/edge=latenza).

VRP v2 porta 3 idee di OptionsAgent nel framework, causale + fee-aware:
- put credit spread (rischio definito): worst-week -16.6%->-7.4%, DD 33%->21%
- gate IV-rank>0.30: ribalta HOLD-OUT da -0.25 a +0.28 (alpha = filtro regime)
- COMBO f=1.0: FULL Sh 1.10, HOLD 0.60, DD 12%, positiva/piatta ogni anno
- blend TP01 70/30 -> Sh 1.00, DD 7% (corr +0.07)

Lead quantificato, non deploy (premio modellato ATM, serve f di stress reale).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 11:16:59 +02:00
Adriano Dal Pastro 92a63feb9c chore(monitor): cron giornaliero (refresh dati + avanza paper) + cleanup crontab/orfano
scripts/cron_daily.sh: rebuild_history BTC/ETH + fetch_hyperliquid (52 alt) + fetch_dvol +
paper_portfolio, ogni giorno 00:30 UTC -> tiene fresco il dato che il dashboard legge e avanza
il paper forward. fetch_hyperliquid END ora DINAMICO (oggi) per il refresh.

Cleanup: rimosso container orfano pythagoras-portfolio (vecchio runner pre-reset, exited);
crontab ripulito dai 4 job rotti del micro-test mainnet (hourly_report/drift/reconcile/
ledger_vs_backtest -> script archiviati in Old/), backup in logs/crontab.pre-reset.bak.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 09:06:38 +00:00
Adriano Dal Pastro 26e977d338 feat(monitor): dashboard PAPER del portafoglio attivo (TP01+XS01) + paper forward loop
src/live/dashboard.py: web UI stdlib (:8787) che mostra metriche (FULL/HOLD Sharpe, DD, CAGR),
per-sleeve, posizioni correnti, equity (backtest + paper forward), ultimo dato. Solo MONITOR,
esecuzione REALE disabilitata. scripts/live/paper_portfolio.py: forward-only del portafoglio
(StrategyPortfolio su active_sleeves), stato persistente in data/paper_portfolio (gitignored).

Dockerfile + docker-compose.yml minimali (solo servizio dashboard; runner/esecuzione restano in
Old/). Container pythagoras-dashboard ricostruito col codice nuovo (il vecchio mostrava dati
pre-reset). Mount data/ read-only. .dockerignore esclude Old/data/.venv/.git/.env.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-20 08:57:55 +00:00
Adriano Dal Pastro 0d9f483131 docs: aggiorna CLAUDE.md allo stato corrente (XS01 blend+gate, portafoglio FULL/HOLD 1.55)
XS01 ridescritta con affinamenti (blend lookback [30,90] + gate dispersione p30, standalone FULL
1.50). Portafoglio attivo TP01 70% + XS01 30% -> FULL Sh 1.55 / HOLD 1.55 / DD 4.4%. Aggiunte le
lezioni: espansione universo Hyperliquid NON aiuta XS (52/top-liq/trend-multiasset tutti peggiori,
i margini sono nel segnale); lead opzioni VRP quantificato (f reale ~1.0, non deploy). Struttura/
comandi aggiornati (scripts/research track A-I + options_vrp + fetch_dvol; scripts/portfolio xsec_*).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 22:29:24 +00:00
Adriano Dal Pastro 87dd56a9ce feat(XS01): + gate di dispersione (p30) — portafoglio FULL 1.48->1.55, HOLD 1.06->1.55
Momentum cross-sectional vive nella dispersione; gate: entra solo se la dispersione cross-section
del momentum supera il percentile ESPANDENTE causale (altrimenti flat). Plateau robusto p15-p35
(non knife-edge: il crollo a p40+ e' over-gating); scelto p30. XS01 standalone FULL 1.10->1.50,
HOLD 1.03->1.71, DD 14%->10.8%. Portafoglio TP01 70+XS 30: FULL 1.48->1.55, HOLD 1.06->1.55, DD
4.6%->4.4%. Il gate alza SIA FULL SIA hold-out (tiene XS attivo nei regimi dispersi, flat nei bull
compatti; causale). E' il concetto del vecchio XS01.

sleeves.XS_CFG disp_pct=30; engine _xsec_returns gatea su dispersione. 12 test ok.
Diario 2026-06-19-xsec-dispgate.md. Affinamenti del segnale (blend+gate) > espansione universo.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 22:24:04 +00:00
Adriano Dal Pastro fd5a0bd3cf feat(XS01): affina con blend di lookback [30,90] — FULL 0.80->1.10, portafoglio 1.41->1.48
Come TP01 fonde gli orizzonti, XS01 ora fonde 30g+90g del momentum cross-sectional (z-score per
lookback, mediato). Sweep: [30,90] e' il sweet spot (fonde i due singoli robusti, anti-overfit):
XS01 standalone FULL 0.80->1.10, DD 21%->14%, corr a TP01 -0.06->-0.12, 100% anni+. Portafoglio
TP01 70 + XS01 30: FULL Sh 1.41->1.48, DD 5.2%->4.6%, ~€/g 1.65->1.78; hold-out 1.15->1.06 (calo
marginale dentro il rumore). Piu' robusto (due orizzonti) + diversifica meglio -> promosso.

sleeves.XS_CFG lookbacks=(30,90), engine _xsec_returns usa lo score blended. 12 test ok.
Diario 2026-06-19-xsec-blend.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 22:19:12 +00:00
Adriano Dal Pastro bf6ade51af research: strato trend multi-asset (52 alt) RIDONDANTE col trend TP01 -> non aggiunto
TSMOM CANONICAL applicato a ogni alt dei 52, equal-weight. Standalone FULL 0.66 ma HOLD-OUT -1.03
(long negli alt nel calo 2025-26), corr a TP01 +0.74 (stessa beta direzionale). Contributo al
portafoglio NEGATIVO (HOLD -0.16/-0.27). Broadenizzare il TREND non diversifica: e' la stessa
direzionalita' su asset piu' rumorosi. Solo il market-neutral (XS01) diversifica davvero.

Chiude il filone espansione-universo (XS-52, top-liquidita' dinamico, trend-52: tutti peggiori).
Configurazione validata invariata: TP01 70% + XS01 (19 major) 30%, FULL Sh 1.41 / HOLD 1.15.
I margini reali sono in un MECCANISMO diverso (opzioni VRP), non nell'universo crypto-direzionale.
Diario 2026-06-19-trend-multiasset.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 21:17:16 +00:00
Adriano Dal Pastro 182d4eeac2 research: universo top-liquidità DINAMICO per XS — anch'esso peggiore del fisso-19 (memecoin diluiscono)
xsec_dynuniverse.py: a ogni ribilancio top-N per dollar-volume 30g causale (ragged-aware), poi XS
momentum. Esito: best dinamico top12 FULL 0.65/OOS0.54 (un anno neg) vs fisso-19 FULL 0.80/OOS1.20
(100% anni+). Contributo TP01+DYN 1.10/0.60 vs TP01+XS19 1.25/1.15. La classifica per volume ammette
i MEMECOIN ad alto volume (WIF/ORDI/JUP) erratici -> diluiscono. Liquidità != qualità.

Conclusione: ne' 52-all ne' top-liquidità dinamico battono i 19 major curati. XS01 resta sui 19.
Portafoglio invariato TP01 70% + XS01 30% (FULL 1.41 / HOLD 1.15). 12 test ok. I 52 parquet restano
per ricerca futura. Diario 2026-06-19-xsec-universe-expansion.md aggiornato.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 21:09:48 +00:00
Adriano Dal Pastro 8426d05f12 research: espandere universo XS01 a 52 asset DILUISCE (negativo) -> XS01 blindato sui 19 major
Esteso fetch_hyperliquid a 52 alt certificati (cross-venue vs Binance, flat 0%, 2024+; +gate
delistato per MKR/FXS). Ma il cross-sectional momentum sui 52 e' NEGATIVO (FULL -0.1..-0.6, k grande
non aiuta) vs +0.67/OOS0.91 sui 19 major (stessa finestra): i ~33 small-cap (WIF/JUP/ORDI/PYTH/TAO..)
sono idiosincratici/mean-reverting e rovesciano il momentum relativo. "Piu' asset = piu' robusto"
e' FALSO per l'XS momentum: la breadth utile e' quella dei major liquidi.

Fix: lo sleeve _xsec_returns usa XS_UNIVERSE esplicito (19 major), non glob-all (aggiungere parquet
certificati non lo rompe piu'). I 52 parquet restano su disco per ricerca futura, non per XS01.
Portafoglio ripristinato e invariato: TP01 70% + XS01 30%, FULL Sh 1.41 / HOLD 1.15. 12 test ok.
Diario 2026-06-19-xsec-universe-expansion.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 21:00:00 +00:00
Adriano Dal Pastro 53d0134cb1 research: calibra VRP su quote REALI cerbero-bite — f≈1.0 (non 1.29), lead DEBOLE confermato non-deploy
cerbero-bite GIA' accumula la catena reale mainnet (option_chain_snapshots, 2026-05->oggi) -> uso
quella (niente nuovo snapshotter). options_vrp_calibrate.py misura il fattore f reale su 223
snapshot/asset (put weekly delta-0.28, BID): BTC f median 1.03, ETH 0.97, skew reale +1.5..1.9 pt.
Il f reale e' ~1.0 NON 1.29 (lo snapshot singolo del branch era outlier ad alto skew). -> VRP sleeve
= punto f≈1.0 = Sharpe ~0.71 (conservativo), DD 33%, hold-out piatto: diversificatore DEBOLE (corr
+0.07) sotto TP01, coda severa. Calibrazione su ~10g densi, 1 regime calmo; f di stress non misurato.

Verdetto: la decorrelazione modesta NON giustifica il rischio di coda short-vol senza dato reale
multi-regime (serve che cerbero-bite copra un crash). Confermato NON-deploy. Portafoglio invariato
TP01 70% + XS01 30%. Diario 2026-06-19-options-vrp-lab.md aggiornato.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 20:38:54 +00:00
Adriano Dal Pastro 8f9ce89039 research: imposta sleeve OPZIONI VRP — infrastruttura + prima validazione (LEAD reale, non deploy)
fetch_dvol.py: storia DVOL (IV Deribit) BTC/ETH 2021-2026 -> data/raw/dvol_*. options_vrp_lab.py:
backtest CSP settimanale, premio BS su DVOL reale + calibrazione f (skew/spread), payoff sul path
realizzato, causale; gauntlet (VRP, sweep f/delta, per-anno, worst-weeks, corr+contributo vs TP01).

Esiti (book 50/50 put delta-0.28): VRP reale (BTC IV>RV 78% del tempo). Sharpe DIPENDE da f:
0.71 conservativo (IV-ATM) -> 1.70 a f=1.29 (skew reale calm). CODA severa (DD 30-33%, settimane
-15..-26% su LUNA/FTX/crash; 2022 -9%, 2026-YTD -14%). Scorrelato a TP01 (+0.07) -> migliora il
portafoglio anche a premio conservativo (TP01 70%+OPT 30%: Sh settimanale 0.71->0.97).

VERDETTO: lead reale e diversificante, MA premio modellato (non catena reale) + calibrazione
ottimistica + coda short-vol non catturata nello stress. Regola: mai short-vol da modello in
deploy. NON aggiunto. Portafoglio invariato TP01 70% + XS01 30%. Prossimo: accumulo quote reali
multi-regime + stress crash + daily-MTM + paper testnet. Diario 2026-06-19-options-vrp-lab.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 20:30:08 +00:00
Adriano Dal Pastro 87af03955c research: porta artefatti da strategy-research-calendar (tracks F-I + eval crypto_backtest + lead OPZIONI/VRP)
Dal branch parallelo strategy-research-calendar (continuazione della linea TP01). Porta su main il
record di ricerca + la fondazione del lead opzioni (NIENTE blob dati, niente codice in conflitto):
- Tracks F/G/H/I (seasonality/calendar, prior-levels, volume-vol, momentum-reversal): tutti
  NEGATIVI/spurii -> confermano il soffitto Sharpe ~1.3 su BTC/ETH direzionale (calendar = buy&hold
  travestito; mean-reversion morta anche a fee 0). Diari + script.
- trackD_lookahead_audit.py: audit anti-look-ahead (stesso esito del nostro fix >=12h).
- eval-crypto-backtest-options.md: valutazione strategia esterna crypto_backtest. Cross-valida TP01
  (il loro sleeve spot 12h ~ TP01: due ricerche indipendenti, stessa conclusione). Identifica il
  LEAD: sleeve income OPZIONI (vendita put settimanali delta-0.28, VRP IV>RV), scorrelato ~0.22 al
  trend -> via per superare il soffitto ~1.3.
- options_real_quote_check.py + cerbero-bite-mainnet-verified.md: VERIFICATO su QUOTE REALI Deribit
  mainnet (cerbero-bite/MCP = mainnet, bit-identico a ccxt.deribit). Premio reale (BID, con skew) =
  1.29x il modellato -> il backtest SOTTOSTIMA il premio; il rischio vero e' la CODA (short-vol) +
  liquidita' di roll in stress, non la magnitudine.

NB: lo sleeve opzioni e' un LEAD, NON deployato: prezzato da modello (BS su DVOL) + 1 snapshot in
regime calmo. Serve validazione real-chain multi-regime + stress crash + paper su testnet prima di
aggiungerlo al portafoglio. Portafoglio attivo invariato: TP01 70% + XS01 30%.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 20:24:16 +00:00
Adriano Dal Pastro 790caefd52 research: wave1 beat-TP01 (26 agenti BTC/ETH) — nessun 3o sleeve robusto, portafoglio invariato
26 agenti, 3 contender ri-verificati onesti: tsmom_12h scartato (corr +0.49 = TP01 veloce),
breakout_atr scartato (gonfia solo FULL storico, hold-out +0.05), highvol_rev in WATCHLIST
(scorrelato e migliora FULL+hold-out MA edge solo a REV_LB=1 = picco non-plateau, FULL mediocre
0.74, HOLD>>FULL = regime-luck alta-vol 2025-26, reversal+concept-flip). Stesso difetto del RV
bocciato -> non deployato. Portafoglio resta TP01 70% + XS01 30%. L'edge incrementale e' venuto
dall'espansione universo (Hyperliquid cross-sectional), non da altre trend-variant su 2 asset.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 20:19:47 +00:00
Adriano Dal Pastro a5a61ac7e3 feat(portfolio): XS01 cross-sectional (Hyperliquid) BATTE il portafoglio -> TP01 70% + XS01 30%
Espansione universo (su input utente "storico da cerbero"): il Cerbero MCP col token MAINNET serve
Hyperliquid (230 perp REALI, storia nativa dal 2024). fetch_hyperliquid.py certifica 19 alt liquidi
a 1d (flat 0%, cross-venue 4-9 bps vs Binance) -> data/raw/hl_*_1d.parquet. Abilita le strategie
CROSS-SECTIONAL (impossibili a 2 asset).

XS01 = cross-sectional momentum market-neutral (long 5 forti / short 5 deboli su ret 30g, ogni 10g,
vol-target 20%). Validato onesto: plateau (config/k/subset), fee-robusto (0.3% RT), scorrelato a TP01
(-0.06), positivo OGNI anno 2024-26, meccanismo complementare (lavora nella dispersione quando TP01
e' in cash). Diverso dal regime-luck RV bocciato (19 asset, plateau, ogni anno+).

Contributo al portafoglio (outer-join + pesi rinormalizzati per sleeve a date diverse):
  TP01-solo FULL 1.30 / HOLD 0.31  ->  TP01 70% + XS01 30%: FULL 1.41 / HOLD 1.15, DD giu', ~ogni anno+.
-> XS01 BATTE il portafoglio esistente: inserito in active_sleeves.

Caveat (documentati): storia XS ~2.5 anni; STAT-MODE (book 19 gambe non eseguibile a 2k -> ~20k),
sleeve diagnostico/forward-monitor. portfolio.combine ora outer-join+renorm. 12 test passano.
Diario 2026-06-19-hyperliquid-xsec.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 20:05:45 +00:00
Adriano Dal Pastro 18f22160b2 research: caccia al 2o sleeve — nessun diversificatore robusto, TP01-only resta
Tool second_sleeve_hunt.py: giudica i candidati per CONTRIBUTO al portafoglio (non Sharpe
standalone). RV mean-rev ETH/BTC morto (come sempre). RV relative-momentum (ratio_trend ==
xs_momentum) sembrava promosso (hold-out portafoglio 0.31->1.51) MA il per-anno + plateau lo
smascherano come REGIME-LUCK 2025: FULL Sh mediocre 0.56, 2 anni consecutivi negativi
(2023 -17%, 2024 -19%), guadagno concentrato nel 2025 (+62%), hold-out Sh non-plateau (0.25-1.92
al variare dei parametri). Beneficio FULL robusto solo +0.09 (diversificazione di uno sleeve
scorrelato debole). NON promosso: la disciplina che boccia i falsi positivi in-sample boccia
anche i falsi positivi nel hold-out. Criterio aggiornato: breadth per-anno + plateau, non solo
hold-out. Relative-momentum in WATCHLIST. Diario 2026-06-19-second-sleeve-hunt.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 19:28:51 +00:00
Adriano Dal Pastro ef52ad6a79 feat(portfolio): contenitore di strategie ESTENSIBILE — TP01 primo sleeve
src/portfolio/: Sleeve (serie rendimenti netti per-barra, causale/fee-aware) + StrategyPortfolio
(combina N sleeve per peso su griglia giornaliera comune, metriche FULL/HOLD-OUT/per-anno +
standalone per-sleeve, vs buy&hold). Registry sleeve attivi in sleeves.py: per ora SOLO TP01
(peso 100%); aggiungere = una riga (dopo validazione col gauntlet).

Report (run_portfolio.py): TP01 FULL Sh 1.30 / DD 14.3% / ~€1.52/g, HOLD-OUT 0.31 / +3.5%
(buy&hold -0.32 / -39%). Posizione corrente flat (difensivo). tests/test_portfolio.py (6 test).
CLAUDE.md aggiornato (struttura + comando + come aggiungere uno sleeve).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 19:17:18 +00:00
Adriano Dal Pastro 12754c4908 fix(TP01): bug look-ahead ffill mixed-TF -> deploy a >=12h (1d), strategia DIFENSIVA
Segnalato: ffill MIXED-TIMEFRAME su barre open-labeled (resample label="left") gonfiava il 4h
(~1.60 -> reale ~1.1). Ri-verifica per-SINGOLO-TF leak-free (guard prefix-recompute, leak=0 su
4h/6h/12h/1d): FULL Sh piatto ~1.3, hold-out 2025-26 MIGLIORE a 1d (Sh 0.31 / +3.5% vs buy&hold
-39%). Conclusione adottata: NON scendere sotto le 12h (sotto, costi+overfit dominano senza vantaggio).

- trend_portfolio.py: canonica PORT LF1d; resample_tf/resample_1d (resample_4h deprecato deploy);
  docstring con nota look-ahead + natura DIFENSIVA (taglia DD ~6x, non alpha).
- paper_trend.py: deploy a 1d (resample_1d, build_bars). 5 test passano.
- CLAUDE.md: TP01 ridescritta (>=12h/1d, gotcha ffill mixed-TF, difensiva).
- tp01_lowfreq.py + diario 2026-06-19-tp01-lookahead-fix-lf.md.
Gotcha: mai ffill/combine mixed-TF su timestamp open-labeled (close propagata indietro = leak).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 19:04:38 +00:00
Adriano Dal Pastro 756a2bdf04 research: stress-test TP01 — robusto come strategia DIFENSIVA (DD-cut), edge ritorno hold-out sottile
Stress sul modulo integrato: FULL regge fee 0.40% + lag + ampio plateau parametri (orizzonti
20/60/120 fa Sh 1.61, non cherry-pick); deflated-Sharpe DSR 0.999 a N=100 (no multiple-testing
artifact). MA il ritorno nel hold-out 2025-26 e' SOTTILE (+2.8%/Sh0.27 a 0.10%, ~flat a 0.40%/lag2):
TP01 PROTEGGE il drawdown (8% vs 60% buy&hold) piu' di quanto profitti. Proprieta' robusta e
deployabile = taglio DD; alpha = no. Da monitorare col paper trader prima di scalare.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 18:57:22 +00:00
Adriano Dal Pastro d152941360 integra(TP01): merge ricerca branch strategy-research-2026-06 (squash) — strategia vincente + harness + track A-E
Integra il lavoro della linea di ricerca parallela (AdrianoDev), verificato indipendentemente
col mio gauntlet onesto (regge il hold-out 2025-26 su entrambi gli asset, plateau 1h/4h/1d):
- src/strategies/trend_portfolio.py  TP01 (TSMOM 30/90/180 vol-target 20% lev2x long-flat, 50/50 BTC+ETH)
- src/backtest/harness.py            harness onesto (load + backtest_signals no-leakage + OOS)
- scripts/research/track{A,B,C,D,E}_*.py + trackD_timing.py  (le 5 track della ricerca)
- scripts/live/paper_trend.py        paper trader forward-only di TP01 (no esecuzione reale)
- tests/test_trend_portfolio.py (5 test, passano) + 6 diari trackA-E + synthesis
- CLAUDE.md aggiornato con l'esito ricerca (TP01 vincente, mean-rev morto, onesta su €50/g)

Squash (non merge) per NON portare in git i ~68MB di data/_feed_backup/*.bak che il branch
aveva committato per errore: esclusi + data/_feed_backup/ e data/paper_trend/ ora gitignorati.
Storia granulare del branch conservata sul ref origin/strategy-research-2026-06.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 18:55:04 +00:00
Adriano Dal Pastro 55c28e51b2 research: verify TP01 (branch parallelo) col gauntlet onesto — REGGE il hold-out 2025-26
TP01 (TSMOM 30/90/180 vol-target 20% lev2x long-flat, 50/50 BTC+ETH) passa dove il mio trend 1h
era caduto: hold-out 2025-26 +2.8%/DD8% vs buy&hold -39%/DD60%, positivo su ENTRAMBI gli asset,
plateau 1h/4h/1d. La chiave e' il vol-targeting (esposizione ~1/vol -> cash nei crash) che non
avevo combinato col trend. Edge DIFENSIVO reale (Sharpe full 1.36 vs B&H 0.92, ma CAGR 16.6% vs 48%).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 18:50:36 +00:00
Adriano Dal Pastro 38c8cdf25b research(v2.0.0): honest harness + fasi 0-3 + ricerca frattale 63 agenti — nessun edge robusto su BTC/ETH
Harness onesto research_lab.py (serie di posizione causale, fee-aware, null model a
rotazione circolare, hold-out 2025+ bloccato; self-test cheat/noise che valida il banco).
- Fase 1: triage superstiti (DIP, shape-ML) -> morti net-fee.
- Fase 2: esplorazione famiglie (reversal morta; solo trend long-only/MA-cross passa i gate base).
- Fase 3: conferma avversariale del trend -> regime-luck del toro, bocciato sul hold-out 2025-26.
- Ricerca frattale multi-agente (Workflow, 63 agenti, 52 ipotesi dai due documenti) con guard
  anti-look-ahead (eval_signal.py) + hold-out + test cross-asset -> 0 edge robusto (l'unico
  "confermato" su ETH fallisce su BTC con lo stesso codice).
- Analisi options: VRP reale +10/+14 vol pt ma finestra 6 sett. regime unico -> non validabile;
  ruolo solo overlay tail-cap, tenere cerbero-bite ad accumulare.

Quinta conferma indipendente: su BTC/ETH-solo-prezzo non c'e' un edge facile. Il processo
disciplinato ha evitato un falso "+49% vs -49%" che sul vecchio feed contaminato sarebbe
finito in produzione. Diari docs/diary/2026-06-19-research-phase0-1 / -phase2-options /
-phase3-confirm / -fractal-multiagent-search.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 18:37:05 +00:00
Adriano Dal Pastro 14522262e6 chore(reset): v2.0.0 — storico certificato Deribit mainnet, ripartenza pulita
Reset del progetto su fondamenta verificate dopo la scoperta che l'intera
libreria "validata OOS" era artefatto di feed contaminato (print fantasma del
feed Cerbero TESTNET + storico Binance/USDT).

- Storico ricostruito da Deribit MAINNET (ccxt pubblico, tokenless) e
  CERTIFICATO (certify_feed.py): BTC/ETH puliti su TUTTA la storia
  (mediana 2-6 bps vs Coinbase USD), integrita' OHLC + coerenza resample
  (maxΔ 0.00) + cross-venue OK. Alt esclusi (illiquidi/divergenti: LTC/DOGE
  50-82% barre flat; XRP/BNB non certificabili).
- Verdetto sul feed pulito: FADE / PAIRS / XS01 / TSM01 morti (ogni
  portafoglio Sharpe -2.3..-3.0, DD ~40%); solo SH01 e frammenti HONEST
  con segnale residuo, da ri-validare in isolamento.
- Cleanup "restart pulito": strategie, stack live (src/live, src/portfolio,
  runner/executor, yml, docker), ~100 script ricerca/gate, waste/games/
  portfolios, dati non certificati + cache e 60+ diari -> archiviati in Old/
  (preservati, non cancellati). Diario consolidato in un unico documento.
- Skeleton ricerca tenuto: Strategy ABC + indicatori + src/fractal +
  src/backtest/engine + load_data; tool dati certificati (rebuild_history,
  certify_feed, audit_feed, multi_source_check).
- Universo dati ATTIVO: solo BTC/ETH (5m/15m/1h); guardrail fisico
  (load_data su alt -> FileNotFoundError). Esecuzione DISABILITATA, conto flat.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 15:20:59 +00:00
Adriano Dal Pastro 8401a280b9 chore: bump 1.1.34 — GRID_BTC paper sleeve (Price Ladder shadow stage 1)
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 16:19:48 +00:00
Adriano Dal Pastro b4d4961d77 merge: Price Ladder research + GRID_BTC paper sleeve (shadow stage 1)
Porta su main: pulizia feed (clean_feed, 254 spike-print Binance), ricerca Price Ladder
(ladder_search/regate/sltp), GridWorker paper + validazione, wiring runner kind=grid +
paper_extra (PORT06 canonico INTATTO: 19 sleeve), GRID_BTC paper in portfolios.yml.
Tutto additive + validato; nessun ordine reale (grid sim-only).
2026-06-18 16:19:48 +00:00
Adriano Dal Pastro 264b9200ea feat(live): Stage 2 — GridWorker (Price Ladder) come PAPER sleeve nel runner
Wire del Price Ladder come sleeve PAPER (sim-only, fuori dal pool €500, NESSUN ordine reale):
- runner: kind="grid" -> GridWorker in build_worker_for; _spec_assets_tf grid; tick branch
  (w.tick(res[asset])); meccanismo PAPER_EXTRA (sleeve paper letti da overrides.paper_extra,
  NON da _defs.py -> NON entrano nel backtest canonico/regression-lock: PORT06 resta 19 sleeve).
  Parsing difensivo (un errore non crasha il runner mainnet). Loop dati estesi a paper_extra.
- GridWorker: bootstrap storia FULL (start fisso, come SH01) + mappatura capitale forward dal
  deploy (capital = initial*eq[-1]/base_norm) -> niente salti da finestra mobile; base_norm
  persistito (resume). grid_mtm robusto al df live (timestamp senza datetime; param df).
- portfolios.yml: GRID_BTC in paper_extra (regime range1.5, rd0.20/ru0.06, L6, sl0.10/tp0.03,
  position_size 0.15 PINNATO). Gira in data/portfolio_paper_stats/GRID_BTC/.
Validazione (validate_grid_worker.py): [A] logica n_trades==backtest, [B] forward-tracking
esatto, [C] resume esatto. Dry-test integrazione runner: import OK, build OK, tick OK, pos 0.15.
SICUREZZA: kind=grid mai eseguito reale (runner avvia ordini solo per single/ml); €500 intatti.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 16:18:53 +00:00
Adriano Dal Pastro b3d4ab7150 feat(live): GridWorker (Price Ladder) SIM/PAPER + validazione replay==backtest — shadow stage 1
Stage 1 dello shadow per il Price Ladder (config finale: BTC 1h range1.5 rd0.20 ru0.06 L6
sl0.10 tp0.03). GridWorker (src/live/grid_worker.py) gira sul feed LIVE e contabilizza
l'equity mark-to-market col motore CANONICO grid_mtm (parita' col backtest per costruzione),
SENZA piazzare ordini reali (sim/paper). Stato persistente + resume. grid_mtm esteso con
param df=None (retro-compatibile: il feed live passa il df; None = _load come prima, gate
invariato — BTC ladder 10.8/5.9, PORT06 base 8.18 identici). Validazione
validate_grid_worker.py: [A] full-tick == grid_mtm esatto, [B] replay incrementale converge
esatto, [C] resume entro la persistenza (4 dec) -> VALIDAZIONE OK.

NB SICUREZZA: nessuna modifica a runner/portfolios.yml/_defs -> il sistema mainnet (€500
reali) e' INTATTO; il worker e' inerte finche' non wirato. L'esecuzione REALE (griglia di
LIMIT resting su Deribit, fill parziali/episodi) e' lo stage 2-3, dietro testnet +
autorizzazione esplicita. Il runner avvia ordini reali solo per kind in (single,ml);
kind=grid resta sim per costruzione.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 14:58:11 +00:00
Adriano Dal Pastro 587fbc0f61 feat(analysis): ladder_sltp_study — 3 passi pre-deploy + SL/TP, config finale ladder
I 3 passi: [1] valutazione 2018-INCLUSIVE (il gate IDX2021+ e' cieco al 2018) -> il tail
vero del BTC ladder e' il 2018 (-27.7% regime-gated / -50% none); [2] fill maker 0% vs
taker 0.10% (Deribit = LIMIT = maker) -> maker leggermente MIGLIORE, harness conservativa,
nessun fee-cliff; [3] half-size (la coda 2018 si dimezza sul book). STUDIO SL/TP: sweet spot
sl_buf=0.10/tp_buf=0.03 cappa il 2018 a -23.5% (da -27.7) senza intaccare l'edge (oos 5.06).
Lezione (conferma prior progetto): SL troppo stretto PEGGIORA (redeploy nel coltello = falso
negativo MR), SL da solo senza regime-gate e' erratico -> il regime-gate e' il controllo
PRIMARIO della coda, il SL moderato fine-tuna. Config finale: BTC 1h range1.5 rd0.20 ru0.06
L6 sl0.10 tp0.03 half-size, PROMOSSO (OOS 10.86->11.0, corr 0.195). Unico passo residuo:
shadow ledger reale (operativo). Diario sez. 8.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 14:48:39 +00:00
Adriano Dal Pastro 8abeb7a83f docs(diary)+feat(analysis): re-gate Price Ladder su dati puliti — tail vero = 2018
ladder_regate_clean.py ri-valuta i top candidati dopo clean_feed.py con gate PORT06 +
stress close_only + DD per anno. Esiti (sez. 7 diario): (1) l'obiezione "coda artefatto"
CADE -- il 54% BTC era spike-print 2024, ora DD gate (2021+) ~11-15%, tutti PROMOSSO half,
corr 0.22-0.29, reggono fee2x = candidati VERI; (2) emerge il tail REALE = 2018 (-44/-52%
standalone) che il gate NON vede (IDX parte dal 2021) -> lacuna metodologica generale; il
regime-gate stretto (BTC rd0.2 L6 range1.5) lo dimezza a -27.7%; (3) l'edge dipende dai fill
INTRABAR (close_only crolla 4.7->0.24): legittimo per LIMIT ma serve shadow ledger.
Verdetto: miglior candidato BTC 1h rd0.20 ru0.06 L6 range1.5 (PROMOSSO, corr 0.23, miglior
coda 2018); prima del deploy servono gate 2018-inclusive + shadow fill + half-size.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 14:42:18 +00:00
Adriano Dal Pastro b9e3388f76 feat(data): clean_feed — ripara spike-print del feed Deribit coi dati reali Binance
La ricerca Price Ladder ha rivelato spike-print nei parquet storici (es. BTC 2024-02-13
low 38.580 / high fasulli, BTC reale ~50k) = stesso problema TP_PHANTOM/feed testnet di
CLAUDE.md, che avvelena i backtest (stop/entry su prezzi mai avvenuti) e gonfia le code.
Tool conservativo: DETECT (wick >15% oltre il cluster close locale) -> ARBITRA con Binance
spot (ccxt, gia' cablato): sostituisce O/H/L/C solo se Binance dissente >2% su high/low (un
wick VERO confermato da Binance resta intatto), backup in data/_feed_backup/ + scrittura
atomica + validazione. RIPARATE 254 barre (BTC 132, ETH 122) su 8 file BTC/ETH x TF; 2 wick
reali confermati da Binance e TENUTI (ETH 30m/1h flash-crash veri). Impatto validato: il
BTC ladder che dava FULL DD 53.69% (artefatto) ora ne da 10.8% (la "coda di trend" era spike
fasulli); PORT06 baseline FULL Sharpe 8.13->8.18, DD/OOS invariati (canonici stabili).
data/raw e' gitignored: e' committato il TOOL, non i parquet (rigenerabili + backup locale).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 14:25:34 +00:00
Adriano Dal Pastro e631e1b89c docs(diary): price-ladder search 2026-06-18 — verdetto RETTIFICATO (nessun deploy)
Caccia multi-agente (34 agenti, 200 celle) a Price Ladder che passi il gate PORT06 su
Deribit. La sintesi iniziale trovava candidati "deployabili" (ETH 1h range-gated half-size,
OOS 10.86->11.0; BTC half-size OOS->11.34). Il critico + verifica dati ROVESCIANO il verdetto
(sez. 6): (1) la "coda BTC ~54%" e' DATI CORROTTI da spike-print (37 barre >20% intrabar, feb-2024
wick fasullo -23%, min 22.7k/max 104.7k vs BTC reale ~47-57k = stesso problema TP_PHANTOM/feed
testnet di CLAUDE.md) -> BTC non affidabile, lo stress-2022 non toccherebbe la coda vera;
(2) il +0.14 OOS Sharpe e' rumore al peso deployabile (~2.7% half, 592g regime calmo, no
significativita'); (3) il finalista ETH e' corr 0.305 (vicino allo 0.40 che fece bocciare la
griglia originale) e il regime_mask condivide il filtro trend con le fade ETH live; (4) FULL DD
standalone mascherata dal compounding (31x); (5) close_only disponibile ma non girato sui
finalisti. VERDETTO: nessun Price Ladder deployabile dimostrato; il multi-agente+critico ha
evitato un deploy ingiustificato. Config live INVARIATA. Harness validata resta come record.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 14:16:54 +00:00
Adriano Dal Pastro d733196564 feat(analysis): ladder_search — harness caccia Price Ladder che passi il gate PORT06
Goal "decine di agenti a cercare strategie Price Ladder" (Deribit). Riusa il motore
grid_mtm mark-to-market ONESTO (SL gap-aware, flat-skip, fee 0.10% RT taker = CONSERVATIVO
su Deribit, dove i fill ai livelli LIMIT sono maker ~0%) ed espone:
  - eval  <asset tf rd ru levels sl_buf tp_buf max_bars [regime] [trend_max]>
  - scan  <asset tf [regime] [trend_max]>  (sub-griglia struttura, gate PORT06, baseline
    cachata) -> top celle con verdetto gate + max_corr coi 19 sleeve + FULL DD.
Leva NUOVA: regime-gate `range` (deploy_mask in grid_mtm, retro-compatibile) = deploya la
griglia SOLO in regime di range (|close-EMA200|/ATR < trend_max), dove la griglia vive, e
non in trend dove muore. Contesto della ricerca: la griglia ETH del gioco e' BOCCIATA
(ridondante, corr 0.40); i ladder BTC sono meno correlati (~0.18) e passano il gate, MA il
nodo e' la FULL DD (coda di trend 2021/22, ~60% standalone) che il verdetto del gate NON
controlla -> la harness la espone (full_dd standalone + full_full_dd di portafoglio).
grid_mtm: aggiunto param deploy_mask (None = comportamento storico, parita' col gate).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 12:29:25 +00:00
Adriano Dal Pastro 57758ffcb1 feat(analysis): leverage_sweep — sweep leva 1-10, stress 2022, leva max raccomandata
Risponde a "se porto a leva 10 cosa succede?". Sweep leva 1->10 su PORT06
(modello daily lineare == live) FULL/OOS + anno per anno (2021-2026), con le
non-linearita' che il modello daily NASCONDE: volatility drag/Kelly, rovina
intraday vs daily. Stress con shock REALI 2022 (BTC/ETH storici: LUNA -29/-36%,
3AC-giugno -44/-52%, FTX -26/-32%) sull'esposizione netta del book -> leva di
rovina per net-long beta. Verdetto: leva 10 NON sopravvive a un 2022-repeat
(rovina gia' a ~5-9x se net-long). Leva MAX raccomandata ~3x (DD<=50% recuperabile,
beta=0.6) == config live attuale. Non modifica nulla del live.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 09:48:33 +00:00
Adriano Dal Pastro c8b956ab56 fix(dashboard): PnL totale dal ledger, non init hardcoded 2000
La KPI "PnL totale" sottraeva un capitale iniziale fisso di 2000 (retaggio
testnet) -> sul micro-test mainnet da 500 mostrava -1499 (-74.95%) invece di
+0.95 (+0.19%). Nuovo helper _ledger_pnl(): legge pnl_total dall'ultima riga
di equity.jsonl (il ledger lo scrive come equity-initial_capital) e ne deriva
l'iniziale -> la dashboard combacia col ledger per costruzione, qualunque sia
il capitale (500 mainnet / 2000 testnet), niente piu' valori fissi da
aggiornare a mano. Fallback: primo punto equity, poi l'equity stessa.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-18 09:48:33 +00:00
Adriano Dal Pastro 3b60289cbd fix(gitignore): commento su riga propria per data/funds_watch.json
Il commento inline rendeva il pattern non-matchante (gitignore non
supporta i commenti a fine riga).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-17 21:16:13 +00:00
Adriano Dal Pastro e328836614 feat(live): switch a MAINNET — micro-test fade-only €500 + funds-watch
Conversione testnet -> mainnet Deribit (soldi veri). Vedi
docs/specs/mainnet-microtest-plan.md, Fase 1.

- portfolios.yml: total_capital 500, leva 3, weighting equal; eseguono
  REALE solo i 7 single-leg (6 fade MR01/02/07 x BTC/ETH 15m + DIP01 1h);
  pairs/SH01/multi-asset -> paper (rumore arrotondamento a €500); real_truth.
- docker-compose.yml: portfolio+dashboard caricano anche .env.mainnet
  (token mainnet, prevale su .env; .env.mainnet resta gitignored).
- reconcile_account.py: watermark FONDI (compute_funds_change) — rileva
  aumenti di capitale (deposito/top-up) e cali anomali (prelievo) sul
  balance USDC, alert Telegram FUNDS_INCREASE/FUNDS_DECREASE; soglia
  max(€25, 5%). Stato in data/funds_watch.json (host-writable).
- .gitignore: ignora data/funds_watch.json (stato runtime).

Ledger testnet archiviato in data/_reset_backup/pre_mainnet_*.tgz e azzerato.
Crons host ri-puntati al conto reale (sourcing .env + .env.mainnet).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-17 21:15:55 +00:00
Adriano Dal Pastro a0842a61cc feat(analysis): trades_status — PnL live per posizione aperta (entry reale vs mark USDC)
Riusa la convenzione della dashboard (get_ticker_batch USDC perp, real_entry vs mark;
pairs a 2 gambe). Mostra unrealized per trade + Σ REALE, e segnala che il ledger
unrealized e' sul feed sim-decisione testnet DISLOCATO (lo scarto e' dislocazione,
non soldi). Fix sys.path: import src.* anche eseguito come script file.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-17 15:56:22 +00:00
Adriano Dal Pastro 3a66907f43 feat(analysis): trades_status.py — report stato trades con POOL reale vs PAPER-STATS separati
La dir e' la fonte di verita': portfolio_paper/ = pool (ledger/equity), portfolio_paper_stats/
= TR01/ROT02/TSM01/XS01 solo statistica. Niente piu' glob su portfolio_paper* (matchava
entrambi -> +8.15 XS01 sim attribuiti per sbaglio all'equity il 2026-06-17). Mostra realizzato
POOL + unrealized aperti e riconcilia con Δequity del ledger. Caveat + comando in CLAUDE.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-17 15:17:50 +00:00
Adriano Dal Pastro aee53161c3 docs: Fase 0 smoke mainnet VERDE (ETH->USDC limit) + aggiorna piano micro-test
Catena d'esecuzione validata su mainnet con soldi veri a costo ~0: LIMIT SELL ETH_USDC
0.0138 @ floor 1776.3 -> filled@1778.1 (=bid), fee 0, USDC 25->49.54. Consolidato l'ETH
stranded in margine USDC. Funding parziale ~$49.54 (sotto il min EUR500) -> Fase 1 in
attesa di top-up a ~EUR1000. Diario + STATO/checklist del piano aggiornati.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-16 15:48:38 +00:00
Adriano Dal Pastro 7b3e554424 release: v1.1.33 2026-06-16 14:16:22 +00:00
Adriano Dal Pastro b576ee66ac feat(worker): guard TP-invertito — sopprime l'entry quando il TP e' gia' sfondato (wick-print)
Un wick transitorio fa calcolare un tp dal lato sbagliato dell'entry (donchian: segnale
su barra wickata, entry al prezzo recuperato oltre il proprio tp) -> l'exit intrabar
scatta a bars_held=0 in perdita (16-06: 8 giri MR02_BTC 15m, sim -17.9 / reale -2.3).
TP_PHANTOM non lo prende (niente resting oracle, prezzo oltre il livello). Gate
zero-parametri in StrategyWorker._open_position, solo path live. Test + diario + CLAUDE.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-16 14:16:13 +00:00
Adriano Dal Pastro ef797f1ff0 release: v1.1.32 2026-06-15 08:44:42 +00:00
Adriano Dal Pastro 4c184d5cbc feat(runner): gate feed CONGELATO — sospende gli sleeve ETH-leg finche' il feed non si sblocca
Audit "stato ordini": il feed ETH-PERPETUAL congelato a 1661.95 (36h+) generava
perdite REALI (SH01_ETH -2.83 reali vs -0.09 sim su un close + riapertura; 4 pairs
con gamba ETH entrati su z-score spuri -3/-5/+5.6 = artefatto del log-ratio con ETH
pinnato mentre gli alt si muovono).

_frozen_assets + _feed_gated_sids: quando il feed di decisione 1h di un asset e'
congelato, gli sleeve concentrati (single/ml/pairs) che ne dipendono saltano il tick
(entry+exit) finche' non si sblocca (come outage; disaster-SL on-book = coda).
Auto-guarente: rilascio alla prima barra COMPLETA non-flat (NON l'entry-guard
post-flat bocciata). Detector guasto-vs-illiquido: conta la run di close INVARIATE
(ETH/BNB/DOGE run 40-64, 1-4 val/48h = morti; SOL/LTC/ADA run <=12, 5-31 val = vivi).
Soglia feed_freeze_gate_bars=24 -> gatea le 9 gambe ETH esatte, PR_BTCLTC e i
multi-asset restano attivi. Alert Telegram FEED_FROZEN_GATE GATED/RIPRESO.

Test test_freeze_gate.py (6, detector+scope+rilascio). Suite portfolio 140/140.
Cerotto testnet: il fix vero e' mainnet. Diario 2026-06-15-frozen-feed-gate.md.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-15 08:44:39 +00:00
Adriano Dal Pastro c21e1dc635 docs: timing-sweep pairs/honest (NO deploy) + stato mainnet + vincolo feed v2
- CLAUDE: feed ETH ancora congelato 36h+; vincolo Cerbero v2 (serve SOLO
  5m/15m/1h, 30m/10m -> 400, legacy 404; _SUBHOURLY "30m" speculativo mai
  testato); esito timing-sweep (5m non conviene: regime recente peggiore +
  flat ETH 29%; gate full+OOS necessario ma non sufficiente); stato mainnet
  (token in .env.mainnet verificato is_mainnet=True, conto VUOTO = blocco)
- spec mainnet-microtest: blocco STATO 2026-06-14, .env.mainnet separato +
  servizio dedicato, checklist aggiornata (token done, funding = blocco)
- nuovo diario 2026-06-14-timing-sweep-pairs-honest.md + harness riusabile
  scripts/analysis/timing_sweep_pairs_honest.py
- .gitignore: .env.mainnet (token mainnet mai in git)

Nessuna modifica a codice/config live: PORT06 invariato (19 sleeve).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-14 20:19:56 +00:00
Adriano Dal Pastro 47e92a0425 docs(CLAUDE): aggiorna memoria — dashboard, report ledger-vs-backtest, feed ETH congelato, micro-test mainnet
Fatti di sessione: dashboard web (porta 8787), cron ledger-vs-backtest (gate scaling),
caveat feed testnet ETH-PERPETUAL congelato (spiega 0-trade fade ETH 15m; fix=mainnet),
piano micro-test mainnet + token Cerbero env-configurabile (CERBERO_TOKEN).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 22:46:29 +00:00
Adriano Dal Pastro faf08b3988 docs(spec): piano micro-test mainnet + token Cerbero env-configurabile
Piano operativo per validare l'edge su mainnet con poco denaro reale (il gate per
scalare). Fasi: smoke -> fade-only €1000 2-4 sett -> verdetto ledger-vs-backtest ->
espansione. Sizing motivato (fades €1000 = rumore arrotondamento 2.6% BTC; pairs
esclusi: 30% a quella taglia). Token ora da env CERBERO_TOKEN (default testnet
invariato) -> switch mainnet = solo .env, niente codice. is_mainnet() helper.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 22:36:26 +00:00
Adriano Dal Pastro 3ac8a46e6a feat(dashboard): trade attivi con data/ora ingresso + tempo in posizione
Nuove colonne 'Ingresso (UTC)' (entry_time) e 'In posizione' (durata dall'ingresso,
formattata m/h/g) con flag stantio. Sostituisce la colonna Eta (staleness) col
tempo di holding effettivo.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 22:24:22 +00:00
Adriano Dal Pastro 7ee5b1767f feat(dashboard): solo dati REALI nei trade attivi + valore mercato reale (anche pairs) + attivi sotto il grafico
- entry/mark/unrealized SEMPRE reali (entry di esecuzione vs mark USDC live); il
  feed sim/decisione (testnet inverse dislocato) non e' piu' mostrato come prezzo
- pairs: valore di mercato reale di ENTRAMBE le gambe + PnL non realizzato reale a
  2 gambe (prima 'pairs (z)' senza valore)
- tabella attivi spostata subito sotto il grafico equity

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 22:21:22 +00:00
Adriano Dal Pastro d5a83075f8 fix(dashboard): unrealized usa entry REALE (non sim) per coerenza col mark reale
Le posizioni eseguite mostravano l'entry SIM (feed decisione testnet inverse,
dislocato ~1.3% dal lineare USDC) confrontato col mark REALE -> unrealized gonfiato
(SH01_ETH -1.36% invece di ~-0.25%) e due trade ETH con lo stesso entry sim 1661.95.
Ora entry = real_entry_price/real_entry_a se eseguito; unrealized vs mark reale su
base coerente. Indicatore '⚠sim' quando il feed di decisione diverge dal reale.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 22:13:48 +00:00
Adriano Dal Pastro 183209dbd4 feat(dashboard): grafico equity per famiglia + tabella strategie raggruppata per famiglia
- nuovo grafico multi-linea 'Equity per famiglia' (PnL cumulato realizzato di ogni
  famiglia su asse-tempo comune, colori per famiglia, legenda col totale)
- tabella strategie reali raggruppata per famiglia con intestazioni colorate +
  PnL di famiglia; attive prima delle ritirate dentro ogni gruppo
- backend: fam_curves (step-wise cumulato per famiglia dai CLOSE reali), tag fam
  sui trade chiusi

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 21:48:56 +00:00
Adriano Dal Pastro e311d00fe4 fix(dashboard): tooltip equity allineato al mouse (responsive canvas)
Forzare l'altezza del canvas via CSS !important con maintainAspectRatio default
sfalsava la risoluzione interna vs quella mostrata -> hit-test tooltip offset dal
mouse. Fix canonico: canvas in contenitore .chartbox ad altezza fissa + chart
responsive:true/maintainAspectRatio:false + interaction index su tutti e 3 i grafici
(equity, modal, paper).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 21:35:15 +00:00
Adriano Dal Pastro 37ffe92498 docs(report): strategie_attive.html aggiornato a config live (fade 15m, leva 3x)
Era fermo al 2026-06-12 06:17 (pre-swap): diceva fade 'intraday 1h' e 'leva 2x'.
Rigenerato -> numeri post-swap (FULL Sh 8.13/DD 2.47%, OOS 10.86/2.09%) + fix
etichette hardcoded nel generatore (header FADE 1h->15m, leva 2x->3x, nota tabella).
E' la scheda linkata dal modal della dashboard.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 21:30:28 +00:00
Adriano Dal Pastro f6287fcd36 feat(dashboard): area PAPER distinta con equity separata
I 4 multi-asset (TR01/ROT02/TSM01/XS01, solo statistica fuori dal pool reale) ora
in una zona dedicata con la PROPRIA equity (capitale nozionale + PnL cumulato del
book paper) e tabella separata. La tabella/fam_pnl/closed dell'area principale
diventano SOLO reali. Curva paper Chart.js (ocra), cliccabile -> stesso modal.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 21:25:17 +00:00
Adriano Dal Pastro b6b465878a feat(dashboard): scheda per strategia (modal: curva PnL reale vs sim + trade + link grafici) + versione sistema/strategia + equity restyling
- click su una strategia -> modal con descrizione, versione di creazione/modifica,
  curva PnL CUMULATO reale vs sim (mostra il leakage), trade, e link alla scheda
  dettagliata strategie_attive.html (servita, docs/report montato ro)
- versione di sistema (APP_VERSION) nell'header; per ogni strategia la versione/
  origine documentata (mappa VERSIONS da CLAUDE.md)
- equity restyling: gradiente verde/rosso secondo segno, tooltip con EUR e delta,
  valore+delta in testata, assi in EUR, piu' alto. /api/strategy con guard
  path-traversal.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 21:20:33 +00:00
Adriano Dal Pastro 22af19c7f9 feat(dashboard): badge strategie RITIRATE (staleness) + descrizioni per strategia
Le fade 1h sostituite dallo swap 15m sono marcate RITIRATA→15m (rilevate per
status.json stantio >30min, ordinate in fondo, riga barrata). Descrizioni concise
per ogni strategia (da strategie_attive.html) come tooltip + sezione legenda.
Fix rilevazione paper: per directory (portfolio_paper_stats), non per chiave
'weights' (TR01/TSM01/XS01 non ce l'hanno) -> ora i 4 multi-asset sono paper.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 21:12:42 +00:00
Adriano Dal Pastro 31f08ddf32 feat(dashboard): frontend web PORT06 — stato live, PnL totale/per-strategia, grafici, trade
Server stdlib http.server (zero dipendenze nuove) che legge data/: KPI equity/PnL/DD,
grafico equity (Chart.js CDN + fallback), PnL per-strategia (barre, realizzato reale),
trade attivi in TEMPO REALE (mark Cerbero best-effort, PnL non realizzato, barre, eta
stantio) e chiusi (ultimi 50). Servizio docker-compose 'dashboard' porta 8787, stessa
immagine, monta data/, restart unless-stopped + healthcheck. Nessuna auth -> rete interna.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 19:46:47 +00:00
Adriano Dal Pastro dc22256e0e feat(report): ledger reale vs backtest — il gate per scalare il capitale
Per gli sleeve eseguiti sim==backtest per costruzione -> reale vs backtest =
fuga di esecuzione (slippage + fee + netting/phantom/sim_fallback). Misura
LEAKAGE sim-reale per-trade, slippage ingressi/uscite, fee reali, sim_fallback,
ledger per-sleeve; verdetto verde/giallo/rosso. Clean-start --since 2026-06-13
(la finestra mobile includerebbe l'incidente testnet pre-fix). Cron host
giornaliero 08:30 UTC --telegram. Read-only, niente rete.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 11:24:19 +00:00
Adriano Dal Pastro 6fe45867f0 docs(CLAUDE): stato live v1.1.31 — leva 3x, swap fade 15m, lineage, stale-guard, ribilancio conservativo
Aggiorna il doc canonico: default PORT06 ora leva 3x + fade 15m (FULL 8.13/OOS
10.86), e i fix di sessione: INIT_LINEAGE, STALE_REAL_POSITION, conservazione
equity al ribilancio. TF sweep (1m/2m/5m/10m) annotato.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 10:21:27 +00:00
Adriano Dal Pastro ab9899b0c4 release: v1.1.31 2026-06-13 10:09:57 +00:00
Adriano Dal Pastro 432c1ad790 fix(ledger): ribilancio conserva l'equity (no doppio conteggio in-position)
Bug: i flat si dividevano l'INTERO total includendo il capitale dei worker in
posizione, che lo trattenevano in piu' -> equity gonfiata di Sigma(capital-alloc)
sugli in-pos. Caso MR02_BTC 15m seedato (181.19) e in posizione al ribilancio
00:01: +4.77 fantasma. allocate(weights, reserved={sid:cap}): gli in-pos
trattengono il loro, i flat si dividono total-Sigma(reserved) per peso
rinormalizzato -> Sigma alloc == total sempre. Parita' runner intatta
(5.8e-08). Test conservazione (ledger + runner). Suite verde.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 10:09:36 +00:00
Adriano Dal Pastro 85043bf2d3 feat(reconcile): guard STALE_REAL_POSITION — rileva posizioni reali non gestite
Caso MR02_BTC 1h (2026-06-13): ritirato dallo swap a 15m mentre short reale ->
short nudo (TP perso nel netting), reconciler cieco perche' lo status fermo
contava ancora come libro. compute_stale_real_positions: worker con
real_in_position e status.json fermo >15min = non gestito -> alert
STALE_REAL_POSITION. Discriminante = staleness (venue-agnostico: cattura
ritirati-da-swap/crashati). Gira dal cron host :40 (no rebuild). 3 test nuovi,
suite 132 passed. Orfano chiuso a mano (testnet, +0.85 netto).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-13 09:43:47 +00:00
Adriano Dal Pastro 643ff7f943 feat(live): INIT_LINEAGE — eredita' capitale al cambio timeframe + sweep migliorie serale
Worker nuovo (no status.json) eredita capital/real_capital dal gemello piu'
recente stessa strategia+asset (mai la posizione): niente piu' seed manuale
al prossimo swap. 3 test nuovi, suite 129 passed.
Ricerca: gate 10m ADD bocciato (OOS Sh 10.86->10.76, watchlist chiusa);
XSEC breadth 8->14 Deribit BOCCIATO (gambe flat 91-99% corrompono il ranking)
ma promettente su dati HL reali (-6%->+9% stessa finestra) -> sblocco = routing
dati Hyperliquid quando la storia sara' sufficiente.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-12 21:18:30 +00:00
Adriano Dal Pastro 12e71d4c8b research: fade TF sweep 1m/2m/5m/10m/30m — 15m confermato, 10m in watchlist, 1m/2m chiusi
Frontiera Sharpe monotona al scendere del tf ma margine fee si assottiglia:
MR02_BTC muore a fee2x a 5m (-1.70); MR02 sotto i 15m e' fee-death nel regime
corrente (1m -64%). 1m: flat share ETH 25.6% + niente storia full -> chiuso.
Corr col 15m live: 5m 0.46 / 10m 0.53. Fix resample unit-safe (pandas 2.x ms).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-12 20:56:15 +00:00
Adriano Dal Pastro 378ec7fb43 release: v1.1.30 2026-06-12 20:47:45 +00:00
Adriano Dal Pastro f78380596a feat(live): SWAP fade 1h -> 15m su PORT06 (scelta utente, gate fade15m_port06_gate)
FADE specs tf=15m (sid invariati -> pesi/alloc intatti; DIP01 resta 1h);
builder canonico allineato (combine_portfolio.FADE_TF) -> parita' delle due
facce; regression-lock aggiornato al nuovo baseline (FULL Sh 7.34->8.13
DD 3.46->2.47, OOS Sh 10.07->10.86 DD 1.48->2.09). Runner invariato (fetch
15m gia' esistente dal blend pairs). Suite 126 passed.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-12 20:47:44 +00:00
1396 changed files with 227812 additions and 1643 deletions
+11
View File
@@ -0,0 +1,11 @@
Old/
data/
.venv/
.git/
logs/
__pycache__/
**/__pycache__/
*.pyc
.env
.env.mainnet
docs/
+7
View File
@@ -0,0 +1,7 @@
# Credenziali IB Gateway PAPER per la ricerca dati (account paper, es. DUQ513966).
# COPIA questo file in .env.ibgw (gitignored) e riempi i valori REALI.
# cp .env.ibgw.example .env.ibgw && chmod 600 .env.ibgw && nano .env.ibgw
# NON committare mai .env.ibgw. Sono credenziali del CONTO PAPER (nessun denaro reale),
# l'API e' comunque READ_ONLY (solo dati storici, nessun ordine).
TWS_USERID=il_tuo_username_paper
TWS_PASSWORD=la_tua_password_paper
+60
View File
@@ -6,6 +6,8 @@ build/
.venv/
.env
!.env.example
.env.ibgw
!.env.ibgw.example
.vscode/
.idea/
.DS_Store
@@ -20,6 +22,8 @@ data/paper_trades/
data/portfolio_paper/
data/portfolio_paper_stats/
data/portfolios/
# watermark fondi del reconciler (stato runtime, contiene il balance)
data/funds_watch.json
# stato locale di tooling (non condiviso)
.claude/
@@ -27,6 +31,7 @@ data/portfolios/
# dati regime (DVOL/funding/feature cache, rigenerabili)
data/regime/
data/venue_watch/
_disp_scratch/
data/regime/dispersion_features.parquet
@@ -36,3 +41,58 @@ data/_reset_backup/
# game artifacts (log/json di scripts/games e gate)
data/games/
.env.mainnet
# archived data (mirrors top-level data/ ignores, which are top-level-anchored)
Old/data/
Old/**/__pycache__/
# run logs (rigenerabili dagli script)
logs/
# cache di ricerca rigenerabile (serie d'ancora, tabelle di segnale intra-bin SKH01):
# 22MB, ~2.4h a ricostruirla, ma e' DERIVATA dai parquet certificati -> non si versiona.
data/_cache/
# cache della ricerca trackE (rigenerabile)
.cache_trackE_*.npy
# feed backup pre-rebuild (binari rigenerabili, NON in git) + stato paper trader (runtime)
data/_feed_backup/
data/paper_trend/
data/paper_portfolio/
# output grezzo dello sweep di ricerca xsec (rigenerabile dagli script in runs/)
scripts/research/xsec/runs/out/
# blind-signal derived data (regenerable via make_blind.py)
data/blind/
scripts/research/blind/leaderboard.json
# forward-monitor runtime state (regenerable, forward-only)
data/paper_prevday/
data/paper_combo/
data/paper_statarb/
data/paper_xsr/
data/paper_dvolspread/
# stato della sorveglianza fee (ultima lettura del tier Deribit, per rilevarne i cambiamenti)
data/fee_watch/
# battuta di cuore del collettore catena (stato runtime, come gli altri monitor)
data/chain_collect/
data/vrp_f_watch/
# giri misurati del trigger di regime CC01 (letti da monitor_health, #12)
data/cc01_regime/
# giri misurati dei sorveglianti generalizzati da cc01 (#16), letti da monitor_health
data/edge_watch/
data/scale_watch/
data/venue_news/
# log esecuzioni del book live (stato runtime, contiene fill/fee del conto reale)
data/live/
# dati esterni di ricerca (on-chain CoinMetrics community, F&G) — non certificati, non in git
data/external/
data/options_daily/
# libro di bordo: il DB e' dato operativo (coperto dal backup), non codice
data/live/trades.db
data/cache_regime_capitale.json
+731 -522
View File
File diff suppressed because it is too large Load Diff
+3 -10
View File
@@ -1,18 +1,11 @@
FROM python:3.11-slim
COPY --from=ghcr.io/astral-sh/uv:latest /uv /usr/local/bin/uv
WORKDIR /app
COPY pyproject.toml uv.lock ./
RUN uv sync --frozen --no-dev
COPY src/ src/
COPY scripts/ scripts/
COPY strategies.yml portfolios.yml VERSION ./
COPY VERSION ./
VOLUME /app/data
# Default: paper trader multi-strategia. Il servizio "portfolio" in docker-compose
# sovrascrive il command per il runner a portafoglio (src.portfolio.runner).
CMD ["uv", "run", "python", "-m", "src.live.multi_runner"]
# Monitor PAPER del portafoglio attivo (TP01+XS01). Esecuzione REALE disabilitata.
CMD ["uv", "run", "python", "-m", "src.live.dashboard", "--port", "8787"]
+18
View File
@@ -0,0 +1,18 @@
FROM python:3.11-slim
COPY --from=ghcr.io/astral-sh/uv:latest /uv /usr/local/bin/uv
WORKDIR /app
COPY pyproject.toml uv.lock ./
RUN uv sync --frozen --no-dev
COPY src/ src/
COPY scripts/ scripts/
COPY strategies.yml portfolios.yml VERSION ./
VOLUME /app/data
# Default: paper trader multi-strategia. Il servizio "portfolio" in docker-compose
# sovrascrive il command per il runner a portafoglio (src.portfolio.runner).
CMD ["uv", "run", "python", "-m", "src.live.multi_runner"]
+49
View File
@@ -0,0 +1,49 @@
services:
portfolio:
build: .
container_name: pythagoras-portfolio
restart: unless-stopped
command: ["uv", "run", "python", "-m", "src.portfolio.runner"]
volumes:
- ./data:/app/data
- ./portfolios.yml:/app/portfolios.yml:ro
env_file:
- .env
- .env.mainnet # token MAINNET (soldi veri); prevale su .env (vedi micro-test plan)
environment:
- PYTHONUNBUFFERED=1
healthcheck:
test: ["CMD", "python", "-c", "import os; assert any(f.endswith('status.json') for r,d,fs in os.walk('/app/data/portfolios') for f in fs)"]
interval: 120s
timeout: 10s
retries: 3
labels:
- com.centurylinklabs.watchtower.enable=false
# Dashboard web read-only (stato live, PnL totale/per-strategia, grafico equity,
# trade attivi+chiusi). Stessa immagine del runner, monta gli stessi data/ in sola
# lettura logica (legge equity.jsonl + status/trades dei worker). Porta 8787.
# NB: nessuna auth -> non esporre su internet pubblico, solo rete interna/VPN.
dashboard:
build: .
container_name: pythagoras-dashboard
restart: unless-stopped
command: ["uv", "run", "python", "-m", "src.live.dashboard", "--port", "8787"]
ports:
- "8787:8787"
volumes:
- ./data:/app/data
- ./portfolios.yml:/app/portfolios.yml:ro
- ./docs/report:/app/docs/report:ro # scheda strategie_attive.html (modal "scheda dettagliata")
env_file:
- .env
- .env.mainnet # token MAINNET (soldi veri); prevale su .env (vedi micro-test plan)
environment:
- PYTHONUNBUFFERED=1
healthcheck:
test: ["CMD", "python", "-c", "import urllib.request; urllib.request.urlopen('http://localhost:8787/api/state', timeout=5)"]
interval: 120s
timeout: 10s
retries: 3
labels:
- com.centurylinklabs.watchtower.enable=false
View File
@@ -0,0 +1,57 @@
# 2026-06-12 — FADE TF SWEEP: 1m / 2m / 5m / 10m / 30m (post-swap 15m)
Richiesta utente: estendere l'analisi timeframe dei fade oltre il 15m appena
deployato (v1.1.30). Script: `scripts/analysis/fade_tf_sweep.py`.
Dati: parquet locale (5m/15m/30m full-history; 10m = resample dal 5m, unit-safe);
1m/2m da Cerbero (120 giorni recenti — la storia 1m locale non esiste: esclusa
dal refresh notturno per costo, 2m/10m non sono intervalli nativi del v2).
## A. Storia completa (engine canonico, OOS da 2024-10, fee 0.10% RT)
OOS Sharpe per timeframe (e OOS Sharpe a fee 2x del peggiore):
| tf | MR01_BTC | MR02_BTC | MR07_BTC | MR01_ETH | MR02_ETH | MR07_ETH | worst f2x |
|----|---------|---------|---------|---------|---------|---------|-----------|
| 5m | 3.66 | 1.90 | 4.12 | 5.31 | 6.54 | 5.52 | **MR02_BTC −1.70** |
| 10m | 2.62 | 2.69 | 3.31 | 5.32 | 6.49 | 5.59 | MR02_BTC 0.32 |
| 15m (live) | 1.94 | 2.30 | 2.37 | 4.94 | 6.40 | 4.44 | MR02_BTC 0.60 |
| 30m | 1.35 | 2.32 | 1.56 | 3.25 | 5.23 | 2.81 | MR02_BTC 1.40 |
**La frontiera è monotona**: più il tf scende, più Sharpe sale (MR01/MR07)… e più
il margine fee si assottiglia. A fee 2x MR02_BTC muore a 5m e resta fragile a 10m.
MR02 (donchian) fa 3-6x i trade degli altri: è la strategia più esposta al churn.
## B. Finestra comune recente (2026-02-12 → 06-12, il regime CORRENTE)
- **MR02 sotto i 15m è un disastro**: 1m −64%, 2m −44%, 5m −22% (fee-death).
- **MR01 a 1m brilla** (ETH +60.6%, Sh 5.7; BTC +33.5%) ma **muore a fee 2x**
(unico sopravvissuto MR01_ETH +16.5%): margine troppo sottile per fidarsi.
- Flat share a 1m: ETH 25.6%, BTC 13.3% → rischio stale-print alto (la lezione
del giorno: pairs-alt/XEX/PAXG).
- Il regime recente è CALMO: anche il 5m vi è fiacco (+4.8/−22.9/+3.7 BTC).
I tf veloci pagano nella volatilità, non nella calma — il loro vantaggio
full-history viene dai regimi mossi (2021-22, 2024).
## C. Correlazione col 15m live (daily, storia completa)
5m↔15m media **0.46**, 10m↔15m media **0.53** (range 0.28-0.81). Diversificazione
parziale: un eventuale ADD del 10m avrebbe senso ma è meno pulito del salto
1h→15m (che era a 0.26).
## Verdetto
- **1m / 2m: CHIUSI.** Fee-margin nullo a stress, microstruttura flat pesante,
validazione full-history impraticabile. Non deployare mai MR02 sotto i 15m.
- **5m: no-swap.** L'edge c'è ma MR02_BTC muore a fee 2x — viola il criterio di
robustezza fee che tutte le strategie deployate rispettano.
- **10m: in WATCHLIST.** Quasi l'edge del 5m con più margine (f2x 0.32 resta
sotto la soglia di comfort per MR02_BTC; MR01/MR07 reggono bene). Possibile
ADD selettivo (solo MR01/MR07?) da gateare su PORT06 più avanti — NON ora:
il 15m è live da poche ore, un cambio alla volta e si lascia parlare il
ledger reale.
- **15m: confermato** come ginocchio della frontiera margine-fee/rendimento.
Collaterale tecnico: bug di resample scoperto e fixato nello sweep — pandas 2.x
conserva `datetime64[ms]` da `to_datetime(unit="ms")`, quindi `.view(int64)//10**6`
divide due volte e manda i timestamp nel 1970 (equity piatta silenziosa). Usare
`(index - EPOCH) // pd.Timedelta(milliseconds=1)`.
@@ -51,3 +51,28 @@ il suo OOS DD peggiora 1.48→2.09). In subordine BLEND (miglior FULL DD 2.31%).
position_size ridotto come il blend pairs (il gate ADD qui è già a peso pieno
e migliora comunque, ma il caveat slippage 15m suggerisce prudenza).
5. MR02_BTC 15m è il più fee-sensitive (fee2x OOS 0.60): monitorare le fee reali.
## Addendum — DEPLOY: SWAP SECCO (stessa giornata, scelta utente)
L'utente ha scelto **SWAP** (la variante a CAGR più alto), consapevole dei due
costi discussi: OOS DD 1.48→2.09% e perdita della maturità operativa 1h (la
meccanica live — EXIT-16 confirm, TP_PHANTOM, TP resting — gira 4x più veloce
su un feed testnet con wick anomali; il gate misura l'edge, non la robustezza
operativa). Proposta alternativa staged (ADD temporaneo 1-2 settimane, poi
spegnere il 1h) declinata: "swap secco".
Implementazione (deliberatamente minima, sid INVARIATI → pesi/alloc/epoche
intatti):
- `_defs.py`: FADE specs → `tf="15m"` (DIP01 resta 1h: non era nel gate).
- `combine_portfolio.py`: `FADE_TF="15m"` nel builder canonico → le due facce
(backtest/live) restano sulla STESSA definizione; il lock di parità
(`test_backtest_parity`) confronta le facce fra loro e resta verde.
- Runner: NESSUNA modifica (il fetch sub-orario BTC/ETH 15m esisteva già per il
blend pairs; `_spec_assets_tf`/`_series_for` sono generici).
- Worker: nuove dir `*__15m` (stato 1h preservato in `*__1h`, worker flat al
momento dello switch). Esecuzione reale invariata (match per nome MR01/02/07).
- max_bars=24 barre ora = 6h; EXIT-16 confirm sulla barra 15m completata.
Monitor post-deploy: stop-rate e divergenza sim/reale dei fade 15m
nell'hourly report; fee reali su MR02_BTC; STALE_FEED (le barre flat 15m
sono più frequenti che a 1h).
@@ -0,0 +1,51 @@
# 2026-06-12 — Sweep migliorie/strategie nuove (sera, post-swap 15m)
Richiesta: cercare altre migliorie da implementare o strategie nuove. Tre
esperimenti + una miglioria di codice.
## 1. INIT_LINEAGE — eredità capitale al cambio timeframe (IMPLEMENTATO)
`StrategyWorker._inherit_lineage_capital`: al primo avvio (niente status.json)
il worker eredita `capital`/`real_capital` dal worker più recente di stessa
strategia+asset su altro tf (glob `{strategy}__{asset}__*`). MAI la posizione.
Nato dallo swap 1h→15m di oggi: i worker nuovi partivano dall'allocazione del
pool scartando il PnL del gemello (−16.8 di equity fantasma, riallineata a mano
col seed). Il prossimo swap non avrà bisogno di seed manuale.
Test: `tests/portfolio/test_capital_lineage.py` (eredita / no-sibling / resume).
## 2. Gate 10m ADD selettivo (MR01/MR07) — BOCCIATO, watchlist chiusa
Baseline aggiornata al PORT06 post-swap (fade 15m): ADD di 4 sleeve 10m
(MR01/MR07 × BTC/ETH, MR02 escluso perché fee-fragile) dà FULL Sh 8.13→8.33 e
DD 2.47→2.28, ma **OOS Sharpe 10.86→10.76** → fallisce il criterio standard.
Il 15m cattura già quasi tutto l'alpha veloce (corr 10m↔15m 0.53). Chiuso.
## 3. XSEC breadth (universo 8 → 14/15) — direzione GIUSTA, venue SBAGLIATO
La breadth è la leva classica delle strategie cross-sectional. Due banchi:
- **Hyperliquid 15 coin** (dati REALI, ma profondità v2 limitata a ~207 giorni,
regime calmo recente): CORE-8 **−6.2%** (Sh −1.38, coerente col
dispersion-gate live che tiene XS01 fuori in questo regime) vs FULL-15
**+9.4%** (Sh 1.58, WR 41→51%). La breadth trasforma un book perdente in
vincente — **sui prezzi veri**.
- **Deribit 14 coin** (storia piena 2022-10→2026-06, +AVAX/DOT/TRX/LINK/BCH/UNI,
parity del sim verificata ESATTA vs `xsec_sim`): FULL Sh 1.48→**1.22**, OOS
4.66→**3.41**, fee 2x da −0.33 a **−1.45**. PEGGIO dell'8: le 6 gambe nuove
hanno chiusure flat al **91-99%** e il loro "momentum" è rumore stale che
corrompe il ranking cross-section (3ª conferma della lezione del giorno:
pairs-alt, XEX/DOGE, ora XSEC).
**Conclusione:** l'espansione dell'universo XS01 è promettente ma bloccata dalla
qualità dati del venue. Sblocco strategico: **routing dati Hyperliquid** nel
runner (il client v2 già supporta `exchange="hyperliquid"`) + accumulo storia
HL in avanti. Rivalutare quando HL avrà ≥12-18 mesi di storia utile.
## Direzioni aperte residue (non attaccate oggi)
- **Put settimanale standing** (catastrofe-cap): unica struttura opzioni
eseguibile, da gateare coi premi reali cerbero-bite (~1%/mese il 10% OTM).
Harness `option_overlay_lab.py` pronto.
- **Hyperliquid come venue di esecuzione** (oltre che dati): aprirebbe fades su
alt liquidi con fill realistici; lavoro infrastrutturale grosso.
- 10m fade: chiuso oggi. 1m/2m/5m: chiusi oggi. Pairs nuove/PAXG/XEX: chiusi oggi.
+40
View File
@@ -0,0 +1,40 @@
# 2026-06-13 — Dashboard web PORT06 (stato live + PnL + grafici + trade)
Richiesta utente: frontend per visualizzare lo stato con PnL totale e per-strategia,
grafici, e liste trade (attivi in tempo reale + chiusi).
## Cosa
`src/live/dashboard.py` — server **stdlib `http.server`** (zero nuove dipendenze),
legge i file `data/` e serve:
- `GET /api/state` → JSON con tutto lo stato calcolato
- `GET /` → single-page HTML (vanilla JS, polling ogni 5s)
Contenuto della pagina:
- **KPI**: equity, PnL totale (€ e %), max DD, peak
- **Grafico equity** (Chart.js da CDN, fallback testuale se offline) dalla
`equity.jsonl` del ledger (downsample a 400 punti)
- **PnL per strategia** (barre verdi/rosse): realizzato netto fee = Σ `pnl` reali
dai CLOSE (REAL-TRUTH), n trade, win-rate, capitale; tag `paper` per i
multi-asset non eseguiti, `•aperta` se in posizione
- **Trade attivi in tempo reale**: lato, entry, **mark corrente** (Cerbero
best-effort, cache 20s), **PnL non realizzato** (€ e %, da `real_entry_notional`),
barre/max_bars, distanza al TP, età dello status (⚠ se >15min = stantio)
- **Trade chiusi** (ultimi 50): ora, strategia, motivo, PnL reale, sim, esito
## Deploy
Servizio docker-compose `dashboard` (stessa immagine del runner, monta gli stessi
`data/`, porta **8787**), `restart: unless-stopped` + healthcheck sull'API.
Accesso: `http://<host>:8787`. **Nessuna auth** → solo rete interna/VPN, non
esporre pubblicamente. Avvio: `docker compose up -d --build dashboard` (il runner
non viene toccato).
uv run python -m src.live.dashboard --port 8787 # anche standalone su host
## Note
- Il PnL per-strategia usa il PnL REALE (real_truth), coerente col report orario.
- I 6 fade 1h ritirati dallo swap restano in lista (hanno storico CLOSE): flat,
mostrano il loro PnL realizzato storico accanto ai gemelli 15m attivi.
- Unrealized € sui pairs non mostrato (posizione a 2 gambe, z-based) → "pairs (z)".
@@ -0,0 +1,49 @@
# 2026-06-13 — Report ricorrente LEDGER REALE vs BACKTEST (il gate per scalare)
## Perché
Domanda dell'utente: "come cresco il capitale a 12k". Risposta: il prerequisito
prima di mettere soldi veri è che il **ledger reale combaci col backtest** —
soprattutto lo slippage del 15m appena deployato. Questo report rende quel gate
un dato osservabile, non un'opinione.
Insight chiave: per gli sleeve eseguiti (6 fade 15m, DIP01, 6 pairs, SH01) il
**sim del worker == backtest canonico PER COSTRUZIONE** (validato). Quindi
"reale vs backtest" = "reale vs sim" = la **fuga di esecuzione**: slippage +
fee reali vs assunte + effetti netting/phantom/sim_fallback.
## Cosa misura
`scripts/analysis/ledger_vs_backtest.py` (read-only: solo trades.jsonl +
status.json, nessuna rete → affidabile in cron):
- PnL realizzato sim vs reale (Σ e per-trade) → **LEAKAGE** € e per-trade (bottom line)
- slippage ingressi (REAL_OPEN) e uscite-a-mercato (REAL_CLOSE; escluse le uscite
da TP resting, fill maker al livello = no slippage)
- fee reali vs assunte (0.10% RT)
- trade `sim_fallback` (reale mai eseguito/fillato) = quota NON coperta dal reale
- ledger per-sleeve: real_capital vs capital (sim)
- **verdetto** 🟢/🟡/🔴: <10 trade = campione piccolo; leakage basso+slippage ≤15bps
= verde (si può pensare a scalare); slippage >40bps = rosso (edge erode, NON scalare)
## Clean-start (importante)
Una finestra mobile pura includerebbe l'**incidente testnet pre-fix**: a 7g il
report dà sim +82 vs reale +5 (🔴) — ma è gonfiato dai +4% FANTASMA che il sim
bookava e il reale no, prima di TP_PHANTOM (v1.1.23), netting (v1.1.25) e
ribilancio-conservativo (v1.1.31). Lo scheduler usa **`--since 2026-06-13`** →
accumula SOLO dati post-fix, e diventa statisticamente significativo coi giorni.
Finestra pulita oggi: 1 trade, leakage +0.07, slippage ingresso 12-29 bps.
## Scheduling
Cron host (come reconcile/hourly_report), **giornaliero 08:30 UTC**:
`ledger_vs_backtest.py --since 2026-06-13 --telegram` → Telegram + log in
`~/port06_ledger_vs_backtest.log`. Invio verificato.
## Come usarlo
Quando il campione supera ~10-20 trade reali e il verdetto è 🟢 stabile per
qualche giorno (leakage per-trade piccolo, slippage medio ≤15 bps), allora il
15m regge l'esecuzione e si può passare da testnet a piccolo reale → poi scalare.
Se resta 🔴/🟡, l'edge si erode sui fill e NON va scalato: prima si capisce dove
perde (slippage ingressi? uscite a mercato? sim_fallback frequenti?).
@@ -0,0 +1,41 @@
# 2026-06-13 — Orfano da swap: incidente + guard nel reconciler
## Incidente
Lo `stato trades` del mattino ha scoperto una **posizione reale orfana**: il
worker fade **MR02_BTC 1h** aveva aperto uno short reale (0.0028 BTC @ 64135.5)
ieri alle 15:01; lo **swap a 15m (v1.1.30, ~20:48) lo ha rimosso dal config
mentre era ancora in posizione** → da allora nessun runner lo gestiva. Stato:
- conto Deribit: short 0.0028 BTC (il long di apertura del gemello 15m aveva
aperto e chiuso nettando via il resto)
- il **TP limit (63387.75) era sparito** dal book (cancellato durante il netting
della chiusura 15m) → short NUDO, protetto solo dal disaster-SL a +30%
- il **reconciler NON allarmava**: lo `status.json` del worker morto dichiarava
ancora `real_in_position: true` → conto == libri. Punto cieco: il reconciler
leggeva i libri dagli status ma non sapeva quali worker fossero VIVI.
Chiusura manuale (testnet): buy 0.0028 reduce-only @63766.5 (~+$0.85 netto sullo
short), cancel disaster-SL, worker marcato flat, PnL bookato (real_capital
181.18→182.03). Conto verificato flat su BTC; SH01_ETH short intatto.
## Guard implementato
`reconcile_account.compute_stale_real_positions(max_age_min=15)`: segnala i
worker che dichiarano `real_in_position` ma il cui `status.json` è fermo da
oltre 15 min. Un worker vivo riscrive lo status a ogni poll (~60s) → la
**staleness** è il discriminante robusto e venue-agnostico (cattura
ritirati-da-swap, crashati, worker rimossi dal config). Alert Telegram
`STALE_REAL_POSITION` (con `--telegram`), incluso nell'exit code e nel verdetto.
Gira già al prossimo cron host (:40) — nessun rebuild (lo script gira dal
working tree). Test: `tests/portfolio/test_reconcile_resting.py` (stantio
flaggato / fresco no / flat-vecchio no).
## Causa radice e direzione
La feature `INIT_LINEAGE` di ieri trasferisce il *capitale* al gemello del nuovo
timeframe, ma non la *posizione*. Il guard di oggi è la **rete di sicurezza**
(rileva e allarma entro un'ora). La **prevenzione** vera — flattare/consegnare la
posizione reale del worker ritirato al boot del runner — resta da implementare
(va fatta lato runner, con cautela: piazza ordini reali all'avvio). Per ora:
swap a conto fade-flat quando possibile, e il reconciler copre il resto.
@@ -0,0 +1,56 @@
# 2026-06-13 — Equity gonfiata dal ribilancio: +4.77 fantasma (causa + fix)
## Sintomo
Report "dall'ultimo reset": equity 2020.53 → 2025.80 (+5.27), ma un solo trade
chiuso (MR02_BTC 15m, reale +0.50). Il +4.77 residuo è comparso di colpo a
00:01:52 (primo poll dopo mezzanotte UTC = ribilancio giornaliero), senza alcuna
chiusura dietro.
## Causa — doppio conteggio del capitale degli in-position al ribilancio
`rebalance_allocations` faceva:
1. `total_capital = Σ capital di tutti i worker`
2. `alloc[sid] = peso × total_capital` per OGNI sid
3. ai worker in posizione NON applicava l'alloc (la posizione tiene il suo notional)
4. ai flat: `capital = alloc[sid]`
`update_equity` (ogni poll) = Σ capital. Dopo il ribilancio la somma diventa:
Σcapital = Σ(peso_i × total) [flat] + Σ(capital_j) [in-pos]
= total − Σalloc_j + Σcapital_j
= total + Σ(capital_j − alloc_j) ← inflazione
Cioè i flat si dividevano l'INTERO total (che includeva anche il capitale degli
in-position), e gli in-position lo tenevano in più → doppio conteggio.
Al ribilancio delle 00:01, **MR02_BTC 15m era in posizione** col capitale seedato
**181.19** (eredità del gemello 1h, INIT_LINEAGE di ieri) mentre la sua allocazione
era ~176.42 → **+4.77** di equity dal nulla. Lo scatenante è stato il seed (capitale
ben sopra l'allocazione media) combinato con la posizione aperta al ribilancio; ma
il bug era latente da sempre (ogni worker in-pos che devia dall'alloc gonfiava/sgonfiava
l'equity al ribilancio successivo).
## Fix — conservazione (ledger.allocate `reserved`)
`allocate(weights, reserved={sid: capitale})`: i worker in posizione TRATTENGONO il
loro capitale (deployato, non spostabile); i flat si dividono `total − Σreserved`
per peso **rinormalizzato sui soli flat**. Così `Σalloc == total_capital` sempre →
**l'equity è conservata dal ribilancio** (un ribilancio sposta capitale fra sleeve,
non crea valore). `runner.rebalance_allocations` calcola `reserved` dai worker
`in_position` e lo passa. Senza `reserved` (default) = comportamento storico
(corretto solo a worker tutti flat, es. allocazione iniziale).
Test: `tests/portfolio/test_ledger.py::test_alloc_conserves_total_with_reserved`.
## Correzione dello stato (rimozione del +4.77 già accumulato)
Equity riportata a **2021.03** = baseline post-seed verificata (2020.53) + unico
trade reale (MR02_BTC 15m +0.50). Capitali dei worker del pool scalati ×
(2021.03/2025.79) e peak del ledger resettato a 2021.03 (il 2025.80 non è mai
stato un massimo legittimo → niente DD fantasma). L'orfano MR02_BTC 1h chiuso a
parte (+0.85) resta sul worker ritirato, fuori dal pool.
## Esito
Equity = soldi veri: dal reset il trading ha prodotto **+0.50** (1 trade), non +5.27.
Deploy con codice fixato (rebuild) così il prossimo ribilancio conserva.
@@ -0,0 +1,149 @@
# 2026-06-14 — Timing sweep: PAIRS & HONEST su 5/10/15/30m (vs live)
## Domanda (goal utente)
Dopo lo swap fade 1h→15m (v1.1.30), i **pairs** e le **honest** beneficiano dello stesso
trattamento — girare su timeframe più veloci (5/10/15/30 min)?
Script: `scripts/analysis/timing_sweep_pairs_honest.py` (riusa i motori canonici
`pairs_sim_flat`, replica DIP intrabar verificata == `dip_market_gated(market_n=0)`, gate
PORT06 == `pairs30m_gate`/`dip01`). Niente re-tuning dei parametri al cambio TF (anti-overfit,
come lo swap fade). Tutto netto, leva 3x, OOS held-out (da 2024-10).
## Vincolo dati (hard — definisce lo scope)
Solo **BTC/ETH** hanno 5m/15m/30m in locale (10m = resample causale da 5m). **TUTTI gli alt**
(ADA/BNB/DOGE/LTC/SOL/XRP) sono **SOLO 1h**. Quindi:
- **PAIRS:** solo **ETH/BTC** è sweepabile sub-orario. Gli altri 4 pair (gambe alt: LTC/ETH,
ADA/ETH, BTC/LTC, ETH/SOL) restano 1h per sempre senza dati alt sub-orari.
- **HONEST:** solo **DIP01** (BTC, mean-reversion) ha senso + dati. **TR01** (trend EMA20/100 su
4h, basket alt) e **ROT02** (rotazione dual-momentum 1d, momentum 60g, universo alt) sono lente
(orizzonte multi-giorno/mese) E multi-asset-su-alt → sub-orario **infattibile** (dati) e
**insensato** (momentum a 60 giorni su barre da 5 min). Nessuno sweep.
## Flat-share (print stale O=H=L=C, = rischio fill) — sale al scendere del TF
| asset | 5m | 10m | 15m | 30m | 1h |
|-------|----|-----|-----|-----|-----|
| BTC | 10.0% | 4.8% | 3.5% | 1.5% | 0.9% |
| ETH | **29.0%** | 17.3% | 16.4% | 9.0% | 6.7% |
ETH 5m al 29% è un allarme operativo serio. Nota: **30m ETH (9%) < 15m (16.4%)** → il 30m ha
*meno* rischio stale-print del 15m già live.
## PAIRS ETH/BTC — il vero free-lunch
Config UNIVERSALE 1h (n=50, z_in=2.0, z_exit=0.75, max_bars=72), flat_skip live-realizable:
| tf | Sharpe FULL | OOS Sh | OOS Sh fee2x | CAGR | win% |
|----|-------------|--------|--------------|------|------|
| 5m | 9.54 | 17.19 | 11.98 | 2071% | 56.0 |
| 10m | 9.26 | 16.54 | **13.03** | 1214% | 64.1 |
| 15m (live) | 8.10 | 14.40 | 11.74 | 673% | 66.7 |
| 30m | 6.20 | 11.17 | 9.59 | 312% | 71.7 |
| 1h (live) | 3.74 | 7.11 | 6.19 | 119% | 72.4 |
(I CAGR a quattro cifre sono compounding leva su singolo sleeve, irrealistici — il portafoglio
normalizza/cappa; il segnale robusto è lo **Sharpe** e il **gate PORT06**.)
- Sharpe **monotono** al scendere del TF, e **regge le fee 2x** (a differenza delle fade, dove
MR02 muore a 5m). Pairs market-neutral: lo spread rientra più spesso ad alta frequenza, e
ETH/BTC è la coppia più liquida.
- Corr daily fra TF: 5m↔1h 0.28, 10m↔1h 0.32, 30m↔1h 0.51; 10m↔15m 0.67 → i TF veloci sono
**fasi diverse dello stesso edge**, diversificanti, non duplicati.
**Gate PORT06 (add half-size al BLEND 1h+15m, OOS da 2024-10):**
| config | FULL Sh | FULL DD% | OOS Sh | OOS DD% | verdetto |
|--------|---------|----------|--------|---------|----------|
| ATTUALE (1h+15m) | 8.13 | 2.47 | 10.86 | 2.09 | — |
| +30m | 8.24 | 2.28 | 10.87 | 1.97 | **MIGLIORA** (già `pairs30m_gate`, mai deployato) |
| +10m | 8.44 | 2.28 | 11.04 | **1.92** | **MIGLIORA** (domina tutto) |
| +5m | 8.52 | 2.30 | 11.00 | 1.95 | **MIGLIORA** (FULL Sh max) |
Tutte e tre dominano su FULL Sh, FULL DD, OOS Sh, OOS DD. **10m** è il candidato più pulito
(miglior OOS DD, flat-share moderato 17%); **30m** è il più sicuro (flat-share 9% < 15m live).
## DIP01 (BTC) — più veloce, ma lo swap NON domina
Engine canonico (n=50, z_in=2.5, sl_atr=2.5, max_bars=24), parità 1h verificata:
| tf | OOS Sh BTC | OOS Sh fee2x BTC | corr↔1h | OOS Sh ETH |
|----|------------|------------------|---------|------------|
| 5m | 4.91 | 2.41 | 0.13 | 8.43 |
| 10m | 3.47 | 1.99 | 0.17 | 6.51 |
| 15m | 2.40 | 1.40 | 0.22 | 4.49 |
| 30m | 1.34 | **0.77** | 0.41 | 3.54 |
| 1h (live) | 1.69 | 1.36 | — | 2.68 |
Standalone Sharpe sale al scendere del TF e i TF veloci sono **fortemente diversificanti**
(corr 0.13–0.22 con l'1h). MA: **BTC fee-fragile** (30m f2x 0.77), e il **gate-swap non domina**:
| config | FULL Sh | FULL DD% | OOS Sh | OOS DD% |
|--------|---------|----------|--------|---------|
| DIP01 1h (live) | 8.13 | 2.47 | 10.86 | 2.09 |
| DIP01 30m | 8.16 | 2.27 | 10.78 | 2.03 |
| DIP01 15m | 8.16 | 2.30 | 10.82 | 2.14 |
| DIP01 10m | 8.31 | 2.49 | 10.85 | 2.15 |
| DIP01 5m | 8.46 | 2.27 | 11.02 | 2.16 |
Tutti migliorano i FULL ma **alzano l'OOS DD** (e 30m abbassa l'OOS Sharpe) → nessuno domina
sui 4 criteri. DIP01 5m dà il miglior OOS Sharpe (11.02) ma OOS DD 2.16 vs 2.09. La bassa corr
suggerirebbe un **ADD** (DIP01 5m come secondo sleeve diversificante) più che uno swap, ma
aumenta la concentrazione BTC-rev e non è il free-lunch netto che sono i pairs.
## Caveat (perché backtest ≠ via libera a scalare)
1. **Slippage su feed flat-alto** = il vero banco di prova, già flaggato per il 15m blend
("il vero banco di prova è il ledger reale shadow"). A 5m/10m è peggio (ETH 5m 29% flat).
Il backtest usa flat_skip (timing live-realizable) ma NON modella lo slippage attorno ai
print stali. → gateare via shadow ledger PRIMA di sizing, specie il 5m.
2. **OOS = un solo regime** (2024-10→, calmo). Lo Sharpe monotono-col-TF può essere in parte
un artefatto di regime calmo (la MR veloce prospera nel range a bassa vol; lo sweep fade
trovò "i tf veloci pagano nella volatilità, non nella calma"). I pairs sono market-neutral
→ meno esposti dei fade ai crash direzionali, ma il caveat resta.
## Verdetto del backtest (gate full + OOS 2024→)
- **PAIRS ETH/BTC: il gate diceva SÌ.** Estendere il BLEND con TF più veloci migliorava PORT06
su tutte le metriche (10m domina, 30m il più sicuro, 5m FULL Sh max), fee-2x robusto.
- **DIP01: marginale.** Più veloce è diversificante ma lo swap non domina e BTC è fee-fragile.
- **TR01/ROT02: NO.** Dati alt 1h-only + orizzonte lento → fuori scope per costruzione.
## Tentativo di deploy → due muri, NESSUN deploy (2026-06-14)
L'utente ha scelto di deployare un blend pairs ETH/BTC più veloce. Il wiring è stato fatto e
validato (sleeve def, backtest face, worker replay == backtest esatto, regression-lock
aggiornato) PRIMA di scoprire due blocchi che hanno ribaltato la decisione:
1. **MURO FEED (30m e 10m).** Il feed live **Cerbero v2 (`/mcp/tools/get_historical`) serve
solo 5m/15m/1h** — il 30m e il 10m danno 400 in OGNI formato (30m/30/30min/1800), e
l'endpoint legacy è 404 (rimosso). La voce `"30m"` in `runner._SUBHOURLY` era **speculativa,
mai testata live**. → un blend 30m/10m NON è drop-in: richiede di derivarlo resamplando il
feed 15m/5m nel runner (modifica al data-path live condiviso). **Lezione: il _SUBHOURLY del
runner ≠ ciò che il feed serve davvero — smoke-testare il fetch prima di promettere un TF.**
2. **MURO REGIME (5m).** Il 5m è l'unico TF veloce nativo (drop-in), ma il gate full-history
(Sharpe 9.54) è un **relitto dei regimi volatili vecchi**. Nel regime ATTUALE è il PEGGIORE
(ETH/BTC pairs half-size, ret%/Sharpe/DD):
| tf | ultimi 30g | ultimi 90g | ultimi 180g |
|----|-----------|-----------|------------|
| 5m | −10.5% / −11.5 / 11.6% | −2.0% / −0.2 / 14.1% | +78% / 2.93 / **19.5%** |
| 15m | −4.4% / −6.2 / 5.8% | −3.1% / −0.9 / 5.8% | +56% / 3.80 / 7.9% |
| 1h | −1.0% / −1.1 / 3.0% | +3.0% / +1.3 / 3.0% | +25% / **3.95** / 3.0% |
Il 5m perde su ogni finestra recente e ha **DD 3-6× il 1h**; persino sui 180g il suo Sharpe
(2.93) è SOTTO 15m/1h. Sommato al **flat-share ETH 5m 29%** (slippage reale, non modellato
dal backtest) e al fatto che girerebbe **reale**, il guadagno modesto di backtest (FULL
Sharpe +0.39) non vale il rischio. **5m: non conviene.**
**ESITO: nessun deploy. Config live invariata (19 sleeve, pairs 1h+15m).** I file tracciati
ripristinati a HEAD; restano solo questo diario + `timing_sweep_pairs_honest.py` come record.
**Lezione di metodo:** il gate PORT06 full+OOS è necessario ma non sufficiente — va incrociato
con (a) la fattibilità del FEED live e (b) il regime RECENTE. Un edge full-history può essere
un relitto di volatilità passata; "più veloce = più Sharpe storico" si rovescia in "più veloce
= più DD nel regime calmo attuale". Se in futuro si vorrà un blend più veloce: il **30m** resta
il migliore on-paper (flat 9%), ma serve prima derivarlo dal 15m nel runner + ri-verificarlo
nel regime del momento.
@@ -0,0 +1,85 @@
# 2026-06-15 — Gate del feed CONGELATO (freeze gate)
## Problema (da "stato ordini")
Audit degli ordini live: 5 sleeve in posizione reale, **4-5 contaminati dal feed ETH
congelato**. `ETH-PERPETUAL` (inverse, il feed di DECISIONE del runner) è fermo a
**1661.95 da 36h+** (100% barre flat, 57/57 nel windows 2g, **1 solo valore distinto**),
mentre il book reale dove si ESEGUE (`ETH_USDC-PERPETUAL`, lineare) si muove ~1717-1722.
Effetto misurato sui soldi reali (log container):
- **SH01_ETH** ha aperto short a sim 1661.95 / real 1717.10 (slippage 332 bps), chiuso a
time_limit con `sim_exit 1661.95` ma `real_fill 1719.21` → **−2.83 USD reali vs −0.09 sim**
→ e ha **riaperto subito** lo stesso short sulla trappola.
- I 4 pairs con gamba ETH (ETH/BTC 1h+15m, ETH/SOL, LTC/ETH, ADA/ETH) sono entrati con
z-score **estremi** (−3.10, −2.96, +5.58, −2.56): artefatto MECCANICO del log-ratio con
ETH pinnato a 1661.95 mentre gli alt si muovono → falsa divergenza → carico di spread long-ETH.
È un GUASTO testnet, non di strategia: in mainnet l'arbitraggio tiene inverse ≈ lineare ≈ realtà.
## Decisione utente
> "congela gli sleeve ETH-leg finché il feed non si sblocca"
## Soluzione: gate del feed congelato nel runner (auto-guarente)
`src/portfolio/runner.py`: quando il feed di decisione 1h di un asset è **congelato**, gli
sleeve CONCENTRATI (single/ml/pairs) che ne dipendono **saltano il tick** (entry E exit)
finché il feed non si sblocca. Come un outage (i worker non valutano gli exit, protezione =
disaster-SL on-book). Si rilascia DA SOLO alla prima barra completa non-flat.
### Distinguere il GUASTO dall'ILLIQUIDITÀ (il punto critico)
Un detector flat-bar ingenuo sarebbe SBAGLIATO: sul feed reale (2026-06-15) gli alt sono
flat ma VIVI. Firma misurata (run finale di close invariate / valori distinti in 48h):
| Asset | run | distinti/48h | natura |
|-------|-----|--------------|--------|
| ETH | 64 | **1** | MORTO (guasto) |
| BNB | 64 | 2 | MORTO (testnet, solo paper) |
| DOGE | 42 | 4 | MORTO (testnet, solo paper) |
| XRP | 12 | 3 | illiquido |
| ADA | 11 | 5 | illiquido ma VIVO |
| LTC | 10 | 5 | illiquido ma VIVO |
| SOL | 1 | 31 | VIVO |
→ il detector conta la **run di close INVARIATE** (prezzo che non cambia MAI), non le barre
flat. Soglia **24** (`feed_freeze_gate_bars`, configurabile, 0=off): un giorno intero di
prezzo immobile separa nettamente le due popolazioni. ETH/BNB/DOGE (run 40-64) gateati,
ADA/LTC/XRP/SOL (run ≤12) no. **PR_BTCLTC resta attivo** (BTC vivo + LTC solo illiquido NON
deve sospendere il pair: si perderebbero segnali reali sulla gamba BTC).
### NON è l'entry-guard post-flat (BOCCIATA)
Si gatea **DURANTE** il freeze (ultima barra completa ferma). La barra di RIPRESA è non-flat
→ la run si azzera → il tick riprende SU di essa. NON si salta la candela-gap di ripresa
(quella è l'overshoot che la fade fada con profitto — l'entry-guard post-flat è bocciata,
CLAUDE.md / 2026-06-05). Rilascio solo su barra **completata** non-flat (la forming non basta,
coerente con EXIT-16).
### Scope
Solo sleeve `single`/`ml`/`pairs`. I multi-asset (basket/rotation/tsmom/xsec, tutti PAPER)
NON sono gateati: diversificati su 8 asset, un feed fermo non li compromette (e ROT02 ha ETH
nell'universo ma resta attivo). Osservabilità: log `FEED_FROZEN_GATE` + alert Telegram
GATED/RIPRESO, dedup per episodio.
## Esito (smoke feed reale, soglia 24)
- CONGELATI: ETH, BNB, DOGE.
- **GATEATI: le 9 gambe ETH esatte** — MR01/MR02/MR07_ETH, SH_ETH, PR_ETHBTC, PR_ETHBTC_15M,
PR_LTCETH, PR_ADAETH, PR_ETHSOL. BTC-only, PR_BTCLTC e i multi-asset restano attivi.
Le 5 posizioni ETH già aperte NON vengono flattate (freeze = pausa, non liquidazione): un
close forzato passerebbe per lo stesso feed congelato (= il close −2.83 di SH01). Restano
gestite alla ripresa del feed; protezione di coda = disaster-SL on-book a −30%.
Test: `tests/portfolio/test_freeze_gate.py` (detector guasto-vs-illiquido, rilascio su barra
completata, scope sui veri sleeve PORT06). Suite portfolio: 140/140 verdi.
## Lezione
Tre livelli di osservabilità del feed ora distinti: STALE_FEED (≥2 barre flat, alert umano),
FEED_BOOK_GAP (feed≠book d'esecuzione, alert), **FEED_FROZEN_GATE (≥24 barre invariate, AGISCE)**.
La firma che separa guasto da illiquidità è la **run di prezzo invariato**, non la barra flat:
gli alt illiquidi stampano barre flat ma il prezzo si muove ogni ~10 barre.
@@ -0,0 +1,66 @@
# 2026-06-16 — Guard TP-invertito (churn MR02_BTC 15m)
## Sintomo
Burst di **8 trade in 15 minuti** su `MR02_donchian_fade__BTC__15m` (09:00–09:15 UTC),
tutti `long`, tutti chiusi `take_profit` a `bars_held=0-1` **in perdita**, accuracy
crollata 60%→27%. TP **fisso** a 66189.25, **sotto** ogni entry (66700–66834):
```
09:00 OPEN long 66780.5 tp=66189.25 sl=64218.21 ← tp E sl ENTRAMBI sotto l'entry
09:02 CLOSE take_profit exit=66189.25 held=0 sim=-2.63 real=-0.12
... ×8 ... +7× REAL_TP_FAIL: invalid_reduce_only_order
```
I trade MR02 sani prima del cluster hanno il TP dal lato giusto (long → tp>entry:
65033>63414, 64148>63775, 66079>65717). Il cluster delle 09:00 è l'unico **invertito**.
## Causa radice — segnale da wick transitorio (NON feed congelato, NON spike d'ingresso)
BTC alle 09:00 era **davvero** ~66780 (MR01 short@66919, MR07 short@66780.5 nello stesso
istante, slippage reale 0.7–2.5 bps → feed sano). Il difetto è a monte:
1. Una barra con **wick verso il basso** (~64218 = il livello SL) fa scattare il donchian
"rottura canale basso" → segnale **LONG**, con `tp`=centro canale (66189) e `sl`=64218
calcolati **dal contesto wickato**.
2. Il wick rientra; il worker entra `long` al prezzo **recuperato** 66780 — cioè **sopra
il proprio TP=66189**.
3. L'exit intrabar (`bar_high >= tp`) è banalmente vera all'istante → chiude "take_profit"
a 66189 = **perdita garantita a held=0**. Si ripete 8× perché il livello donchian
wickato resta nel lookback.
Differenza chiave da TP_PHANTOM: lì il wick è sull'**exit** (tocco fantasma del TP);
qui il wick produce un **tp dal lato sbagliato dell'entry** → la posizione non doveva
proprio aprirsi.
## Perché i guard esistenti non l'hanno preso
- **TP_PHANTOM** richiede un limit reduce-only resting come oracolo. Qui il limit è
**respinto** (`invalid_reduce_only_order`: una sell reduce-only a 66189 sotto il mercato
è invalida) → niente `real_tp_order_id` → fail-open → l'exit passa. E il prezzo corrente
(66780) ha **realmente** superato il livello → non è un tocco fantasma.
- **Freeze-gate (v1.1.32)**: BTC non è congelato (prezzi che si muovono) → non scatta.
## Danno reale: contenuto (il real-truth ledger ha funzionato)
- Σ **reale** del cluster ≈ **−€2.29** (solo slippage+fee: il fill reale è al prezzo vero
~66700-66730, non al TP fantasma).
- Σ **sim** sarebbe stato ≈ **−€17.9** → il real-truth ledger ha evitato che ~**€15.6** di
perdita fantasma colpisse l'equity.
- Costi collaterali: 8 round-trip di fee, 7 TP reduce-only respinti, 8 disaster-SL da
piazzare/cancellare, sim accuracy/report inquinati.
- Auto-esaurito alle 09:15 (sleeve poi flat).
## Fix — guard "TP invertito" (v1.1.33, zero parametri)
`StrategyWorker._open_position`: **prima** di aprire, se il TP è già sfondato all'ingresso
(`long & tp<=entry` oppure `short & tp>=entry`) il segnale è malformato (artefatto wick)
→ **NON si apre** (niente ordine reale, niente disaster-SL). Verità d'esecuzione, non un
filtro di strategia (stessa filosofia di TP_PHANTOM). Log `INVERTED_TP_SKIP` (dedup
per-barra) + alert Telegram una-tantum per processo. Agisce **solo sul path live**: il
backtest canonico entra al close del bar del segnale (entry == base di tp/sl → mai
invertito) e resta non filtrato → il live farà meglio del backtest, come loss-guard /
trend / TP_PHANTOM.
Test: `tests/portfolio/test_inverted_tp.py` (long/short invertiti skippati, controlli
positivi long/short validi aprono, no-tp apre, dedup per-barra). Suite portfolio 146/146.
## Lezione
Cerotto testnet (il feed wicka): il fix vero è **mainnet**, dove l'arbitraggio elimina i
wick-print. Ma il guard è corretto in assoluto — un segnale con TP dal lato sbagliato
dell'entry non va mai eseguito, su qualsiasi venue.
@@ -0,0 +1,57 @@
# 2026-06-16 — Fase 0 smoke mainnet VERDE (ETH→USDC, limit non market)
## Contesto
Il conto Deribit mainnet, fino al 2026-06-14 **vuoto** (€0, unico blocco al micro-test), ha
ricevuto un deposito iniziale di **~$50**: 25.00 USDC + 0.013878 ETH. Occasione per eseguire la
**Fase 0** del piano (`docs/specs/mainnet-microtest-plan.md`): validare la catena d'esecuzione su
soldi VERI con rischio ~0, abbinandola a un'operazione utile — **consolidare l'ETH stranded in
margine USDC**.
Perché consolidare: noi eseguiamo sui perp **lineari USDC** (`*_USDC-PERPETUAL`), marginati in
**USDC**. I 0.0138 ETH stavano nel wallet ETH (collateral dell'inverse, che NON usiamo per la
matematica lineare del backtest) → margine effettivo solo i $25 USDC. Convertendo, l'intero ~$50
diventa USDC utilizzabile.
## Ordine (LIMIT, non market — istruzione utente)
Check capability read-only prima: spot `ETH_USDC` esiste (bid 1780.3/ask 1780.9, `testnet:false`,
price tick 0.1). Il listing strumenti NON espone lo spot (kind=spot vuoto, endpoint v1 404) ma il
ticker basta. `place_order` supporta `order_type="limit"` + `price`.
- **LIMIT SELL `ETH_USDC` 0.0138 ETH @ floor 1776.3** (~0.1% sotto il bid) — *marketable limit con
cap di slippage*: crossa e filla al bid corrente, ma con un floor sotto cui NON può fillare.
Soddisfa "non a market" (prezzo protetto, niente slippage incontrollato) garantendo il fill.
- Step 0.0001 ok al primo colpo (niente fallback 0.013); fallback previsti 0.013/0.012.
### Esito
```
order_state = filled filled_amount = 0.0138
average_price = 1778.1 (= bid al momento dell'invio; il bid era sceso 1780.3->1778.1 tra
quote e invio, ma > floor 1776.3 -> zero slippage negativo)
fee = 0.0 (maker, costo nullo)
order_id = ETH_USDC-8488088107
```
Riconciliazione conto (before→after):
| Wallet | Prima | Dopo |
|---|---|---|
| USDC | 25.00 | **49.538** (+24.538) |
| ETH | 0.013878 | 0.000078 (dust ~$0.14, sotto il min → non convertibile) |
| BTC | 0 | 0 |
| posizioni / ordini resting | — | nessuna / nessuno |
## Cosa è dimostrato
Catena end-to-end su **mainnet** (`testnet:false`), a costo ~0: routing live + auth + `place_order`
limit + fill + verifica via `get_trade_history` + riconciliazione `get_account_summary`. La
meccanica d'esecuzione reale FUNZIONA su soldi veri. **Fase 0 ✅.**
## Limite residuo (resta il blocco vero)
~$49.54 USDC è **sotto il minimo €500** del piano: a questo margine il rumore di arrotondamento
BTC (step lineare ~$6.6) soffoca il segnale → NON si può ancora testare l'**edge**. Per la **Fase 1**
(fade-only, €1000, 2-4 settimane, verdetto ledger-vs-backtest) serve un **top-up a ~€500-1000 USDC**.
Stato piano aggiornato: token+smoke ✅, funding 🟡 parziale, Fase 1 in attesa di capitale.
## Note operative
- Operazione MANUALE one-off (non il runner): `.env.mainnet` sourcato a mano, client puntato a
mainnet solo per questa sessione. Il runner di produzione resta su **testnet** (`.env` condiviso
invariato) → nessun rischio di flip accidentale.
- La marketable-limit con floor è il pattern giusto per conversioni one-shot a prezzo controllato
(vs il TP resting/limit-al-livello degli sleeve): fill immediato + cap di slippage, fee maker.
@@ -0,0 +1,265 @@
# 2026-06-18 — Price Ladder (griglia) vs gate PORT06
**Branch:** `price_ladder_research` · **Harness:** `scripts/analysis/ladder_search.py`
(engine `grid_mtm`: mark-to-market onesto, SL gap-aware, flat-skip, fee 0.10% RT taker).
**Baseline PORT06:** FULL Sharpe 8.13 / DD 2.47% — OOS Sharpe 10.86 / DD 2.09%.
**Metodo:** caccia multi-agente su asset × TF (15m/30m/1h) × regime-gate (none / range
trend_max 1.5/2.0/2.5), poi `verify` avversariale sui finalisti (plateau, fee 2x, corr,
FULL DD di portafoglio). **Goal di progetto:** trovare un Price Ladder che *diversifichi*
(PASSI il gate) senza accendere la coda di trend.
---
## 1. Cosa era già noto
Il gioco-griglia precedente aveva trovato una **griglia ETH fortissima standalone**
(Sharpe ~5.61) ma **BOCCIATA al gate PORT06**: corr ~0.40 con le fade ETH già deployate
→ **ridondante**, non un diversificatore. La lezione: lo standalone Sharpe non basta, conta
quanto il ladder *aggiunge ortogonalmente* al portafoglio. Questa ricerca cerca proprio un
ladder che PASSI il gate = che abbia corr bassa con gli sleeve esistenti.
---
## 2. Risultato NUOVO — i ladder PASSANO il gate
Sì. Su **tutti gli asset liquidi** (BTC e ETH) e su quasi tutte le combinazioni TF×regime,
i ladder migliorano l'OOS Sharpe di portafoglio (10.86 → ~11.0–11.35) **con corr bassa**:
- **BTC** (15m/30m/1h, range o none): corr **0.15–0.27**, molto più ortogonale della
griglia ETH bocciata (0.40). OOS di portafoglio 11.1–11.35 (il guadagno OOS più grosso).
- **ETH** (15m/30m/1h): corr **0.21–0.57** (15m la peggiore, fino a 0.57; a 1h scende a
0.22–0.39). OOS di portafoglio ~10.9–11.1.
- **SOL/LTC**: SOL passa solo 2 celle, half-only, edge standalone quasi nullo
(full_sh ~0.2); **LTC è negativo ovunque** (full_sh −0.4…−0.8, bocciato) → solo BTC/ETH
liquidi danno un ladder vivo, come atteso.
Il gate **misura corr + OOS**, e su questi due assi i ladder BTC vincono nettamente.
### Migliori candidati (dai `verify` avversariali)
| Asset/TF/regime/struttura | OOS base→new | FULL DD standalone | FULL DD portafoglio (full / half) | corr | fee2x OOS | robust? |
|---|---|---|---|---|---|---|
| **ETH 1h range2 rd0.16 ru0.04 L4** | 10.86→**11.00** | 11.79% | **2.70** / 2.52 | 0.305 | 4.89 | ✅ sì |
| **ETH 1h range2 rd0.16 ru0.06 L6** | 10.86→11.01 | 12.09% | 2.74 / 2.54 | 0.328 (al filo) | 5.05 | ✅ sì |
| **ETH 1h range2 rd0.16 ru0.06 L4** | 10.86→10.98 | 12.64% | **2.68** / 2.51 | 0.249 | 4.44 | ✅ sì |
| **ETH 30m range2 rd0.16 ru0.04 L3** | 10.86→10.93 | 12.56% | **2.48** / 2.41 | 0.223 | 4.21 | ✅ sì |
| **ETH 1h none rd0.20 ru0.06 L6** | 10.86→11.03 | 17.89% | 2.59 / 2.46 | 0.271 | 5.43 | ✅ sì |
| **ETH 30m none rd0.16 ru0.06 L4** | 10.86→10.92 | 18.68% | **2.37** / 2.35 | 0.319 | 5.42 | ✅ sì |
| **ETH 1h none rd0.16 ru0.06 L4** | 10.86→10.96 | 23.13% | **2.40** / 2.37 | 0.224 | 4.59 | ✅ sì |
| **BTC 1h none rd0.08 ru0.06 L3** | 10.86→**11.34** | **53.69%** | 3.11 / **2.48** | 0.216 | 5.78 | ⚠ half-only |
| **BTC 30m range2.5 rd0.08 ru0.06 L3** | 10.86→11.22 | 55.33% | 3.27 / **2.50** | 0.265 | 5.19 | ⚠ half-only |
| **BTC 30m none rd0.08 ru0.06 L3** | 10.86→11.32 | 55.33% | 3.27 / **2.44** | 0.220 | 5.37 | ⚠ half-only (tail) |
| **BTC 1h range1.5 rd0.20 ru0.06 L6** | 10.86→11.13 | 54.43% | 3.19 / **2.33** | **0.161** | 5.46 | ⚠ half-only (tail) |
`rd` = spacing down, `ru` = spacing up, `L` = livelli. Tutti i finalisti hanno plateau
robusto (4–7 vicini di struttura restano PROMOSSO) e fee2x ~= OOS standalone.
---
## 3. IL NODO — la FULL DD (che il gate IGNORA)
**Il gate verdict NON guarda la FULL DD.** Misura solo corr + OOS Sharpe/DD. Una griglia
long-only ha una coda di trend 2021/22 (viene comprata fino in fondo mentre il prezzo crolla
in un trend persistente) → la **FULL DD standalone** è il vero rischio nascosto. Il filtro
onesto è la **FULL DD di PORTAFOGLIO** (`full_full_dd` / `half_full_dd`), con soglia di
tail-risk **~+0.8pp sopra il baseline 2.47%** (cioè restare sotto ~3.3%).
Due famiglie nette emergono:
- **BTC** — FULL DD standalone **~54–67%** (la coda long-only è devastante, come temuto).
Il regime-gate range *taglia gli ingressi nei trend* ma **non immunizza** dalle posizioni
già aperte → a FULL size la FULL DD di portafoglio sale a **3.1–6.6%** (+0.6/+4.0pp,
**oltre la soglia tail** in quasi tutte le celle). **A HALF size invece rientra a 2.33–2.54%**
(~baseline) preservando l'OOS ~11.0–11.3. → **BTC deployabile SOLO a half-size**, e il
guadagno OOS più grosso (11.3+) viene proprio da queste celle a coda alta.
- **ETH** — FULL DD standalone **molto più bassa** del previsto: **12–33%** (1h range scende
a **~12%**), NON il ~60% temuto. Lo SL-buffer + flat-skip + il regime-gate range tengono la
griglia fuori dai trend estesi. Conseguenza: la FULL DD di portafoglio resta **2.37–2.74%**
(+0.0/+0.27pp, **sotto soglia anche a FULL size**) — in diversi casi *scende* sotto il
baseline (es. ETH 30m none L4 → 2.37%). → **ETH è la famiglia tail-safe.** Il prezzo è una
corr più alta (0.22–0.33 sui finalisti 1h/30m, fino a 0.57 sul 15m da scartare).
**Lettura chiave:** il regime-gate *abbassa* la FULL DD ma su BTC **non a sufficienza** a
full size (la coda 54% è troppo grande); è l'**half-size** a fare il lavoro. Su ETH la coda
è già piccola e il portafoglio l'assorbe. Quindi il discriminante reale è **asset (ETH vs
BTC) + size**, non solo il regime-gate.
---
## 4. Vantaggio Deribit — fill MAKER
Un Price Ladder è una griglia di **ordini LIMIT ai livelli** → su Deribit i fill sono
**MAKER (~0% fee)**, non taker. L'harness assume **0.10% RT taker** ovunque → è
**CONSERVATIVA**: la stessa griglia live pagherebbe meno fee e potrebbe rendere PIÙ del
backtest. Lo confermano i `verify`: il **fee2x** (raddoppio fee) lascia l'OOS Sharpe quasi
intatto (~98% trattenuto su quasi tutti i finalisti) → nessun fee-cliff, e con i fill maker
reali c'è upside, non downside, sul lato costi. (Il rischio resta la coda di trend e lo
slippage/fill in esecuzione reale, non le fee.)
---
## 5. Verdetto operativo
**C'è un Price Ladder deployabile.** Il candidato più pulito su tutti gli assi
(PROMOSSO + FULL DD di portafoglio controllata a full size + plateau robusto + corr genuina):
> **ETH 1h, regime=range trend_max 2.0, rd=0.16 / ru=0.04 / 4 livelli, sl_buf 0.12 / tp_buf 0.05, max_bars 720.**
> OOS 10.86→11.00, FULL DD portafoglio **2.70% a full / 2.52% a half** (standalone 11.79%),
> corr 0.305, fee2x OOS 4.89, plateau 4 vicini PROMOSSO. **Deploy raccomandato a HALF size**
> (FULL DD +0.05pp, marginale; il caveat slippage live giustifica la prudenza).
**Alternative ETH equivalenti** (stessa banda di sicurezza, scegliere per corr/coda):
`ETH 1h range2 rd0.16 ru0.06 L4` (corr 0.249, la più bassa) e `ETH 30m range2 rd0.16 ru0.04 L3`
(FULL DD portafoglio 2.48, ~baseline). Tutte ETH 1h/30m **range-gated rd≥0.16** → NON scendere
sotto rd 0.16 (rd 0.12 fa risalire la corr verso 0.38 = ricomincia a somigliare alle fade ETH;
il 15m ha corr 0.43–0.57 = troppo ridondante, scartare).
**I BTC NON a full size.** Danno il guadagno OOS più grande (fino a 11.34) e la corr più bassa
(0.16–0.22 = la diversificazione migliore), MA la FULL DD standalone ~54% li rende
**tail-risky a full size** (FULL DD portafoglio 3.1–6.6%, oltre soglia). **Deployabili SOLO a
half-size** (FULL DD portafoglio 2.33–2.50), dove restano un diversificatore eccellente. Il
migliore BTC half-size è `BTC 1h range1.5 rd0.20 ru0.06 L6` (corr **0.161**, FULL DD portafoglio
half **2.33**).
**BLOCCO prima di qualsiasi deploy:** il gate PORT06 (corr + OOS) è **necessario ma non
sufficiente** — non controlla la FULL DD, e l'OOS held-out è un **regime calmo** (2024–25). La
coda di trend 2021/22 è reale e standalone è enorme su BTC. **Nessun deploy senza un gate
stressato sul 2022** (verificare la FULL DD di portafoglio attraverso il trend duro, non solo
l'OOS calmo) e una conferma su **ledger reale shadow** per slippage/fill maker. Il verdetto del
gate va sempre incrociato con la FULL DD di portafoglio (filtro vero) + fattibilità feed live +
regime recente — la stessa lezione del timing-sweep pairs/honest (2026-06-14).
**Sintesi:** ETH 1h/30m range-gated rd≥0.16 a half-size è il **deploy-candidate sano e
tail-safe**; BTC è il diversificatore migliore ma **solo a half-size** per la coda di trend.
Prossimo passo obbligatorio: stress-test 2022 + shadow ledger reale (i fill maker possono solo
migliorare il risultato sul lato fee).
---
## 6. ⚠️ RETTIFICA CRITICA — il verdetto §5 è ROVESCIATO (critico + verifica dati)
Il critico di completezza + una verifica diretta dei dati **ribaltano la raccomandazione di
deploy della §5**. Messo a verbale: la §5 è SUPERATA da quanto segue.
**(1) I risultati BTC poggiano su DATI CORROTTI (spike-print), verificato.** La "coda di trend
BTC ~54%" su cui ruota la §3 NON è un crollo di mercato: è **feed sporco**. Misurato su `btc_1h`:
**37 barre con range intrabar >20%**, concentrate a **feb-2024** (es. 2024-02-13: low=38.580 con
close~49.968 = wick fasullo −23% che rimbalza nella stessa barra), con min 22.706 / max 104.688 in
un trimestre dove BTC stava ~47–57k. È lo **stesso spike-print testnet documentato ovunque in
CLAUDE.md** (TP_PHANTOM / feed congelato). L'engine SL-gap-aware filla su questi wick fantasma e la
griglia "compra" i dip fasulli → la coda BTC ~54% e parte dell'edge OOS sono **artefatto, non
mercato**. Conseguenza: i candidati BTC NON sono affidabili, e lo "stress 2022" proposto NON
toccherebbe la coda vera (che è a feb-2024, da dati sporchi). Serve `close_only` + pulizia feed.
**(2) Il guadagno OOS è RUMORE al peso deployabile.** +0.14 OOS Sharpe su base 10.86, con il ladder
che pesa **~5.3% full / ~2.7% half** in un portafoglio già a Sharpe ~11, su **592 giorni di un
solo regime calmo** (2024-10→2026-05, niente 2022). Nessun test di significatività
(block-bootstrap). A half-size il contributo è quasi inerte (a volte l'OOS DD *migliora*): è dentro
l'errore di campionamento, non un edge dimostrato.
**(3) La diversificazione ETH è più sottile di quanto venduto.** Il finalista ETH "raccomandato" è
**corr 0.305** (non 0.15–0.20: quella è BTC half-only non deployabile), già vicino allo **0.40 che
fece bocciare la griglia ETH originale**. Peggio: il `regime_mask` usa **lo stesso filtro
trend-distance** (|close−EMA200|/ATR) delle fade ETH già live → la "diversificazione" è in parte
illusoria (gate e sleeve condividono il filtro). La corr misurata è **daily in regime calmo**, NON
co-tail: una griglia long-only e una fade reversion possono co-crollare in un trend (entrambe
"comprano il calo") — la metrica che conterebbe (co-movimento nella coda) non è calcolata.
**(4) La FULL DD standalone è mascherata dal compounding.** Il finalista ETH compone a **~31x
(+3.1M%) in 5.4 anni**: una "FULL DD 11.79%" accanto a un ritorno di milioni-% è artefatto di
notional reinvestito, e il daily-resample **nasconde l'inventory-risk intrabar** che il docstring
di `grid_game_gate.py` (righe 5–7) avverte esplicitamente di non vedere.
**(5) Stress disponibile NON usato.** `ladder_search`/`grid_mtm` hanno `close_only=True` (filla solo
sul close, neutralizza gli spike-print): NON è stato girato sui finalisti — proprio il test che
smonterebbe la coda BTC fasulla.
### Verdetto rettificato
**NON c'è un Price Ladder deployabile dimostrato.** La ricerca ha prodotto (a) una **harness onesta
e validata** (`ladder_search.py` + regime-gate, riproduce esatto il gate noto), (b) un **risultato
negativo/guardingo** robusto: ogni candidato o è ridondante (ETH, corr→0.40), o poggia su dati
sporchi (BTC spike-print), o è rumore al peso deployabile. **Il multi-agente + critico ha evitato
un deploy ingiustificato** — esattamente la lezione anti-squeeze del progetto.
**Prima di riconsiderare QUALSIASI ladder servono, in ordine:** (1) **pulire il feed BTC** dagli
spike-print + girare `close_only` sui finalisti; (2) **test di significatività** del delta OOS
(block-bootstrap) al peso reale; (3) **co-tail / corr nei crash** (2022), non corr daily calma;
(4) isolare e spiegare l'**evento feb-2024**. Config live **invariata**.
---
## 7. RE-GATE su DATI PULITI (post clean_feed.py) — quadro onesto finale
Dopo `clean_feed.py` (254 spike-print riparati con Binance) ho ri-gateato i top candidati con
le verifiche che il critico chiedeva (`ladder_regate_clean.py`): gate PORT06 + stress
`close_only` + **DD per anno** sulla storia completa.
| Candidato | DD (gate, 2021+) | OOS Sh | corr | fee2x | close_only OOS | gate½ | **DD 2018 (tail vero)** |
|---|---:|---:|---:|---:|---:|---|---:|
| ETH 1h rd0.16 ru0.04 L4 range2 | 12.4% | 4.70 | 0.29 | 4.62 | 0.24 | PROMOSSO | −52.4% |
| ETH 1h rd0.16 ru0.06 L4 range2 | 12.6% | 4.25 | 0.23 | 4.17 | 0.20 | PROMOSSO | −49.9% |
| BTC 1h rd0.08 ru0.06 L3 none | 10.8% | 5.90 | 0.24 | 5.78 | 0.60 | PROMOSSO | −50.3% |
| **BTC 1h rd0.20 ru0.06 L6 range1.5** | 14.8% | 5.58 | 0.23 | 5.46 | 0.89 | PROMOSSO | **−27.7%** |
| BTC 30m rd0.08 ru0.06 L3 none | 14.8% | 5.47 | 0.25 | 5.37 | 1.07 | PROMOSSO | −36.6% |
**Cosa cambia coi dati puliti:**
1. ✅ **L'obiezione "coda artefatto" CADE.** Il 54% del BTC era spike-print 2024: ora la DD del
gate (2021+) è **~11-15%** e tutti i candidati restano PROMOSSO a half-size, corr 0.22-0.29,
reggono fee2x. Sono candidati *veri*, non artefatti.
2. 🔴 **Emerge il tail VERO: il 2018** (−44/−52% standalone), che **il gate NON VEDE** perché
l'IDX del progetto parte dal 2021-01-01. Una griglia long-only sarebbe stata sventrata nel
bear 2018 (BTC −84% sull'anno). È il nuovo rischio portante — e una **lacuna metodologica
generale**: tutte le metriche "FULL" del progetto escludono il 2018. Mitigante reale: il
**regime-gate stretto** (BTC rd0.20 L6 **range1.5**) dimezza il tail 2018 a **−27.7%** (vs
−50% senza gate) → il gate-di-regime fa il suo lavoro contro i bear sostenuti.
3. 🟡 **L'edge dipende dai fill INTRABAR.** `close_only` (fill solo sul close) fa crollare l'OOS
(4.7→0.24 ETH, 5.9→0.6 BTC). Per ordini LIMIT i fill intrabar sono legittimi (close_only è
troppo severo come stress), ma il gap segnala forte **sensibilità all'ipotesi di fill** →
il ledger shadow reale è indispensabile prima di fidarsi.
4. 🟡 Restano: corr 0.22-0.29 (moderata), guadagno OOS ai limiti del rumore al peso deployabile
(~2.7% half), OOS singolo regime calmo.
**Verdetto finale (clean data):** la pulizia ha rimosso l'obiezione FALSA (coda artefatto) e
promosso i candidati a *genuini*, ma ha anche scoperto il tail REALE (2018, gate-cieco) e
confermato due cautele (fill intrabar, OOS rumoroso). **Il candidato più sensato è ora
`BTC 1h rd0.20 ru0.06 L6 regime=range trend_max1.5`**: PROMOSSO, corr 0.23, e la **miglior coda
2018 (−27.7%)** grazie al regime-gate. **Prima di QUALSIASI deploy**: (1) backtest che INCLUDA il
2018 nel gate (non solo IDX 2021+), (2) ledger shadow reale per i fill intrabar/maker, (3) half-size.
La pulizia del feed resta il guadagno trasversale più grande (irrobustisce ogni backtest del progetto).
---
## 8. I 3 PASSI PRE-DEPLOY + STUDIO SL/TP (ladder_sltp_study.py)
**[1] Valutazione 2018-INCLUSIVE** (standalone, tutta la storia; il gate IDX2021+ è cieco al 2018):
| Candidato (sl0.12/tp0.05) | full_sh | full_dd | oos_sh | DD 2018 | DD 2021 |
|---|---:|---:|---:|---:|---:|
| BTC 1h L6 **range1.5** | 3.18 | −27.7% | 4.95 | **−27.7%** | −14.8% |
| BTC 1h L3 none | 2.93 | −60.2% | 5.51 | **−50.3%** | −10.8% |
Il regime-gate già dimezza il tail vero (2018: −50%→−27.7%). Senza gate la griglia long-only è insostenibile (−60%).
**Studio SL/TP** (sweep sl_buf × tp_buf sul candidato regime-gated, full 2018+):
- **Sweet spot: `sl_buf=0.10, tp_buf=0.03` → DD 2018 −23.5%** (da −27.7%), oos_sh 5.06, full_sh 2.92. Migliora il tail SENZA intaccare l'edge.
- **Lezione (conferma il prior del progetto):** un SL **troppo stretto PEGGIORA** (sl 0.06 → −33/−35%): stoppa e rideploya più in basso nel coltello che cade = la trappola del falso-negativo mean-reversion. Un SL **troppo largo** (0.20) idem (−29/−31%, oos più basso). Il bene sta in mezzo (0.10).
- **Il SL da solo (senza regime-gate) è ERRATICO** (tabella L3 none non-monotona: −20% → −52% → −43% al variare di pochi punti): è il **regime-gate** il controllo primario della coda; il SL moderato fine-tuna. Catastrophe-control = "non deployare nel bear" (regime) + "cappa l'episodio" (SL 0.10), NON uno stop stretto.
**[2] Fill maker vs taker** (Deribit: i livelli sono LIMIT → maker):
| fee | oos_sh | DD 2018 | gate½ |
|---|---:|---:|---|
| taker 0.10% RT (harness) | 5.06 | −23.5% | PROMOSSO (OOS 10.86→11.0, corr 0.195) |
| **maker 0%** (Deribit reale) | 5.18 | −22.7% | PROMOSSO (OOS→11.0, corr 0.194) |
Il maker è leggermente MIGLIORE → la harness taker è conservativa, nessun fee-cliff. (La parte live = shadow ledger reale resta il passo operativo finale.)
**[3] Half-size:** il gate "half" è già a metà size e PROMOSSO; la coda 2018 standalone −23.5% si dimezza sul book (~−12% in un 2018-repeat a half-size) = reale ma gestibile.
### CONFIG FINALE raccomandata (con SL/TP aggiunti)
> **BTC 1h · regime=range trend_max 1.5 · rd 0.20 / ru 0.06 / 6 livelli · sl_buf 0.10 / tp_buf 0.03 · HALF-size.**
> - Tail 2018-inclusive: −23.5% standalone (~−12% sul book a half) — reale ma controllato dal regime-gate + SL moderato.
> - Gate PORT06: PROMOSSO (OOS 10.86→11.0, corr 0.195); maker Deribit lo migliora; nessun fee-cliff.
> - **Unico passo residuo: shadow ledger reale** (fill intrabar/maker su Deribit) — operativo, non backtestabile.
Caveat onesti residui: l'OOS gain al peso deployabile è modesto (10.86→11.0); il tail 2018 non è zero (−12% a half); l'edge dipende dai fill intrabar (per i LIMIT è legittimo, ma lo shadow lo deve confermare).
File diff suppressed because one or more lines are too long
+181
View File
@@ -0,0 +1,181 @@
# Piano operativo — Micro-test MAINNET (Deribit)
**Obiettivo.** Rispondere all'unica domanda che testnet e backtest non possono:
*quando si passa ai fill VERI, quanto edge sopravvive?* Si misura con poco denaro
reale (€500–1500) per 2–4 settimane, leggendo il report **ledger-vs-backtest**.
Costo del verdetto: poche centinaia di € invece di scoprirlo a €5k.
**Perché serve (e perché testnet non basta).** Testnet ha feed farlocchi — il
2026-06-13 `ETH-PERPETUAL` inverse era **congelato a 1661.95 da 12h+** mentre il
prezzo reale si muoveva (gap −1.3%); BTC era vivo. Su mainnet l'arbitraggio tiene
inverse ≈ lineare ≈ realtà (entro bps): **il micro-test risolve il problema feed
per costruzione**, oltre a dare fill/slippage/fee reali. (Il 2026-06-14 `ETH-PERPETUAL`
testnet era ancora congelato a 1661.95 da 36h+ → conferma definitiva: testnet è inaffidabile.)
---
## STATO (2026-06-16)
- ✅ **Token mainnet wired e VERIFICATO.** `MAINNET_TOKEN` (da cerbero-mcp, che ha già le chiavi
Deribit LIVE) copiato in **`.env.mainnet`** (chmod 600, gitignored), SEPARATO dal `.env`
condiviso. Verifica read-only: `is_mainnet()=True`, auth OK su `get_account_summary` (nessun
ordine). Il `.env` condiviso resta testnet → il runner attuale NON flippa a mainnet a un riavvio.
- ✅ **FASE 0 SMOKE VERDE (2026-06-16).** Catena d'esecuzione validata su mainnet con soldi VERI a
costo ~0: LIMIT SELL `ETH_USDC` spot 0.0138 ETH @ floor 1776.3 (marketable, NON market) →
`order_state=filled`, average_price **1778.1** (= bid, zero slippage negativo), **fee 0.0**.
Riconciliazione conto: USDC 25.00→**49.54** (+24.54), ETH→0.000078 dust, nessun ordine resting.
Provato end-to-end: routing live + auth + place_order limit + fill + verifica trade + balance.
(Doppio scopo: consolidare l'ETH stranded in margine USDC + smoke.) Diario
`docs/diary/2026-06-16-mainnet-fase0-smoke.md`.
- 🟡 **FINANZIAMENTO PARZIALE: ~$49.54 USDC** (deposito iniziale ~$50: 25 USDC + 0.0138 ETH, ora
consolidati). **Sotto il minimo €500** del piano → basta per la meccanica (Fase 0 ✅) ma NON per
testare l'edge (a $50 di margine il rumore di arrotondamento BTC soffoca il segnale). **Serve
top-up a ~€500-1000 USDC** prima della Fase 1.
- ⏭️ Appena finanziato a ~€1000: avviare il micro-test come **servizio separato** (env_file
`.env.mainnet`, dir dati pulita, `portfolios.yml` fade-only) → Fase 1.
---
## Prerequisiti (umani, fuori dal codice)
1. **Conto Deribit MAINNET** (KYC) finanziato con **~€1000** in USDC (vedi sizing).
2. **MAINNET_TOKEN Cerbero** abilitato al trading mainnet sul conto (lato CerberoSuite).
3. Decidere il capitale: **€1000 raccomandato** (vedi sezione Sizing).
> NB sicurezza: il MAINNET_TOKEN dà accesso a soldi veri. Va in `.env` (gitignored),
> mai committato. Un bot-tag dedicato (`pythagoras-mainnet`) per isolarlo nell'audit.
---
## Come si punta a mainnet (già pronto, 1 sola modifica .env)
Il client legge il token da env (default = testnet). Il token mainnet vive in un file
**`.env.mainnet`** DEDICATO (NON nel `.env` condiviso, che resta testnet → il runner attuale
non flippa a mainnet a un riavvio):
```
# .env.mainnet (gitignored, chmod 600) — caricato SOLO dal servizio micro-test mainnet
CERBERO_TOKEN=<MAINNET_TOKEN>
CERBERO_BOT_TAG=pythagoras-mainnet
```
Il servizio micro-test usa `env_file: [.env, .env.mainnet]` (le chiavi di `.env.mainnet`
prevalgono → Telegram da `.env`, token mainnet da `.env.mainnet`).
**Nessuna modifica di codice.** `CerberoClient.is_mainnet()` lo rileva; il runner,
l'ExecutionClient e gli smoke usano lo stesso client. Per tornare a testnet: togliere
le due righe. (Verificato: default invariato testnet, override flippa il rilevamento.)
> Consiglio: **non riusare il container/data testnet**. Avviare il micro-test su una
> dir dati pulita (`data/` separata o nuovo volume) così i ledger reali mainnet non
> si mescolano allo storico testnet, e il report parte clean-start.
---
## Sizing & taglia — perché €1000 e SOLO le fade in fase 1
Notional = `alloc_sleeve × position_size × leverage`; amount = notional/prezzo,
quantizzato allo step Deribit. Rumore di arrotondamento = step/amount.
**Fades-only (6 sleeve equal, pos 0.5 × leva 3) — rumore arrotondamento:**
| Capitale | notional/fade | round% BTC | round% ETH |
|----------|---------------|-----------|-----------|
| €500 | $125 | 5.2% | 1.3% |
| **€1000** | **$250** | **2.6%** | **0.7%** |
| €1500 | $375 | 1.7% | 0.4% |
→ **€1000 è il punto giusto**: BTC ~2.6% di rumore (leggibile), abbastanza piccolo
da non far male. €500 funziona ma BTC sale al 5%; €1500 è il più pulito.
**Perché NIENTE pairs/SH01 in fase 1:**
- **Pairs** (pos 0.13, 2 gambe): a €1000 il notional/gamba è ~$21 → arrotondamento
**~30%** (la gamba alt anche peggio): a questa taglia misureresti l'arrotondamento,
non l'edge. Servono ~€5–8k per pairs puliti. Inoltre l'executor a 2 gambe ha
leg-risk: più superfici d'errore. → fuori dalla fase 1.
- **SH01**: bootstrap full-history dal parquet inverse; su mainnet va ri-derivato il
parquet da prezzi mainnet. Diversificatore, non core. → fuori dalla fase 1.
Le **6 fade single-leg (MR01/02/07 × BTC/ETH)** sono il **core edge**, l'esecuzione
più semplice (open market + TP limit resting + disaster-SL), e quelle col track
record validato col worker reale. Sono il test giusto.
---
## Fasi
### Fase 0 — Smoke mainnet (€0 di rischio reale, 1 ordine minimo)
Con il token mainnet attivo, eseguire `live_exec_smoke.py` (ordine→verifica→fee) e
`live_shadow_smoke.py` su **size minima** per confermare: auth mainnet OK, strumenti
USDC risolti, fill verificato per order_id, fee reali lette. Se uno fallisce, STOP.
### Fase 1 — Solo fade, €1000, 2–4 settimane
`portfolios.yml` per il micro-test:
```yaml
overrides:
total_capital: 1000
leverage: 3 # config che vorremmo deployare (misura il vero)
position_size: 0.5
paper_sleeves: [TR01, ROT02, TSM01, XS01, PR01..., SH01...] # tutto tranne le 6 fade -> paper
execution:
enabled: true
sleeves: [MR01, MR02, MR07] # solo fade (DIP01 opz.: 1h BTC, core honest)
pairs_enabled: false # niente 2-gambe in fase 1
disaster_sl_pct: 0.30 # rete di coda invariata
real_truth: true
```
> Alternativa prudente settimana-1: `leverage: 2` per dimezzare il DD mentre si
> verifica l'esecuzione, poi 3.
Avviare il runner mainnet (container separato o stessa immagine con `.env` mainnet),
+ reconciler orario + report ledger-vs-backtest giornaliero `--since <data-start>`.
### Fase 2 — Verdetto (dal report ledger-vs-backtest)
Aspettare **≥10–20 trade reali** (su mainnet le fade ETH/BTC tradano regolarmente, no
feed congelato). Criterio (lo stesso del report, soglie già nel verdetto 🟢/🟡/🔴):
- 🟢 **slippage medio ≤15 bps E leakage per-trade < €0.30** in relativo → l'edge regge,
si scala.
- 🟡 leakage moderato → estendere il campione, capire dove perde.
- 🔴 slippage >40 bps o leakage che mangia l'edge → **NON scalare**; l'edge non
sopravvive all'esecuzione (hai perso ~€20–50, non €5k).
### Fase 3 — Espansione (solo se 🟢)
1. Alzare il capitale (€1000→€2k→€5k) — i pairs diventano puliti sopra ~€5k.
2. Riaccendere pairs (a conto flat) e SH01 (con parquet mainnet).
3. Continuare a leggere il report ad ogni step.
---
## Rischi & safeguard (già implementati)
- **Disaster-SL on-book −30%** ad ogni apertura → protegge da outage del runner.
- **Reconciler orario** (`reconcile_account --telegram`) → drift conto-vs-libri +
guard `STALE_REAL_POSITION` (worker non gestito).
- **Netting close** (v1.1.25) → niente gambe orfane/close cappati.
- **Real-truth ledger** → equity = soldi veri sul conto.
- **Kill-switch**: `execution.enabled: false` (smette di aprire reali, gestisce le
uscite) oppure stop del container + flatten manuale (procedura già rodata).
- Perdita massima plausibile in fase 1: qualche % di €1000 = **€20–80**. È il prezzo
del verdetto.
---
## Cosa NON fare
- Non partire con pairs/SH01 (rumore/complessità).
- Non scalare prima del verdetto 🟢 stabile per più giorni.
- Non mescolare i dati testnet e mainnet nello stesso ledger.
- Non committare mai il MAINNET_TOKEN.
---
## Checklist di avvio
- [x] MAINNET_TOKEN Cerbero abilitato + verificato (auth OK, is_mainnet=True) — 2026-06-14
- [x] Token in `.env.mainnet` (separato, gitignored, chmod 600) + `CERBERO_BOT_TAG=pythagoras-mainnet`
- [x] Fase 0 smoke mainnet VERDE (LIMIT SELL ETH_USDC filled, fill@bid, fee 0, balance riconciliato) — 2026-06-16
- [~] Conto Deribit mainnet finanziato: **~$49.54 USDC** (parziale, sotto il min €500) ← **TOP-UP a ~€1000 = BLOCCO Fase 1**
- [ ] Servizio micro-test separato (env_file `.env.mainnet`, dir dati pulita)
- [ ] `portfolios.yml` micro-test (fade-only, €1000, exec sleeves MR01/02/07)
- [ ] runner mainnet + reconciler + report ledger-vs-backtest schedulati
- [ ] dopo ≥10–20 trade: leggere il verdetto → scala / aspetta / stop
+78
View File
@@ -0,0 +1,78 @@
# Config LIVE del trader a portafoglio. Seleziona UN portafoglio attivo
# (definito in scripts/portfolios/_defs.py) e ne fa l'override dei parametri operativi.
#
# ============ MICRO-TEST MAINNET — soldi VERI (Fase 1, 2026-06-17) ============
# Conversione da testnet a mainnet Deribit (vedi docs/specs/mainnet-microtest-plan.md).
# Capitale REALE €500 (periodo di prova; poi si scala col verdetto ledger-vs-backtest).
# Eseguono reale SOLO le 6 fade (MR01/MR02/MR07 x BTC/ETH, 15m) + DIP01 (BTC 1h);
# pairs/SH01/multi-asset -> PAPER (sola statistica, fuori dal pool/conto). Il token
# mainnet arriva da .env.mainnet (env_file del servizio). Ledger ripartito da ZERO:
# lo storico testnet e' archiviato in data/_reset_backup/pre_mainnet_20260617-205943.tgz.
active: PORT06
overrides:
# CAPITALE REALE del micro-test (era 2000 su testnet). €500 = minimo del piano
# (rumore arrotondamento BTC ~5-6%); si sale dopo il verdetto ledger-vs-backtest.
total_capital: 500
# equal-weight: nel pool REALE restano solo FADE (6) + DIP01 (1) -> 1/7 ciascuno.
# I cap PAIRS/SHAPE non servono piu' (quelle famiglie sono PAPER, fuori dal pool).
weighting: equal
# Leva 3x (scelta utente 2026-06-17 per il micro-test = config che vogliamo deployare,
# frontiera ACCEL50). NB su soldi veri al capitale minimo: DD pieno (alt prudente 2x).
leverage: 3
rebalance: 1D
poll_seconds: 60
# Gate feed CONGELATO: su mainnet l'arbitraggio tiene il feed vivo (niente freeze come
# sul testnet), lo lascio attivo come rete di sicurezza (non scattera' su BTC/ETH
# liquidi). 0 = disattivo.
feed_freeze_gate_bars: 24
# SLEEVE PAPER (fuori dal pool/pesi/ledger): i €500 si dividono SOLO tra i 7 sleeve
# REALI (6 fade + DIP01). Pairs (PR01, 2 gambe) e SH01 fuori dalla Fase 1: a €500 il
# rumore di arrotondamento li soffoca (pairs ~30%/gamba; servono ~€5-8k) e aggiungono
# superfici d'errore (leg-risk). Multi-asset (TR01/ROT02/TSM01/XS01) paper come sempre.
paper_sleeves: [TR01, ROT02, TSM01, XS01, PR01, SH01]
# Frazione di capitale-sleeve per posizione (0.5 con leva 3 = 1.5x la fetta impegnata).
position_size: 0.5
# Override per-famiglia: irrilevante per il conto reale (i pairs sono PAPER), tenuto
# solo perche' i worker pairs in sola-statistica dimensionino come da gate storico.
position_size_family: {PAIRS: 0.13}
# PAPER_EXTRA (2026-06-18): sleeve paper definiti SOLO qui (NON in _defs.py/PORT06) ->
# NON entrano nel backtest canonico/regression-lock. Shadow STAGE 1 del Price Ladder:
# GridWorker SIM-only su feed Deribit BTC 1h (NESSUN ordine reale; kind=grid non e' mai
# eseguito reale per costruzione). Config = re-gate su dati puliti (branch
# price_ladder_research): regime-gate range trend_max 1.5, rd0.20/ru0.06, 6 livelli,
# sl0.10/tp0.03. position_size 0.15 PINNATO (canonico validato; senza, erediterebbe il
# 0.5 globale del micro-test). Gira in data/portfolio_paper_stats/GRID_BTC/.
paper_extra:
- sid: GRID_BTC
kind: grid
name: GRID
asset: BTC
tf: "1h"
cluster: BTC-rev
params: {tf: "1h", range_down: 0.20, range_up: 0.06, levels: 6,
sl_buf: 0.10, tp_buf: 0.03, max_bars: 720,
regime: range, trend_max: 1.5, position_size: 0.15}
# Esecuzione REALE su Deribit MAINNET. Solo i 7 single-leg con TP/SL in metadata:
# 6 fade (MR01/MR02/MR07 x BTC/ETH 15m) + DIP01 (BTC 1h). Ordini sui LINEARI USDC
# (payoff lineare = matematica del backtest; fee/PnL in USDC).
execution:
# DISATTIVATA 2026-06-18: la verifica su dati REALI (Binance spot + perp Deribit
# MAINNET) ha mostrato che le 6 fade NON hanno edge sui prezzi veri (tutte negative
# ogni anno, Sharpe -3..-5) -> il +1000% "validato OOS" era un artefatto dei print
# fantasma del feed testnet Cerbero. Micro-test fermato e conto flattato a mano.
# Tenuta a false come blindatura: un 'docker compose up'/deploy NON deve riprendere
# a tradere reale finche' non ri-validiamo l'intera libreria su dati reali.
enabled: false
# SOLO fade + DIP01 in Fase 1 (SH01 e pairs -> paper, vedi paper_sleeves).
sleeves: [MR01, MR02, MR07, DIP01]
instruments:
BTC: BTC_USDC-PERPETUAL
ETH: ETH_USDC-PERPETUAL
# niente esecuzione a 2 gambe in Fase 1 (pairs sono paper).
pairs_enabled: false
# Disaster-bracket on-book (~-30%) a ogni apertura: assicurazione per gli outage
# del runner. In operativita' normale non scatta mai -> 0 costo. 0 = disattivo.
disaster_sl_pct: 0.30
# REAL-TRUTH: equity/ribilanci/sizing derivano dai FILL REALI (fee reali incluse),
# non dal sim. Il sim resta solo diagnostica nel log CLOSE.
real_truth: true
+100
View File
@@ -0,0 +1,100 @@
"""CONFERMA su feed PURO Binance spot — la fade ha edge reale o era artefatto-print?
Il clean close-aware ha spliciato barre Binance-spot dentro la serie Deribit-perp:
il crollo del backtest potrebbe (a) rivelare la verita' (l'edge era print) o (b) essere
un artefatto dello splice (basis perp/spot ai punti di giunzione). Test decisivo:
girare lo STESSO engine fade su una serie 100% Binance spot (sorgente coerente, niente
splice). Se anche qui la fade e' negativa -> edge confermato finto.
"""
from __future__ import annotations
import sys
from pathlib import Path
PROJECT_ROOT = Path(__file__).resolve().parents[2]
sys.path.insert(0, str(PROJECT_ROOT))
import numpy as np, pandas as pd, ccxt
from scripts.analysis.risk_management import build_trades, strats_for
EX = ccxt.binance({"enableRateLimit": True})
SYM = {"BTC": "BTC/USDT", "ETH": "ETH/USDT"}
START = "2020-06-01" # warmup per EMA200/ATR; il report usa 2021+
YEARS = [2021, 2022, 2023, 2024, 2025, 2026]
def fetch(asset, tf="15m"):
start_ms = int(pd.Timestamp(START, tz="UTC").timestamp() * 1000)
end_ms = int(pd.Timestamp("2026-05-26", tz="UTC").timestamp() * 1000)
tf_ms = 15 * 60 * 1000
rows = []
since = start_ms
while since <= end_ms:
r = EX.fetch_ohlcv(SYM[asset], tf, since=since, limit=1000)
if not r:
break
rows += r
nxt = int(r[-1][0]) + tf_ms
if nxt <= since:
break
since = nxt
df = pd.DataFrame(rows, columns=["timestamp", "open", "high", "low", "close", "volume"])
df = df.drop_duplicates("timestamp").sort_values("timestamp").reset_index(drop=True)
return df[df["timestamp"] <= end_ms]
def yearly(rows_by_year_ret, ts, trades, pos=0.15):
# per-anno compound
yr = {y: 1000.0 for y in YEARS}
# ricostruisco compound per anno separato (reset capitale ogni anno per ret% annuo)
by = {y: [] for y in YEARS}
for i, j, r in trades:
y = ts.iloc[i].year
if y in by:
by[y].append(r)
out = {}
for y in YEARS:
cap = 1000.0
for r in by[y]:
cap = max(cap + cap * pos * r, 10.0)
out[y] = (cap / 1000 - 1) * 100
return out
def full_oos(ts, trades, pos=0.15, split_date="2024-10-12"):
sd = pd.Timestamp(split_date, tz="UTC")
def comp(sub):
cap = 1000.0; rets = []
for i, j, r in sub:
cap = max(cap + cap * pos * r, 10.0); rets.append(r * pos)
return cap, rets
capF, rF = comp(trades)
oos = [(i, j, r) for i, j, r in trades if ts.iloc[i] >= sd]
capO, rO = comp(oos)
shF = float(np.mean(rF) / np.std(rF) * np.sqrt(len(rF))) if len(rF) > 1 and np.std(rF) > 0 else 0.0
shO = float(np.mean(rO) / np.std(rO) * np.sqrt(len(rO))) if len(rO) > 1 and np.std(rO) > 0 else 0.0
return (capF / 1000 - 1) * 100, shF, (capO / 1000 - 1) * 100, shO
def main():
print(f"Fetch Binance 15m (da {START})...\n")
data = {a: fetch(a) for a in ("BTC", "ETH")}
print("=" * 92)
print(" FADE su PURO Binance spot 15m | RET% per anno (pos 0.15, leva 3x, trend 3.0)")
print("=" * 92)
print(f" {'sleeve':<12s}" + "".join(f"{y:>9d}" for y in YEARS) + " | FULL% Shrp | OOS% Shrp")
print(" " + "-" * 88)
for asset in ("BTC", "ETH"):
df = data[asset].copy()
df = df[pd.to_datetime(df["timestamp"], unit="ms", utc=True).dt.year >= 2021].reset_index(drop=True) \
if False else df # tengo il warmup, filtro nei trade
ts = pd.to_datetime(df["timestamp"], unit="ms", utc=True)
for code in ("MR01", "MR02", "MR07"):
fn, params = strats_for(asset)[code]
trades = build_trades(fn(df, **params), df, trend_max=3.0)
trades = [(i, j, r) for i, j, r in trades if ts.iloc[i].year >= 2021]
yr = yearly(None, ts, trades)
fF, shF, fO, shO = full_oos(ts, trades)
print(f" {code+'_'+asset:<12s}" + "".join(f"{yr[y]:>+9.0f}" for y in YEARS) +
f" | {fF:>+8.0f} {shF:>5.2f} | {fO:>+6.0f} {shO:>5.2f}")
if __name__ == "__main__":
main()
+77
View File
@@ -0,0 +1,77 @@
"""PROBE CERBERO MCP — quali exchange/fonti serve davvero? (cerca IBKR & alt)
Non si fida del commento nel codice: interroga il server v2 (/mcp/tools/get_historical
con `exchange=...`) su una matrice di nomi exchange + naming strumento, e riporta chi
risponde con candele vere. Cerca in particolare IBKR e Alpaca (spot US reale).
uv run python scripts/analysis/cerbero_probe.py
"""
from __future__ import annotations
import sys
from pathlib import Path
PROJECT_ROOT = Path(__file__).resolve().parents[2]
sys.path.insert(0, str(PROJECT_ROOT))
import requests
from src.live.cerbero_client import CerberoClient, is_mainnet
C = CerberoClient()
START, END, INTERVAL = "2026-05-20", "2026-05-27", "1h"
# exchange -> naming strumento BTC da provare (varianti)
EXCHANGES = {
"deribit": ["BTC-PERPETUAL"],
"hyperliquid": ["BTC"],
"bybit": ["BTCUSDT", "BTC-PERPETUAL", "BTCUSD"],
"alpaca": ["BTC/USD", "BTCUSD", "BTC/USDT", "BTC"],
"ibkr": ["BTC", "BTC.USD", "BTCUSD"],
"interactivebrokers": ["BTC", "BTCUSD"],
"binance": ["BTCUSDT", "BTC/USDT", "BTC-PERPETUAL"],
"coinbase": ["BTC-USD", "BTC/USD", "BTCUSD"],
"kraken": ["XBTUSD", "BTC/USD", "BTCUSD"],
"okx": ["BTC-USDT", "BTC-USD-SWAP"],
}
def try_v2(exchange: str, instrument: str) -> str:
try:
candles = C.get_historical_v2(instrument, START, END, INTERVAL, exchange=exchange)
if candles:
c0, c1 = candles[0], candles[-1]
return f"OK {len(candles):>4} candele close {c1.get('close')}"
return "vuoto (0 candele)"
except requests.HTTPError as e:
code = e.response.status_code if e.response is not None else "?"
return f"HTTP {code}"
except Exception as e:
return f"{type(e).__name__}: {str(e)[:50]}"
def list_tools() -> None:
"""Tenta di enumerare i tool/endpoint del server (best-effort)."""
for path in ("/mcp/tools", "/mcp/tools/list", "/tools", "/mcp"):
try:
r = requests.post(f"{C.base_url}{path}", headers=C._headers(), json={}, timeout=10)
print(f" POST {path:<18} -> HTTP {r.status_code} {str(r.text)[:200]}")
except Exception as e:
print(f" POST {path:<18} -> {type(e).__name__}: {str(e)[:60]}")
def main():
print("=" * 80)
print(f" PROBE CERBERO MCP @ {C.base_url} (mainnet={is_mainnet()})")
print("=" * 80)
print("\n[1] Enumerazione endpoint/tool (best-effort):")
list_tools()
print(f"\n[2] get_historical_v2 BTC {INTERVAL} {START}->{END} per exchange:")
print(f" {'exchange':<20s}{'instrument':<16s}esito")
print(" " + "-" * 70)
for ex, syms in EXCHANGES.items():
for sym in syms:
res = try_v2(ex, sym)
print(f" {ex:<20s}{sym:<16s}{res}")
if res.startswith("OK"):
break # trovato il naming giusto, basta
if __name__ == "__main__":
main()
+84
View File
@@ -0,0 +1,84 @@
"""RI-ESECUZIONE FADE sul feed PULITO (data/raw ricostruito da Deribit mainnet, 2026-06-19).
Dopo il rebuild (scripts/analysis/rebuild_history.py) i parquet canonici in data/raw
sono storia Deribit mainnet reale (ccxt pubblico), certificata vs Coinbase USD. Qui giro
le 6 fade (MR01/MR02/MR07 x BTC/ETH) con l'ENGINE CANONICO (risk_management.build_trades,
strats_for) sul feed pulito, su ENTRAMBI i timeframe:
- 1h = config dei claim storici "validati OOS" (CLAUDE.md: MR01 BTC +201% / ETH +1238%)
- 15m = config LIVE attuale (swap 1h->15m, v1.1.30)
Stessi parametri del live: pos 0.15, leva 3x, trend_max 3.0, fee 0.10% RT. OOS = ultimo 30%
per indice (convenzione OOS_FRAC del progetto). Read-only, nessuna scrittura.
uv run python scripts/analysis/clean_fade_rerun.py
"""
from __future__ import annotations
import sys
from pathlib import Path
PROJECT_ROOT = Path(__file__).resolve().parents[2]
sys.path.insert(0, str(PROJECT_ROOT))
import numpy as np
import pandas as pd
from src.data.downloader import load_data
from scripts.analysis.risk_management import strats_for, build_trades, POS, LEV, OOS_FRAC
TFS = ["1h", "15m"]
YEARS = list(range(2018, 2027))
def metrics(ts, trades, split_idx, pos=POS):
"""trades = [(i, j, r_netto)]. Ritorna (per-anno%, FULL%, FULL Sharpe, OOS%, OOS Sharpe)."""
by = {y: 0.0 for y in YEARS}
capF = capO = 1000.0
rF, rO = [], []
for i, j, r in trades:
y = ts.iloc[i].year
if y in by:
by[y] += r * pos * 1000.0 # contributo lineare per la riga annuale
capF = max(capF + capF * pos * r, 10.0)
rF.append(r * pos)
if i >= split_idx:
capO = max(capO + capO * pos * r, 10.0)
rO.append(r * pos)
yr = {y: by[y] / 1000.0 * 100 for y in YEARS}
shF = float(np.mean(rF) / np.std(rF) * np.sqrt(len(rF))) if len(rF) > 1 and np.std(rF) > 0 else 0.0
shO = float(np.mean(rO) / np.std(rO) * np.sqrt(len(rO))) if len(rO) > 1 and np.std(rO) > 0 else 0.0
return yr, (capF / 1000 - 1) * 100, shF, (capO / 1000 - 1) * 100, shO
def main():
years_present = set()
results = {}
for tf in TFS:
for asset in ("BTC", "ETH"):
df = load_data(asset, tf)
ts = pd.to_datetime(df["timestamp"], unit="ms", utc=True)
years_present |= set(ts.dt.year.unique().tolist())
split_idx = int(len(df) * (1 - OOS_FRAC))
cov = f"{ts.iloc[0].date()} -> {ts.iloc[-1].date()} ({len(df)} barre, OOS da {ts.iloc[split_idx].date()})"
for code in ("MR01", "MR02", "MR07"):
fn, params = strats_for(asset)[code]
trades = build_trades(fn(df, **params), df, trend_max=3.0)
results[(tf, asset, code)] = (metrics(ts, trades, split_idx), len(trades), cov)
years = [y for y in YEARS if y in years_present]
for tf in TFS:
print("\n" + "=" * (62 + 9 * len(years)))
print(f" FADE su FEED PULITO (Deribit mainnet) — {tf} | pos {POS}, leva {LEV:.0f}x, trend 3.0, fee 0.10% RT")
# mostra la copertura una volta per asset
for asset in ("BTC", "ETH"):
print(f" {asset}: {results[(tf, asset, 'MR01')][2]}")
print("=" * (62 + 9 * len(years)))
print(f" {'sleeve':<11s}" + "".join(f"{y:>9d}" for y in years) +
f"{'Trd':>7s}{'FULL%':>9s}{'Shrp':>7s}{'OOS%':>8s}{'Shrp':>7s}")
print(" " + "-" * (60 + 9 * len(years)))
for asset in ("BTC", "ETH"):
for code in ("MR01", "MR02", "MR07"):
(yr, fF, shF, fO, shO), ntr, _ = results[(tf, asset, code)]
print(f" {code+'_'+asset:<11s}" + "".join(f"{yr[y]:>+9.0f}" for y in years) +
f"{ntr:>7d}{fF:>+9.0f}{shF:>7.2f}{fO:>+8.0f}{shO:>7.2f}")
print()
if __name__ == "__main__":
main()
+274
View File
@@ -0,0 +1,274 @@
"""CLEAN FEED — ripara gli spike-print del feed Deribit/Cerbero coi dati reali di Binance.
Motivo (2026-06-18): la ricerca Price Ladder ha rivelato che data/raw/btc_1h.parquet (e gli
altri TF/asset) contengono barre con WICK FASULLI (es. BTC 2024-02-13: low 38.580 con
close ~49.968, BTC reale ~50k) — lo stesso spike-print testnet documentato in CLAUDE.md
(TP_PHANTOM / feed congelato). Sono pochi (decine per file) ma avvelenano i backtest
(stop/entry su prezzi mai avvenuti) e gonfiano le code (la "FULL DD BTC ~54%" del ladder era
in gran parte questo).
Metodo (conservativo, fonte di verita' = Binance spot via ccxt, gia' cablato nel progetto):
1. DETECT: barra sospetta = high/low che sfora >15% il cluster di close locale [i-1,i,i+1]
(close sano + wick fasullo). Soglia larga: tanto e' Binance ad arbitrare.
2. ARBITRA: per ogni sospetta, scarica la barra Binance reale (BTC/USDT, ETH/USDT) allo
stesso tf/timestamp. Sostituisce O/H/L/C SOLO se Binance dissente materialmente (>2% su
high o low) -> un wick VERO confermato da Binance resta intatto. Volume/timestamp invariati.
3. BACKUP (data/_feed_backup/) + scrittura atomica + VALIDAZIONE (re-scan = 0 sospette,
n righe invariato). Log dettagliato di ogni barra riparata (old OHLC -> new).
uv run python scripts/analysis/clean_feed.py [ASSET_TF ...] # default: tutti BTC/ETH x TF
uv run python scripts/analysis/clean_feed.py BTC_1h # un solo file
"""
from __future__ import annotations
import shutil
import sys
import time
from pathlib import Path
import numpy as np
import pandas as pd
PROJECT_ROOT = Path(__file__).resolve().parents[2]
sys.path.insert(0, str(PROJECT_ROOT))
from src.data.downloader import _parquet_path, DATA_DIR
BACKUP = PROJECT_ROOT / "data" / "_feed_backup"
SYMBOL = {"BTC": "BTC/USDT", "ETH": "ETH/USDT"}
WICK_THR = 0.15 # detect: wick oltre 15% il cluster di close locale
REPLACE_THR = 0.02 # arbitra: sostituisci solo se Binance dissente >2% su high/low
CLOSE_THR = 0.01 # close-aware: sostituisci la barra se il CLOSE Deribit dista >1% da Binance
TF_MS = {"5m": 5, "8m": 8, "13m": 13, "15m": 15, "19m": 19, "30m": 30, "1h": 60}
_EX = None
def _binance():
global _EX
if _EX is None:
import ccxt
_EX = ccxt.binance({"enableRateLimit": True})
return _EX
def suspect_mask(df: pd.DataFrame) -> np.ndarray:
c = df["close"].to_numpy(float); h = df["high"].to_numpy(float); l = df["low"].to_numpy(float)
cp = np.roll(c, 1); cp[0] = c[0]; cn = np.roll(c, -1); cn[-1] = c[-1]
locmax = np.maximum.reduce([c, cp, cn]); locmin = np.minimum.reduce([c, cp, cn])
return (h > locmax * (1 + WICK_THR)) | (l < locmin * (1 - WICK_THR))
def _binance_bar(symbol: str, tf: str, ts_ms: int):
"""OHLC reale Binance alla barra ts_ms (None se assente)."""
try:
rows = _binance().fetch_ohlcv(symbol, tf, since=ts_ms - 1, limit=3)
except Exception as e:
print(f" ! binance err: {type(e).__name__}: {str(e)[:80]}")
return None
for r in rows:
if int(r[0]) == ts_ms:
return float(r[1]), float(r[2]), float(r[3]), float(r[4])
return None
def clean_file(asset: str, tf: str) -> dict:
path = _parquet_path(asset, tf)
if not path.exists():
return {"file": f"{asset}_{tf}", "skip": "no-file"}
df = pd.read_parquet(path)
mask = suspect_mask(df)
idx = np.where(mask)[0]
n0 = len(df)
if len(idx) == 0:
return {"file": f"{asset}_{tf}", "suspect": 0, "repaired": 0, "kept_real": 0,
"missing_binance": 0, "rows_before": n0, "rows_after": n0,
"still_suspect": 0, "log": []}
repaired, kept, missing = 0, 0, 0
log = []
for i in idx:
ts = int(df.iloc[i]["timestamp"])
b = _binance_bar(SYMBOL[asset], tf, ts)
oh, ol = float(df.iloc[i]["high"]), float(df.iloc[i]["low"])
if b is None:
missing += 1
continue
bo, bh, bl, bc = b
if abs(oh - bh) / bh > REPLACE_THR or abs(ol - bl) / max(bl, 1e-9) > REPLACE_THR:
df.iat[i, df.columns.get_loc("open")] = bo
df.iat[i, df.columns.get_loc("high")] = bh
df.iat[i, df.columns.get_loc("low")] = bl
df.iat[i, df.columns.get_loc("close")] = bc
repaired += 1
ts_s = pd.to_datetime(ts, unit="ms", utc=True).strftime("%Y-%m-%d %H:%M")
log.append(f" {ts_s} H {oh:,.0f}->{bh:,.0f} L {ol:,.0f}->{bl:,.0f}")
else:
kept += 1 # Binance conferma il wick: barra reale, intatta
if repaired:
BACKUP.mkdir(parents=True, exist_ok=True)
shutil.copy2(path, BACKUP / f"{asset.lower()}_{tf}.parquet.bak")
tmp = path.with_suffix(".parquet.tmp")
df.to_parquet(tmp, index=False)
tmp.replace(path)
# validazione
df2 = pd.read_parquet(path)
still = int(suspect_mask(df2).sum())
return {"file": f"{asset}_{tf}", "suspect": len(idx), "repaired": repaired,
"kept_real": kept, "missing_binance": missing, "rows_before": n0,
"rows_after": len(df2), "still_suspect": still, "log": log}
def _binance_series(asset: str, tf: str, start_ms: int, end_ms: int) -> dict:
"""OHLC reale Binance per l'intero range -> dict ts_ms -> (o,h,l,c). Bulk paginato."""
ex = _binance()
tf_ms = TF_MS[tf] * 60 * 1000
out: dict[int, tuple] = {}
since = start_ms
while since <= end_ms:
try:
rows = ex.fetch_ohlcv(SYMBOL[asset], tf, since=since, limit=1000)
except Exception as e:
print(f" ! binance err: {type(e).__name__}: {str(e)[:80]}")
break
if not rows:
break
for r in rows:
out[int(r[0])] = (float(r[1]), float(r[2]), float(r[3]), float(r[4]))
nxt = int(rows[-1][0]) + tf_ms
if nxt <= since:
break
since = nxt
if len(rows) < 1000 and since > end_ms:
break
return out
def clean_file_close(asset: str, tf: str, thr: float = CLOSE_THR, backup_dir: Path | None = None) -> dict:
"""CLOSE-AWARE: sostituisce O/H/L/C con Binance per ogni barra il cui CLOSE Deribit
dista > thr da Binance (1% default). Cattura i print 'silenziosi' che il wick-check
>15% non vede (close fantasma su barra di range piccolo). Fonte di verita' = Binance
spot (il feed storico e' perp testnet -> inaffidabile; lo spot ~ mainnet via arbitraggio)."""
if tf not in TF_MS:
return {"file": f"{asset}_{tf}", "skip": "tf-non-binance"}
path = _parquet_path(asset, tf)
if not path.exists():
return {"file": f"{asset}_{tf}", "skip": "no-file"}
df = pd.read_parquet(path)
n0 = len(df)
tms = df["timestamp"].to_numpy("int64")
c = df["close"].to_numpy(float)
bz = _binance_series(asset, tf, int(tms[0]), int(tms[-1]))
col = {k: df.columns.get_loc(k) for k in ("open", "high", "low", "close")}
fixed, by_year, missing = 0, {}, 0
log = []
for i in range(n0):
b = bz.get(int(tms[i]))
if b is None:
missing += 1
continue
bo, bh, bl, bc = b
if bc <= 0:
continue
orig = float(c[i]) # cattura PRIMA della scrittura (to_numpy puo' essere una view)
if abs(orig - bc) / bc > thr:
df.iat[i, col["open"]] = bo
df.iat[i, col["high"]] = bh
df.iat[i, col["low"]] = bl
df.iat[i, col["close"]] = bc
fixed += 1
y = pd.to_datetime(int(tms[i]), unit="ms", utc=True).year
by_year[y] = by_year.get(y, 0) + 1
if len(log) < 10:
ts_s = pd.to_datetime(int(tms[i]), unit="ms", utc=True).strftime("%Y-%m-%d %H:%M")
log.append(f" {ts_s} C {orig:,.2f}->{bc:,.2f} ({abs(orig-bc)/bc*100:.1f}%)")
if fixed:
bdir = backup_dir or BACKUP
bdir.mkdir(parents=True, exist_ok=True)
shutil.copy2(path, bdir / f"{asset.lower()}_{tf}.parquet.bak")
tmp = path.with_suffix(".parquet.tmp")
df.to_parquet(tmp, index=False)
tmp.replace(path)
# validazione: ri-scan, 0 barre residue oltre soglia (fra quelle coperte da Binance)
df2 = pd.read_parquet(path)
c2 = df2["close"].to_numpy(float)
still = sum(1 for i in range(len(df2))
if (b := bz.get(int(tms[i]))) and b[3] > 0 and abs(c2[i] - b[3]) / b[3] > thr)
return {"file": f"{asset}_{tf}", "covered": n0 - missing, "fixed": fixed,
"missing_binance": missing, "rows_before": n0, "rows_after": len(df2),
"still_over_thr": still, "by_year": by_year, "log": log}
def main():
args = [a for a in sys.argv[1:] if not a.startswith("--")]
close_mode = "--close" in sys.argv
dry = "--dry" in sys.argv
if close_mode:
targets = args or [f"{a}_{tf}" for a in ("BTC", "ETH") for tf in ("5m", "15m", "1h")]
stamp = time.strftime("%Y%m%d-%H%M%S")
bdir = BACKUP / f"pre_close_clean_{stamp}"
print(f"CLEAN FEED (close-aware vs Binance, thr={CLOSE_THR*100:.0f}%) — "
f"{'DRY-RUN (nessuna scrittura)' if dry else f'backup in {bdir}'}\n")
grand = 0
for t in targets:
asset, tf = t.split("_", 1)
if dry:
# dry: conta soltanto, niente scrittura
r = _dry_close(asset, tf)
else:
r = clean_file_close(asset, tf, backup_dir=bdir)
if r.get("skip"):
print(f" {t:<9} SKIP ({r['skip']})"); continue
grand += r.get("fixed", 0)
yr = " ".join(f"{y}:{n}" for y, n in sorted(r.get("by_year", {}).items()))
print(f" {r['file']:<9} coperte={r.get('covered',0):>7} riparate={r.get('fixed',0):>4} "
f"no-binance={r.get('missing_binance',0):>5} | righe {r['rows_before']}=={r.get('rows_after',r['rows_before'])} "
f"residue>thr={r.get('still_over_thr','-')}")
if yr:
print(f" per anno: {yr}")
for line in r.get("log", []):
print(line)
print(f"\n TOTALE barre riparate (close-aware): {grand}")
return
targets = args or [f"{a}_{tf}" for a in ("BTC", "ETH") for tf in ("5m", "15m", "30m", "1h")]
print(f"CLEAN FEED — backup in {BACKUP}\n")
grand = 0
for t in targets:
asset, tf = t.split("_", 1)
r = clean_file(asset, tf)
if r.get("skip"):
print(f" {t:<9} SKIP ({r['skip']})"); continue
grand += r.get("repaired", 0)
print(f" {r['file']:<9} sospette={r['suspect']:>3} riparate={r['repaired']:>3} "
f"reali-tenute={r.get('kept_real',0):>3} no-binance={r.get('missing_binance',0):>2} "
f"| righe {r['rows_before']}=={r['rows_after']} residue-sospette={r['still_suspect']}")
for line in r.get("log", [])[:8]:
print(line)
if len(r.get("log", [])) > 8:
print(f" ... (+{len(r['log'])-8} altre)")
print(f"\n TOTALE barre riparate: {grand}")
def _dry_close(asset: str, tf: str, thr: float = CLOSE_THR) -> dict:
"""Conta soltanto quante barre verrebbero riparate (nessuna scrittura)."""
if tf not in TF_MS:
return {"file": f"{asset}_{tf}", "skip": "tf-non-binance"}
path = _parquet_path(asset, tf)
if not path.exists():
return {"file": f"{asset}_{tf}", "skip": "no-file"}
df = pd.read_parquet(path)
tms = df["timestamp"].to_numpy("int64"); c = df["close"].to_numpy(float)
bz = _binance_series(asset, tf, int(tms[0]), int(tms[-1]))
fixed, by_year, missing = 0, {}, 0
for i in range(len(df)):
b = bz.get(int(tms[i]))
if b is None:
missing += 1; continue
if b[3] > 0 and abs(c[i] - b[3]) / b[3] > thr:
fixed += 1
y = pd.to_datetime(int(tms[i]), unit="ms", utc=True).year
by_year[y] = by_year.get(y, 0) + 1
return {"file": f"{asset}_{tf}", "covered": len(df) - missing, "fixed": fixed,
"missing_binance": missing, "rows_before": len(df), "by_year": by_year, "log": []}
if __name__ == "__main__":
main()
@@ -40,9 +40,17 @@ ANN = 365.0 # giorni/anno per annualizzare
# ---------------- equity giornaliere ----------------
def fade_daily_equity(asset: str, fn, params) -> pd.Series:
"""Equity giornaliera di uno sleeve fade: trade 1h (filtro trend 3.0) -> equity -> daily."""
df = load_data(asset, "1h")
# SWAP fade 1h -> 15m (2026-06-12, scelta utente). Gate fade15m_port06_gate.py: parametri
# 1h NON ri-tunati trasferiti a 15m, corr 15m-1h media 0.26, SWAP promosso (FULL CAGR
# 74->101% DD 3.46->2.47%, OOS Sh 10.07->10.86; OOS DD 1.48->2.09 accettato), edge ETH
# regge il flat-entry-skip. Il canonico segue il deployato per tenere la parita' delle
# due facce. Diario docs/diary/2026-06-12-fade15m-gate.md.
FADE_TF = "15m"
def fade_daily_equity(asset: str, fn, params, tf: str = FADE_TF) -> pd.Series:
"""Equity giornaliera di uno sleeve fade: trade (filtro trend 3.0) -> equity -> daily."""
df = load_data(asset, tf)
ts = pd.to_datetime(df["timestamp"], unit="ms", utc=True)
trades = build_trades(fn(df, **params), df, trend_max=3.0)
n = len(df); eq = np.full(n, INIT, dtype=float); cap = INIT
@@ -55,7 +63,7 @@ def fade_daily_equity(asset: str, fn, params) -> pd.Series:
def build_all_sleeves() -> dict[str, pd.Series]:
sleeves: dict[str, pd.Series] = {}
# --- FADE: 8 sleeve ---
# --- FADE: 6 sleeve (15m dal 2026-06-12, vedi FADE_TF) ---
for asset in ["BTC", "ETH"]:
for nm, (fn, params) in strats_for(asset).items():
sleeves[f"{nm}_{asset}"] = fade_daily_equity(asset, fn, params)
@@ -0,0 +1,146 @@
"""PIANO STORICO DERIBIT — quanta storia copre davvero il venue dove ESEGUIAMO?
Obiettivo: scegliere la fonte migliore per ricostruire lo storico di backtest, dato
che si esegue su Deribit. Principio (gia' misurato in multi_source_check): l'ancora
giusta e' il VENUE DI ESECUZIONE, non Binance/USDT. Qui rispondo con i numeri a:
1. COPERTURA: da quando esiste OHLCV su Deribit MAINNET (ccxt pubblico, no token) per
gli strumenti che tradiamo — inverse (BTC/ETH-PERPETUAL) e lineari USDC.
2. TIMEFRAME nativi disponibili su Deribit.
3. FEDELTA' inverse-vs-lineare (stesso indice? -> posso usare l'inverse, storia lunga,
come price-series e i lineari recenti sono ridondanti per il PREZZO).
4. GAP pre-Deribit: quanto indietro vanno le strategie e cosa manca -> da gap-fillare
con Coinbase USD (spot, NON USDT).
Tutto via ccxt pubblico Deribit (= api.deribit.com mainnet, reale). Non modifica nulla.
uv run python scripts/analysis/deribit_history_plan.py
"""
from __future__ import annotations
import sys
from pathlib import Path
PROJECT_ROOT = Path(__file__).resolve().parents[2]
sys.path.insert(0, str(PROJECT_ROOT))
import numpy as np
import pandas as pd
import ccxt
DERIBIT = ccxt.deribit({"enableRateLimit": True})
COINBASE = ccxt.coinbase({"enableRateLimit": True})
def earliest(symbol: str, tf: str = "1d") -> tuple[str | None, int, str | None]:
"""Trova la prima candela disponibile (probe since 2016) + n candele totali stimate."""
since = int(pd.Timestamp("2016-01-01", tz="UTC").timestamp() * 1000)
try:
rows = DERIBIT.fetch_ohlcv(symbol, tf, since=since, limit=5000)
except Exception as e:
return None, 0, f"{type(e).__name__}: {str(e)[:60]}"
if not rows:
return None, 0, "no-data"
first = pd.to_datetime(int(rows[0][0]), unit="ms", utc=True)
last = pd.to_datetime(int(rows[-1][0]), unit="ms", utc=True)
return f"{first.date()} -> {last.date()}", len(rows), None
def list_perps() -> dict:
"""Risolve i simboli ccxt reali dei perp Deribit per BTC/ETH (inverse + lineari)."""
DERIBIT.load_markets()
found = {}
for sym, m in DERIBIT.markets.items():
if not m.get("swap"):
continue
base = m.get("base")
if base not in ("BTC", "ETH"):
continue
settle = m.get("settle")
kind = "inverse" if m.get("inverse") else "linear"
found[f"{base}-{kind}({settle})"] = sym
return found
def fetch_series(ex, symbol, tf, start, end, limit=1000):
start_ms = int(pd.Timestamp(start, tz="UTC").timestamp() * 1000)
end_ms = int(pd.Timestamp(end, tz="UTC").timestamp() * 1000)
tf_ms = ex.parse_timeframe(tf) * 1000
out, since = {}, start_ms
while since <= end_ms:
try:
rows = ex.fetch_ohlcv(symbol, tf, since=since, limit=limit)
except Exception:
break
if not rows:
break
for r in rows:
if start_ms <= int(r[0]) <= end_ms and r[4]:
out[int(r[0])] = float(r[4])
nxt = int(rows[-1][0]) + tf_ms
if nxt <= since:
break
since = nxt
if len(rows) < limit and since > end_ms:
break
return pd.Series(out)
def dev_bps(a: pd.Series, b: pd.Series) -> tuple[int, float, float, float]:
df = pd.concat([a.rename("a"), b.rename("b")], axis=1, join="inner")
if len(df) == 0:
return 0, 0, 0, 0
d = (df["a"] - df["b"]).abs() / df["b"] * 1e4
return len(df), float(d.median()), float(d.quantile(.95)), float(d.max())
def main():
print("=" * 84)
print(" PIANO STORICO DERIBIT MAINNET (ccxt pubblico, reale)")
print("=" * 84)
print("\n[1] Simboli perp Deribit BTC/ETH risolti:")
perps = list_perps()
for k, v in perps.items():
print(f" {k:<22s} -> {v}")
print("\n[2] COPERTURA storica (1d, probe da 2016):")
print(f" {'strumento':<22s}{'range disponibile':<28s}{'giorni':>8s}")
cov = {}
for k, sym in perps.items():
rng, n, err = earliest(sym, "1d")
cov[k] = (sym, rng, n)
print(f" {k:<22s}{(rng or err or '-'):<28s}{n:>8d}")
print("\n[3] TIMEFRAME nativi Deribit (test su BTC inverse, oggi):")
bsym = next((s for k, s in perps.items() if k.startswith("BTC-inverse")), "BTC/USD:BTC")
tfs = []
for tf in ("1m", "3m", "5m", "10m", "15m", "30m", "1h", "2h", "3h", "4h", "6h", "12h", "1d"):
try:
r = DERIBIT.fetch_ohlcv(bsym, tf, limit=3)
tfs.append(tf if r else f"{tf}:vuoto")
except Exception:
tfs.append(f"{tf}:NO")
print(f" ok: {[t for t in tfs if ':' not in t]}")
print(f" ko: {[t for t in tfs if ':' in t]}")
print("\n[4] FEDELTA' inverse-vs-lineare USDC (close 1h, ultimi ~40g):")
for base in ("BTC", "ETH"):
inv = next((s for k, s in perps.items() if k.startswith(f"{base}-inverse")), None)
lin = next((s for k, s in perps.items() if k.startswith(f"{base}-linear")), None)
if not inv or not lin:
print(f" {base}: manca inverse o lineare"); continue
a = fetch_series(DERIBIT, inv, "1h", "2026-04-15", "2026-05-27")
b = fetch_series(DERIBIT, lin, "1h", "2026-04-15", "2026-05-27")
n, med, p95, mx = dev_bps(a, b)
print(f" {base}: barre={n} inverse-vs-lineare med {med:.1f} bps p95 {p95:.1f} max {mx:.1f}")
print("\n[5] GAP pre-Deribit: Deribit inverse vs Coinbase USD su finestra PROFONDA (2020-06, 1d):")
for base in ("BTC", "ETH"):
inv = next((s for k, s in perps.items() if k.startswith(f"{base}-inverse")), None)
a = fetch_series(DERIBIT, inv, "1d", "2020-06-01", "2020-09-01")
b = fetch_series(COINBASE, f"{base}/USD", "1d", "2020-06-01", "2020-09-01", limit=300)
n, med, p95, mx = dev_bps(a, b)
cov_first = cov.get(f"{base}-inverse(BTC)" if base == "BTC" else f"{base}-inverse(ETH)", (None, "?", 0))[1]
print(f" {base}: Deribit-vs-Coinbase barre={n} med {med:.1f} bps p95 {p95:.1f} max {mx:.1f}")
if __name__ == "__main__":
main()

Some files were not shown because too many files have changed in this diff Show More