AEMO SDP-Teacher Decision Transformer (planner-distilled, physics-v2)
The shipped / preferred model of the energydecision benchmark. A standalone Decision Transformer distilled from an honest (non-clairvoyant), degradation-aware SDP-planning teacher β no solver at inference β that beats the PPO reference on all four identity surfaces and remains strong under the market-impact benchmark.
2026-09 update (physics-v2): this model was retrained on the corrected degradation/efficiency physics (round-trip efficiency 0.80, calendar aging, corrected rainflow C-rate units) and a wear-calibrated teacher (
--deg-calibration 0.12, aligning the planner's per-step wear with the environment's realized per-cycle wear). See Provenance below. It supersedes the earlieraemo_dt_sdp_jtsoc_fullcorpus.pt.
Files in this repo
| File | Model | Status |
|---|---|---|
aemo_dt_sdp_jtsoc_v2cal.pt (+ .pt.meta.json) |
Physics-v2 Stage C β J_t(soc) RTG, wear-calibrated SDP teacher (320 eps) | β Shipped β use this one |
aemo_dt_sdp_jtsoc_fullcorpus.pt (+ .pt.meta.json) |
Stage C v1 β J_t(soc) RTG, combined corpus (640 eps), pre-physics-fix | Historical (superseded; kept for the v1 comparison) |
(Removed 2026-09: the behaviour-cloning-era files aemo_dt_fcas_model.pt and aemo_dt_fcas_best_checkpoint.pt.)
Results (physics-v2 shipped model, aemo_dt_sdp_jtsoc_v2cal.pt, rtg_mode="auto")
| Surface | This model | Prev. shipped (v1) | PPO | Ratio vs PPO |
|---|---|---|---|---|
| Standard Oct | $16,209/ep | $11,573 | $2,353 | 6.9Γ |
| Dispatch-matched | $40,039/ep | $35,320 | $22,530 | 1.78Γ |
| 2025 OOD | $30,791/ep | $25,862 | $6,498 | 4.74Γ |
| Expanded broad-2024 | $32,146/ep | $34,761 | $19,504 | 1.65Γ |
| Market impact (piecewise merit-order) | DT well above PPO (e.g. Hornsdale-class SA1 Oct β $362k vs PPO β $75k) | β | β | passes |
All four identity surfaces beat PPO; the model improves on the previous shipped checkpoint on three of four surfaces. Methodology, the physics fixes, and the full experiment ladder: report.md Β§8.2.10 and docs/known_issues.md.
Provenance: what changed in physics-v2
| Fix | Effect |
|---|---|
A3/A4 β rainflow inferred current was %SoC/hour instead of a C-rate (~100Γ too large, then clamped); reset() dropped the C-rate cap |
corrected cycle-aging magnitude globally |
| A5 β planner degradation estimator always returned 0 (a 3-point rainflow sequence can never close a cycle) | planners are now wear-aware and state-dependent |
| A6 / B4 β the planner's per-step wear over-counted the env's per-closed-cycle wear by 8.4Γ on identical actions | added an explicit deg_calibration factor; the teacher corpus was regenerated with --deg-calibration 0.12 |
B1/B8 β impact-aware J_t(soc) dispatch-sign bug and a return_scale sidecar bug in the impact-eval runner |
evaluation correctness (the previous "explicit j_t_soc collapses under impact" claim was an artifact) |
The model card's numbers above are from the corrected pipeline. Prior household and AEMO numbers produced before these fixes are historical.
Architecture
| Parameter | Value |
|---|---|
| Blocks / hidden dim | 8 / 768 |
| Attention | GQA (12 Q / 6 KV), QK-Norm |
| RoPE | enabled (rope_max_position=630, max_timestep=2016) |
| FFN | SwiGLU, dropout 0.15 |
| Weight tying | Enabled |
| State / action dim | 18 / 9 (full_fcas) |
| Action head | Mixed (Tanh energy, Sigmoid FCAS) |
return_scale |
23,284.83 (auto-calibrated) |
Action space: dim 0 energy dispatch in [-1, 1]; dims 1β8 FCAS bids in [0, 1] (RAISEREG, LOWERREG, RAISE6SEC, LOWER6SEC, RAISE60SEC, LOWER60SEC, RAISE5MIN, LOWER5MIN). State space: 18-dim normalized market observations (time features, RRP, demand, 8 FCAS prices, generation mix, SOC).
Training data
- Shipped:
dt_trajectories_jtsoc_v2cal_conservative.parquetβ 320 episodes, 3.13M rows, honest SDP teacher with wear calibration and per-episodeJ_t(soc)cost-to-go RTG. Hosted at mrvictoru/AEMO_simulated_trade_sdp. - Generated by
scripts/generate_sdp_dt_trajectories.py(--deg-calibration 0.12,--rtg-mode j_t_soc); method in report.md Β§4.3/Β§5.4.
Usage
import json
import torch
from huggingface_hub import hf_hub_download
from decision_transformer import DecisionTransformer
from decision import AEMOAgent
repo = "mrvictoru/energydecision-dt-v2-sdp"
ckpt = hf_hub_download(repo, "aemo_dt_sdp_jtsoc_v2cal.pt")
meta = json.loads(hf_hub_download(repo, "aemo_dt_sdp_jtsoc_v2cal.pt.meta.json"))
model_kwargs = dict(
state_dim=meta["model"]["state_dim"], act_dim=meta["model"]["act_dim"],
h_dim=meta["model"]["h_dim"], context_len=meta["model"]["context_len"],
n_block=8, n_heads=12, n_kv_heads=6, drop_p=0.15,
max_timestep=2016, rope_enabled=True, qk_norm=True, tie_weights=True,
action_head_mode="mixed",
)
model = DecisionTransformer(**model_kwargs)
model.load_from_checkpoint(ckpt) # raw state_dict
model.return_scale = meta["return_scale"] # 23284.83
model.eval()
agent = AEMOAgent(env, algorithm="dt", model=model, rtg_mode="auto")
rtg_mode="auto" resolves to state-dependent j_t_soc prompting on price-taking (identity) surfaces and a conservative constant-RTG fallback under a market-impact model.
Inference prerequisites (what else you need)
- Source code. The
DecisionTransformermodel,AEMOAgent, and theAEMOBatteryTradingEnvlive in the energydecision repo, not in this model repo. - Seasonal RRP profiles (bundled here). For
rtg_mode="j_t_soc"/"auto"on identity surfaces, the agent builds a J_t(soc) cost-to-go table from a seasonal price forecast, cached todata/aemo_sdp/seasonal_rrp_<REGION>.json. The five profiles are included in this repo underdata/aemo_sdp/β copy them todata/aemo_sdp/in the repo checkout (otherwise thej_t_socpath has to rebuild them from raw AEMO parquets, which the simulation environment fetches separately). - Alternative without profiles.
rtg_mode="constant"(with a prompt value) needs no seasonal profile, but it is not the shipped setting and under-performs on identity surfaces.
Intended use
Research into offline RL / sequence modeling for energy markets; simulation of multi-market BESS dispatch in Australia's NEM; baseline for planner-distilled offline RL. Not intended for live trading without further validation (sim-to-real is open), risk management, and regulatory compliance.
Citation
@misc{energydecision-dt-v2-sdp,
title = {AEMO SDP-Teacher Decision Transformer (planner-distilled, physics-v2)},
author = {mrvictoru},
year = {2026},
url = {https://huggingface.co/mrvictoru/energydecision-dt-v2-sdp}
}
Related
- Dataset: mrvictoru/AEMO_simulated_trade_sdp
- Modern v2 (behaviour-cloning era, superseded): energydecision-dt-v2
- Impact-aware variant: energydecision-dt-v2-impact
- Source repo: mrvictoru/energydecision