feat(Notebooks): Implement the four use-case notebooks from #34 - #35
Closed
szemyd wants to merge 4 commits into
Closed
feat(Notebooks): Implement the four use-case notebooks from #34#35szemyd wants to merge 4 commits into
szemyd wants to merge 4 commits into
Conversation
Author percent-format .py notebooks implementing the outline specs in #34: - backtest-slippage: builds a half-spread + impact cost model from l1_price, impact and slippage metrics, validates it against measured slippage_bps_mean, and compares zero / flat / dynamic-cost momentum backtests. - backtest-funding: isolates realised-funding PnL by accruing funding at its discrete prints and comparing price-only, price+funding and price+funding+cost backtests; adds a fade-funding diagnostic. - execution-liquidity-timing: spread/depth/toxicity seasonality across the tier-3 L2 datasets, a transparent liquidity score, and best/uniform/worst hour execution schedules priced with the slippage cost model. - risk-positioning: a trailing rolling-percentile crowding score from funding, basis and open-interest change, with a decile event study and an in-window threshold calibration table. All four run end-to-end on the DEMO-KEY preview slice (Binance BTC perpetuals, 5-minute, May 2025), reuse the intro-notebook theme/helpers and the shared run_position_backtest, resolve the key via ... -> APERIODIC_API_KEY -> DEMO-KEY, label one-month statistics as illustrative, and never call load_dotenv or print secrets. .ipynb and HTML are left for CI to generate. Also mark the four notebooks as preview-data in preview-notebooks.json and list them in the README. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HVxnJZYNRifP6pgJ5D13bz
…display from real-data review Reviewing the CI-executed notebooks against real May 2025 data surfaced three issues fixed here: - backtest-funding: the reported funding_rate updates on (nearly) every 5-minute bar, so change-detection was counting thousands of "prints" and inflating a constant long's realised funding to ~-29% for the month. Accrue funding only at the Binance 8-hour settlement schedule (00:00/08:00/16:00 UTC, with a change-detection fallback), which restores a realistic ~-1% and correct per-strategy funding contributions. - execution-liquidity-timing: rank the best/uniform/worst schedules by the spread-plus-impact cost model (what the desk minimises) instead of the holistic liquidity score, so the cheapest hours are genuinely cheapest; on BTC the score and the cost model diverge, which is now framed explicitly and is the subject of Chart 4. Also fold the fetched L2 imbalance into the Chart 3 adverse-move diagnostic (previously fetched but unused). - backtest-slippage: report the impact coefficient per $1M notional so it no longer rounds to 0.0000 next to a non-zero modelled cost. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HVxnJZYNRifP6pgJ5D13bz
This was referenced Jul 14, 2026
Contributor
Author
|
Superseded — split into one PR per notebook as requested:
Each carries the same notebook source that ran green here (executed end-to-end against real May 2025 data via CI, with Generated by Claude Code |
szemyd
added a commit
that referenced
this pull request
Jul 28, 2026
## Summary Adds `notebooks/backtest-slippage.py`, implementing the **backtest-slippage** outline from #34 (use case: *Improve your backtest*). Builds a **microstructure** transaction-cost model — half-spread plus market impact — from Aperiodic's `l1_price`, `impact` and `slippage` metrics, and shows how different cost assumptions reshape a simple momentum backtest. - Binance BTC perpetuals, 5-minute, May 2025 preview slice; runs end-to-end on `DEMO-KEY`. - **Fees are excluded by design** and disclaimed prominently (a Binance taker fee ~5 bps one-way is cited as the dominant real cost); the flat benchmark is a comparable ~1 bps so the equity chart stays readable. - Section 6 **checks the impact model against measured per-trade `slippage_bps_mean` at the actual average trade size** (`volume_notional / taker trade count`). The result is reported straight: the model **under-predicts** measured slippage by roughly an **order of magnitude** at the average trade size, with **~zero per-bar correlation** — `impact_per_notional` (net-flow-based) is an order-of-magnitude proxy, not a per-trade predictor. The notebook prints the notional at which the model mean would equal measured slippage to make the size dependence explicit. - Reuses the intro-notebook theme/helpers and the shared `run_position_backtest`. `.ipynb` and HTML are generated by CI. Adds one README row and one `preview-notebooks.json` slug (also touched by the sibling notebook PRs, so whichever merges last needs a trivial rebase). Part of splitting #35 into one PR per notebook. Implements #34. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --------- Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
szemyd
added a commit
that referenced
this pull request
Jul 28, 2026
## Summary Adds `notebooks/backtest-funding.py`, implementing the **backtest-funding** outline from #34 (use case: *Improve your backtest*). Isolates how **realised** funding changes strategy PnL and shows where it binds. - Binance BTC perpetuals, 5-minute, May 2025 preview slice; runs end-to-end on `DEMO-KEY`. - Funding is accrued at the Binance **8-hour settlements** to the **position held into** each settlement, priced at the last rate observed before it (per the catalogue's "last rate in interval" feed) — not smeared across 5-minute bars. A cadence cross-check prints (settlements ~8 h apart; the first in-window settlement has no pre-window rate and is excluded, so detected = expected − 1). - The headline comparison is **price-only vs price + funding** on two positions: a **constant long** (funding binds — ~−0.43%/month on a +10.9% buy-and-hold) and a **1h momentum** signal (direction-neutral, funding nets out). Turnover costs are delegated to `backtest-slippage.py`. - The fade-funding diagnostic is backtested **with its own funding leg** (price-only vs price + funding — the gap is the carry), noting the position is ~constantly short this month. - Reuses the shared `run_position_backtest`. `.ipynb` and HTML are generated by CI. Adds one README row and one `preview-notebooks.json` slug (sibling PRs touch these too — whichever merges last needs a trivial rebase). Part of splitting #35 into one PR per notebook. Implements #34. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --------- Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
szemyd
added a commit
that referenced
this pull request
Jul 28, 2026
…38) ## Summary Adds `notebooks/execution-liquidity-timing.py`, implementing the **execution-liquidity-timing** outline from #34 (use case: *Execute smarter*). Measures spread / depth / **|toxicity|** seasonality across the tier-3 multi-level **L2** datasets and tests a time-of-day execution schedule **out-of-sample**. - Binance BTC perpetuals, 5-minute, May 2025 preview slice; runs end-to-end on `DEMO-KEY` (tier-3 L2 is in the preview slice; full L2 history needs Prime). - Hours are **calibrated on the first 15 days and evaluated on the held-out remainder**, ranked on the robust **median** cost (the distribution is heavy-tailed), with per-hour IQR bars, rank-persistence, and validation against **measured** slippage. In this month the hour ranking **does not persist** (Spearman −0.07) and the eval medians show no separation — so the notebook demonstrates the *method* and reports the honest one-month verdict, rather than the by-construction monotonicity a same-window ranking would produce. - `flow_toxicity_score` is signed (catalogue), so `|toxicity|` is used throughout; depth is in BTC with `ORDER_NOTIONAL` ≈ 2.2% of level-20 dollar depth; Chart 4 shows why the cheapest hours are not always the safest. `.ipynb` and HTML are generated by CI. Adds one README row and one `preview-notebooks.json` slug (sibling PRs touch these too — whichever merges last needs a trivial rebase). Part of splitting #35 into one PR per notebook. Implements #34. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --------- Co-authored-by: Claude <noreply@anthropic.com> Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Implements the four outline specifications from #34 as polished, preview-runnable
percent-format
.pynotebooks. Each analyses Binance BTC perpetuals(
perpetual-BTC-USDT:USDT) at 5-minute resolution over May 2025 — thewindow served by the shared
DEMO-KEYpreview slice — and every one-monthstatistic is labelled illustrative.
backtest-slippagel1_price,impactandslippage, validates it against measuredslippage_bps_mean, and compares zero / flat / dynamic-cost momentum backtests.backtest-fundingexecution-liquidity-timingrisk-positioningHow the specs were met
.py, jupytext-synced;.ipynbandhtml/are left for CI to generate (no hand-edited notebooks or committed exports)."..."→APERIODIC_API_KEY→"DEMO-KEY";USE_PREVIEW = API_KEY == "DEMO-KEY". Noload_dotenv, no printed secrets, no UUID-shaped example keys.api_key,preview,timestamp,interval,exchange,symbol,start_date,end_date,output="pandas",show_progress=False).rcParams,clip_window,format_time_axis, the sharedrun_position_backtest(5-minute annualisation) and the alpha-discovery rolling-rank transform; uppercase config constants; numbered## Chart N —sections,## Takeaways,## Further reading.notebooks/preview-notebooks.jsonand listed in the README.Validation
nbconvert(the same step CI runs) against a synthetic stand-in for theaperiodicSDK using the exact spec column names, since the live endpoint is not reachable from the authoring sandbox. All four run clean with sensible outputs (cost curves rise with order size; funding sign is correct; the scheduler ranks hours; crowding deciles order forward drawdowns).ruff format ./ruff check .clean; jupytextpy → ipynb → pyround-trip is stable.Implements #34.
🤖 Generated with Claude Code
https://claude.ai/code/session_01HVxnJZYNRifP6pgJ5D13bz
Generated by Claude Code