> ## Documentation Index
> Fetch the complete documentation index at: https://mathematicalcompany.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# Oracle

> Ensemble probability forecasting from 6 signal sources. Surface markets where your model sees edge vs market price.

<Warning>
  **Ultra Feature.** Requires an Ultra subscription. [Get started at api.mathematicalcompany.com](https://api.mathematicalcompany.com)
</Warning>

# Oracle

Combines six independent signal extractors into a single ensemble probability estimate for each market, then surfaces edge opportunities where the forecast diverges materially from the current market price.

<CardGroup cols={3}>
  <Card title="Smart Money Flow" icon="wallet">
    Holder analysis weighted by wallet score.
  </Card>

  <Card title="Microstructure" icon="microscope">
    Kyle's lambda + VPIN for informed trading detection.
  </Card>

  <Card title="Momentum" icon="arrow-trend-up">
    EMA crossover (short/long span ratio).
  </Card>

  <Card title="Volume Profile" icon="chart-bar">
    Buy vs sell volume imbalance.
  </Card>

  <Card title="Holder Concentration" icon="users">
    HHI of top holders as conviction signal.
  </Card>

  <Card title="Temporal Patterns" icon="clock">
    Hour-of-day buy activity patterns.
  </Card>
</CardGroup>

***

## Forecast a Market

```python theme={null}
import horizon as hz

fc = hz.forecast_market(
    "0xcondition...",
    market_title="Will X happen?",
    market_price=0.65,
)
print(f"Ensemble: {fc.ensemble_prob:.4f}")
print(f"Edge: {fc.edge_bps:.0f} bps")
for s in fc.signals:
    print(f"  {s.name}: {s.normalized_value:.4f} (weight={s.weight:.2f})")
```

***

## Scan for Edges

```python theme={null}
edges = hz.scan_edges(min_edge_bps=300, max_markets=30)
for e in edges:
    print(f"{e.market_title}: {e.direction} | edge={e.edge_bps:.0f}bps | size=${e.recommended_size:.0f}")
```

***

## Pipeline Mode

```python theme={null}
hz.run(
    name="oracle-mm",
    markets=["0xcondition..."],
    pipeline=[
        hz.oracle(forecast_interval_cycles=20),
        model,   # reads ctx.params["oracle_edge_bps"]
        quoter,
    ],
    interval=5.0,
)
```

Injects `ctx.params["oracle_forecast"]` and `ctx.params["oracle_edge_bps"]` every N cycles.

***

## Full Report

```python theme={null}
report = hz.oracle_report(max_markets=20)
print(f"Coverage: {report.coverage} markets")
print(f"Avg confidence: {report.avg_confidence:.4f}")
print(f"Calibration (log loss): {report.model_calibration:.4f}")
for edge in report.top_edges:
    print(f"  {edge.market_title}: {edge.edge_bps:.0f}bps ({edge.direction})")
```

***

## Signal Weights

Default weights (configurable via `OracleConfig`):

| Signal                 | Weight | Source                                       |
| ---------------------- | ------ | -------------------------------------------- |
| `smart_money_flow`     | 0.25   | `get_top_holders()` + `score_wallet()`       |
| `microstructure`       | 0.20   | `get_market_trades()` + Kyle's lambda + VPIN |
| `momentum`             | 0.15   | EMA crossover on trade prices                |
| `volume_profile`       | 0.15   | Buy/sell volume ratio                        |
| `holder_concentration` | 0.15   | HHI of top holders                           |
| `temporal_pattern`     | 0.10   | Hour-of-day activity analysis                |

***

## OracleConfig

| Parameter              | Default   | Description                           |
| ---------------------- | --------- | ------------------------------------- |
| `signal_weights`       | See above | Weight per signal in ensemble         |
| `min_confidence`       | `0.3`     | Minimum confidence to report forecast |
| `edge_threshold_bps`   | `200.0`   | Minimum edge to flag as opportunity   |
| `recalibrate_interval` | `50`      | Cycles between recalibration          |
| `holder_limit`         | `50`      | Max holders to fetch per market       |
| `trade_limit`          | `200`     | Max trades to fetch per market        |
