Files
vault-dash/docs/BT-002_HISTORICAL_OPTIONS_SNAPSHOT_PROVIDER.md
2026-03-27 18:31:28 +01:00

2.5 KiB

BT-002 Historical Options Snapshot Provider

What shipped

BT-002 adds a point-in-time historical options snapshot provider for backtests.

The new provider lives in app/services/backtesting/historical_provider.py and plugs into the same BacktestService / engine flow as the existing synthetic provider.

Provider contract

The snapshot provider exposes the same backtest-facing behaviors as the synthetic provider:

  • load underlying daily closes for the scenario window
  • validate ProviderRef
  • open positions at scenario start using only the entry-day snapshot
  • mark open positions later using the exact same contract identity

This lets backtests swap:

  • synthetic pricing: synthetic_v1 / synthetic_bs_mid
  • observed snapshot pricing: daily_snapshots_v1 / snapshot_mid

Contract-selection rules

The provider uses explicit, deterministic, point-in-time rules:

  1. filter to the entry-day option chain only
  2. keep contracts with expiry at or beyond the target expiry date
  3. choose the nearest eligible expiry
  4. within that expiry, choose the nearest strike to the target strike
  5. on equal-distance strike ties:
    • puts prefer the higher strike
    • calls prefer the lower strike

These rules avoid lookahead bias because later snapshots are not consulted for entry selection.

Daily mark-to-market rules

After entry, the provider marks positions using the exact same contract_key.

It does not silently substitute a different strike or expiry when the original contract is missing.

Current fallback policy:

  1. use the exact same contract from the same-day snapshot
  2. if missing before expiry, carry forward the previous mark for that same contract and emit a warning
  3. if the valuation date is at or after expiry, settle to intrinsic value and close the position

Data-quality tradeoffs

The current BT-002 slice intentionally keeps the data model simple:

  • snapshots are assumed to provide a precomputed daily mid
  • the provider does not currently derive mids from bid/ask pairs
  • missing exact-contract marks are explicit warnings, not silent substitutions
  • the engine currently still supports continuous_units sizing for snapshot-backed runs

Known limitations / follow-up

This slice does not yet include:

  • file-backed or external ingestion of real historical snapshot datasets
  • listed-contract rounding / contract-size-aware position sizing
  • persistent run-status objects beyond template-level warnings

Those follow-ups should remain explicit roadmap work rather than being implied by BT-002.