# ADR 17: Historical Header Module

# Changelog

  • 26 November 2019: Start of first version
  • 2 December 2019: Final draft of first version

# Context

In order for the Cosmos SDK to implement the IBC specification (opens new window), modules within the SDK must have the ability to introspect recent consensus states (validator sets & commitment roots) as proofs of these values on other chains must be checked during the handshakes.

# Decision

The application MUST store the most recent n headers in a persistent store. At first, this store MAY be the current Merklised store. A non-Merklised store MAY be used later as no proofs are necessary.

The application MUST store this information by storing new headers immediately when handling abci.RequestBeginBlock:

Copy func BeginBlock(ctx sdk.Context, keeper HistoricalHeaderKeeper, req abci.RequestBeginBlock) abci.ResponseBeginBlock { info := HistoricalInfo{ Header: ctx.BlockHeader(), ValSet: keeper.StakingKeeper.GetAllValidators(ctx), // note that this must be stored in a canonical order } keeper.SetHistoricalInfo(ctx, ctx.BlockHeight(), info) n := keeper.GetParamRecentHeadersToStore() keeper.PruneHistoricalInfo(ctx, ctx.BlockHeight() - n) // continue handling request }

Alternatively, the application MAY store only the hash of the validator set.

The application MUST make these past n committed headers available for querying by SDK modules through the Keeper's GetHistoricalInfo function. This MAY be implemented in a new module, or it MAY also be integrated into an existing one (likely x/staking or x/ibc).

n MAY be configured as a parameter store parameter, in which case it could be changed by ParameterChangeProposals, although it will take some blocks for the stored information to catch up if n is increased.

# Status

Proposed.

# Consequences

Implementation of this ADR will require changes to the Cosmos SDK. It will not require changes to Tendermint.

# Positive

  • Easy retrieval of headers & state roots for recent past heights by modules anywhere in the SDK.
  • No RPC calls to Tendermint required.
  • No ABCI alterations required.

# Negative

  • Duplicates n headers data in Tendermint & the application (additional disk usage) - in the long term, an approach such as this (opens new window) might be preferable.

# Neutral

(none known)

# References