Dashboards¶
ProgridPy includes a Streamlit-based interactive dashboard and an HTML export feature for sharing metrics reports. Both are built on the MetricsPlots visualization layer which produces Plotly figures.
Streamlit Dashboard¶
Launching the Dashboard¶
from progridpy.metrics import MetricsEngine, StreamlitDashboard
engine = MetricsEngine(iso_name="MISO", df_iso=trade_df)
dashboard = StreamlitDashboard(engine=engine)
dashboard.render()
Run the script with Streamlit:
Dashboard Layout¶
The render() method produces a full-page Streamlit application with the following sections:
| Section | Content |
|---|---|
| Title | ISO name and date range |
| KPI Cards | Cumulative PnL, Last Day Gain, Estimated Risk, Max Drawdown |
| Performance Chart | 3-pane interactive chart: cumulative gains, drawdowns, daily gains |
| Supply/Demand Toggle | Checkboxes to show total, supply, and demand curves independently |
| Histograms | Tabbed view: Daily, 30d, and 365d gain distributions |
| Performance Summary | Table comparing YTD vs. Historical metrics |
| Detailed Metrics | Full metrics table with Amount and Ratio columns |
| Calendar Year Gains | Annual cumulative gains overlay chart |
| Heatmaps | GitHub-style daily gains heatmap across all years |
Custom Time Frames¶
By default, the dashboard shows three columns: Overall, YTD, and Historical. You can override this with custom TimeFrameRange objects:
from datetime import date
from progridpy.metrics import MetricsEngine, StreamlitDashboard, TimeFrameRange
engine = MetricsEngine(iso_name="SPP", df_iso=trade_df)
dashboard = StreamlitDashboard(
engine=engine,
time_frames=[
TimeFrameRange(label="H1 2025", start_date=date(2025, 1, 1), end_date=date(2025, 6, 30)),
TimeFrameRange(label="H2 2025", start_date=date(2025, 7, 1), end_date=date(2025, 12, 31)),
TimeFrameRange(label="Q1 2026", start_date=date(2026, 1, 1), end_date=date(2026, 3, 31)),
],
)
dashboard.render()
Time frame limits
You can provide between 1 and 3 TimeFrameRange objects. The constructor raises ValueError if the count is outside this range.
Adding a Description¶
Pass a description string to display explanatory text at the top of the dashboard:
dashboard = StreamlitDashboard(
engine=engine,
description="MISO Day-Ahead Virtual Trading Backtest -- Full Node Universe",
)
dashboard.render()
HTML Export¶
Export the dashboard to a standalone HTML file that can be opened in any browser. All Plotly charts remain fully interactive (hover, zoom, pan) with Plotly.js embedded in the file.
from progridpy.metrics import MetricsEngine, StreamlitDashboard
engine = MetricsEngine(iso_name="MISO", df_iso=trade_df)
dashboard = StreamlitDashboard(engine=engine)
dashboard.export_html("trading_report.html")
The exported HTML includes:
- Title with ISO name and date range
- KPI summary cards
- Performance chart (cumulative gains, drawdowns, daily gains)
- Gain distribution histograms
- Detailed metrics table
- Calendar year gains chart
- Daily gains heatmap
Command-Line Export¶
Use the provided scripts for command-line export:
# MISO dashboard
python scripts/miso/dashboard.py -t ./trades -p ./processed --export report.html
# Or launch interactively
streamlit run scripts/miso/dashboard.py -- -t ./trades -p ./processed
MetricsPlots¶
For programmatic access to individual charts, use the MetricsPlots class directly through the engine's plots property:
from progridpy.metrics import MetricsEngine
engine = MetricsEngine(iso_name="MISO", df_iso=trade_df)
engine.compute()
plots = engine.plots
Available Charts¶
Performance Chart¶
A 3-pane chart with shared x-axis showing cumulative gains, drawdowns, and daily gains:
fig = plots.performance_chart(
show_total=True, # Total cumulative gains line
show_supply=True, # Supply-only cumulative gains
show_demand=True, # Demand-only cumulative gains
)
fig.show()
When a single series is selected (e.g., supply only), the drawdown and daily gains panes update to reflect that specific series.
Gains Histogram¶
Distribution histogram with KDE overlay, per-year breakdown, mean/median lines, and percentile markers (P1, P5, P10, P25, P75, P90, P95, P99):
fig = plots.gains_histogram("daily") # Daily gains distribution
fig = plots.gains_histogram("7d") # 7-day rolling gains
fig = plots.gains_histogram("30d") # 30-day rolling gains
fig = plots.gains_histogram("90d") # 90-day rolling gains
fig = plots.gains_histogram("365d") # 365-day rolling gains
Overlay actual trading data for comparison:
Cumulative Gains by Year¶
Annual cumulative gains overlay -- each year is a separate colored line normalized to start at 0 on day 1:
Daily Gains Bar Chart¶
Recent daily gains as green/red bars:
fig = plots.daily_gains_bar_chart(30) # Last 30 days
fig = plots.daily_gains_bar_chart(90) # Last 90 days
fig = plots.daily_gains_bar_chart("latest_year") # All days in the latest year
Daily Gains Heatmap¶
GitHub-style heatmap showing daily gains for a single year (weeks x days of week):
Or a combined heatmap across all years:
Quantile Box Plots¶
Box plots showing gain distributions across daily, weekly, monthly, quarterly, and yearly periods:
Saving Individual Figures¶
All chart methods return standard Plotly Figure objects: