UpgradesSeptember 14, 2026by
EmpoorioChain Core
EmpoorioChain Core

The Upgrade Manifest: What Every Runtime Upgrade Must Publish

A changelog tells you what someone says changed. A manifest tells you what did change, in a form a machine can check. EmpoorioChain's upgrade policy requires a manifest for every runtime upgrade, and this post walks through it.

The manifest

{
  "upgrade_id": "…",
  "class": "normal | security | economic | emergency",
  "target_network": "testnet",
  "runtime_wasm": "path or URL",
  "runtime_hash": "blake2-256 of the Wasm",
  "spec_version_before": 219,
  "spec_version_after": 220,
  "metadata_hash_before": "…",
  "metadata_hash_after": "…",
  "metadata_diff_summary": "…",
  "timelock_blocks": 7200,
  "has_storage_migration": false,
  "try_runtime_report": null,
  "migration_dry_run_hash": null,
  "rollback_plan": "…",
  "approvals": ["…"]
}

If has_storage_migration is true, try_runtime_report and migration_dry_run_hash become mandatory — a migration nobody has dry-run against a snapshot of the live state does not ship. If the upgrade touches fees, staking, treasury, paymaster, bridge, PQC, sudo, scheduler, preimage or governance, it may not be classed normal.

python3 scripts/validate_runtime_upgrade_manifest.py --manifest upgrade-220.json

validates the manifest before a proposal is even created.

Classes and timelocks

ClassTestnet timelockExtra evidence
normal7,200 blocks (~12 h)reproducible build, metadata diff, runtime tests
security28,800 blocks (~48 h)updated threat model, security approval
economic28,800 blocks (~48 h)economic simulation, fee impact, migration dry-run
emergency1,200 blocks (~2 h)justification, blast radius, rollback plan, mandatory post-mortem

Emergency shortens the wait; it never removes the audit trail.

The approval checklist

  • Wasm built in CI from a signed commit.
  • Wasm hash published on EmpooScan.
  • Metadata diff published on EmpooScan.
  • spec_version_after > spec_version_before.
  • transaction_version reviewed if the extrinsic format changes.
  • try-runtime or dry-run executed against a testnet snapshot.
  • Rollback plan documented.
  • Timelock set according to class.
  • Eoonia Wallet able to warn users before signing sensitive operations during the window.
  • Final result indexed by EmpooScan.

Why try-runtime is not optional

The test suite runs pallets in isolation against mock state. It cannot see what happens when a migration meets real state accumulated over thousands of blocks. try-runtime executes the upgrade against a snapshot of the live chain, and it has caught failures the suite never could — including, in this network's history, an authority-set issue that would have halted block production had the upgrade shipped. The rule written afterwards: a change that can kill the chain is found by running the chain, not the tests.

Why the metadata diff matters to everyone

Runtime metadata is what wallets, indexers and SDKs use to encode and decode calls. It changes in every upgrade — the version number is inside it — and it changes structurally whenever calls, storage or types move. Publishing the diff lets Eoonia, EmpooScan and third-party tools see what they must update before the timelock expires, instead of discovering it when transactions start failing.

From plan to practice

The policy was written in August 2026 as a gate for a network that had never been upgraded in place. Since 4 September it has governed eight real upgrades, including one with a storage migration (runtime 213, storage billing to bytes). What the sequence exposed — stale metadata caches in clients, post_upgrade hooks asserting facts they did not control, call indexes read by position — has been folded back into the checklist. The economic class and the emergency rollback drill remain to be rehearsed before the policy can be called exercised.

Based on RUNTIME_UPGRADE_POLICY.md and the runtime 208–220 upgrade records.

Share this article