Skip to content

Commit

Permalink
db-sync: Add the epoch nonce to the EpochParam table
Browse files Browse the repository at this point in the history
Closes: #322
  • Loading branch information
erikd committed Oct 26, 2020
1 parent 5a40c89 commit c729d55
Show file tree
Hide file tree
Showing 4 changed files with 45 additions and 18 deletions.
11 changes: 6 additions & 5 deletions cardano-db-sync/src/Cardano/DbSync/Era/Shelley/Insert.hs
Expand Up @@ -122,9 +122,9 @@ insertShelleyBlock tracer env blk lStateSnap details = do

whenJust (lssEpochUpdate lStateSnap) $ \ esum -> do
-- Subtract 2 from the epoch to calculate when the epoch in which the reward was earned.
insertRewards tracer env blkId (sdEpochNo details - 2) (esRewardUpdate esum)
insertEpochParam tracer blkId (sdEpochNo details) (esParamUpdate esum)
insertEpochStake tracer env blkId (sdEpochNo details) (esStakeUpdate esum)
insertRewards tracer env blkId (sdEpochNo details - 2) (euRewards esum)
insertEpochParam tracer blkId (sdEpochNo details) (euProtoParams esum) (euNonce esum)
insertEpochStake tracer env blkId (sdEpochNo details) (euStakeDistribution esum)

when (getSyncStatus details == SyncFollowing) $
-- Serializiing things during syncing can drastically slow down full sync
Expand Down Expand Up @@ -617,9 +617,9 @@ insertRewards _tracer env blkId epoch rewards =

insertEpochParam
:: (MonadBaseControl IO m, MonadIO m)
=> Trace IO Text -> DB.BlockId -> EpochNo -> Shelley.PParams StandardShelley
=> Trace IO Text -> DB.BlockId -> EpochNo -> Shelley.PParams StandardShelley -> Shelley.Nonce
-> ExceptT DbSyncNodeError (ReaderT SqlBackend m) ()
insertEpochParam _tracer blkId (EpochNo epoch) params =
insertEpochParam _tracer blkId (EpochNo epoch) params nonce =
void . lift . DB.insertEpochParam $
DB.EpochParam
{ DB.epochParamEpochNo = epoch
Expand All @@ -641,6 +641,7 @@ insertEpochParam _tracer blkId (EpochNo epoch) params =
, DB.epochParamProtocolMinor = fromIntegral $ Shelley.pvMinor (Shelley._protocolVersion params)
, DB.epochParamMinUtxoValue = Shelley.coinToDbLovelace (Shelley._minUTxOValue params)
, DB.epochParamMinPoolCost = Shelley.coinToDbLovelace (Shelley._minPoolCost params)
, DB.epochParamNonce = Shelley.nonceToBytes nonce
, DB.epochParamBlockId = blkId
}

Expand Down
48 changes: 36 additions & 12 deletions cardano-db-sync/src/Cardano/DbSync/LedgerState.hs
Expand Up @@ -3,6 +3,7 @@
{-# LANGUAGE NoImplicitPrelude #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE TypeFamilies #-}

module Cardano.DbSync.LedgerState
( CardanoLedgerState (..)
Expand Down Expand Up @@ -43,20 +44,29 @@ import qualified Data.List as List
import Ouroboros.Consensus.Block (CodecConfig, WithOrigin (..))
import Ouroboros.Consensus.Cardano.Block
(LedgerState (LedgerStateByron, LedgerStateShelley))
import qualified Ouroboros.Consensus.Shelley.Protocol as Consensus
import Ouroboros.Consensus.Cardano.CanHardFork ()
import Ouroboros.Consensus.Config (TopLevelConfig (..), configCodec, configLedger)
import qualified Ouroboros.Consensus.HardFork.Combinator as Consensus
import Ouroboros.Consensus.HardFork.Combinator.Basics (LedgerState (..))
import Ouroboros.Consensus.HardFork.Combinator.State (epochInfoLedger)
import qualified Ouroboros.Consensus.HardFork.Combinator.State as Consensus
import qualified Ouroboros.Consensus.HeaderValidation as Consensus
import Ouroboros.Consensus.Ledger.Abstract (ledgerTipSlot, tickThenApply, tickThenReapply)
import Ouroboros.Consensus.Ledger.Extended (ExtLedgerCfg (..), ExtLedgerState (..),
decodeExtLedgerState, encodeExtLedgerState)
import qualified Ouroboros.Consensus.Node.ProtocolInfo as Consensus
import qualified Ouroboros.Consensus.Shelley.Ledger.Ledger as Consensus
import Ouroboros.Consensus.Shelley.Protocol (StandardShelley)
import Ouroboros.Consensus.Storage.Serialisation (DecodeDisk (..), EncodeDisk (..))
import qualified Ouroboros.Consensus.TypeFamilyWrappers as Consensus



import qualified Shelley.Spec.Ledger.API.Protocol as Shelley
import qualified Shelley.Spec.Ledger.BaseTypes as Shelley
import qualified Shelley.Spec.Ledger.EpochBoundary as Shelley
import qualified Shelley.Spec.Ledger.STS.Tickn as Shelley
import qualified Shelley.Spec.Ledger.LedgerState as Shelley
import qualified Shelley.Spec.Ledger.PParams as Shelley

Expand All @@ -71,9 +81,10 @@ data CardanoLedgerState = CardanoLedgerState
}

data EpochUpdate = EpochUpdate
{ esParamUpdate :: !(Shelley.PParams StandardShelley)
, esRewardUpdate :: !(Shelley.RewardUpdate StandardShelley)
, esStakeUpdate :: !(Shelley.Stake StandardShelley)
{ euProtoParams :: !(Shelley.PParams StandardShelley)
, euRewards :: !(Shelley.RewardUpdate StandardShelley)
, euStakeDistribution :: !(Shelley.Stake StandardShelley)
, euNonce :: !Shelley.Nonce
}

newtype LedgerStateVar = LedgerStateVar
Expand Down Expand Up @@ -119,8 +130,8 @@ applyBlock (LedgerStateVar stateVar) blk =
if ledgerEpochNo newState == ledgerEpochNo oldState + 1
then Just $
ledgerEpochUpdate
(ledgerState (clsState newState))
(ledgerRewardUpdate (ledgerState (clsState oldState)))
(clsState newState)
(ledgerRewardUpdate (ledgerState $ clsState oldState))
else Nothing
}
where
Expand Down Expand Up @@ -276,21 +287,22 @@ ledgerEpochNo cls =
epochInfo = epochInfoLedger (configLedger $ clsConfig cls) (hardForkLedgerStatePerEra . ledgerState $ clsState cls)

-- Create an EpochUpdate from the current epoch state and the rewards from the last epoch.
ledgerEpochUpdate :: LedgerState CardanoBlock -> Maybe (Shelley.RewardUpdate StandardShelley) -> EpochUpdate
ledgerEpochUpdate lcs mRewards =
case lcs of
ledgerEpochUpdate :: ExtLedgerState CardanoBlock -> Maybe (Shelley.RewardUpdate StandardShelley) -> EpochUpdate
ledgerEpochUpdate els mRewards =
case ledgerState els of
LedgerStateByron _ -> panic "ledgerEpochUpdate: LedgerStateByron but should be Shelley"
LedgerStateShelley sls ->
EpochUpdate
{ esParamUpdate = Shelley.esPp $ Shelley.nesEs (Consensus.shelleyLedgerState sls)
, esRewardUpdate = fromMaybe Shelley.emptyRewardUpdate mRewards
{ euProtoParams = Shelley.esPp $ Shelley.nesEs (Consensus.shelleyLedgerState sls)
, euRewards = fromMaybe Shelley.emptyRewardUpdate mRewards

-- Use '_pstakeSet' here instead of '_pstateMark' because the stake addresses for the
-- later may not have been added to the database yet. That means that whne these values
-- are added to the database, the epoch number where they become active is the current
-- epoch plus one.
, esStakeUpdate = Shelley._stake . Shelley._pstakeSet . Shelley.esSnapshots
$ Shelley.nesEs (Consensus.shelleyLedgerState sls)
, euStakeDistribution = Shelley._stake . Shelley._pstakeSet . Shelley.esSnapshots
$ Shelley.nesEs (Consensus.shelleyLedgerState sls)
, euNonce = fromMaybe Shelley.NeutralNonce $ extractEpochNonce els
}

-- This will return a 'Just' from the time the rewards are updated until the end of the
Expand All @@ -302,3 +314,15 @@ ledgerRewardUpdate lsc =
LedgerStateShelley sls -> Shelley.strictMaybeToMaybe . Shelley.nesRu
$ Consensus.shelleyLedgerState sls

-- Some of the nastiness here will disappear when suitable PatternSynonyms are added to Consensus.
-- TODO: Replace this horrible stuff with the PatternSynonyms when they become available.
extractEpochNonce :: ExtLedgerState CardanoBlock -> Maybe Shelley.Nonce
extractEpochNonce extLedgerState =
case Consensus.getHardForkState (Consensus.headerStateChainDep (headerState extLedgerState)) of
Consensus.TZ {} ->
Nothing
Consensus.TS _ (Consensus.TZ (Consensus.Current { Consensus.currentState = chainDepStateShelley })) ->
Just . Shelley.ticknStateEpochNonce . Shelley.csTickn
$ Consensus.tpraosStateChainDepState (Consensus.unwrapChainDepState chainDepStateShelley)
Consensus.TS {} ->
Nothing
2 changes: 2 additions & 0 deletions cardano-db/src/Cardano/Db/Schema.hs
Expand Up @@ -327,6 +327,8 @@ share
minUtxoValue DbLovelace sqltype=lovelace
minPoolCost DbLovelace sqltype=lovelace

nonce ByteString Maybe sqltype=hash32type

blockId BlockId -- The first block where these parameters are valid.
UniqueEpochParam epochNo blockId

Expand Down
Expand Up @@ -94,7 +94,7 @@ BEGIN
EXECUTE 'CREATe TABLE "param_proposal"("id" SERIAL8 PRIMARY KEY UNIQUE,"epoch_no" uinteger NOT NULL,"key" hash28type NOT NULL,"min_fee_a" uinteger NULL,"min_fee_b" uinteger NULL,"max_block_size" uinteger NULL,"max_tx_size" uinteger NULL,"max_bh_size" uinteger NULL,"key_deposit" lovelace NULL,"pool_deposit" lovelace NULL,"max_epoch" uinteger NULL,"optimal_pool_count" uinteger NULL,"influence" DOUBLE PRECISION NULL,"monetary_expand_rate" DOUBLE PRECISION NULL,"treasury_growth_rate" DOUBLE PRECISION NULL,"decentralisation" DOUBLE PRECISION NULL,"entropy" hash32type NULL,"protocol_major" uinteger NULL,"protocol_minor" uinteger NULL,"min_utxo_value" lovelace NULL,"min_pool_cost" lovelace NULL,"registered_tx_id" INT8 NOT NULL)' ;
EXECUTE 'ALTER TABLE "param_proposal" ADD CONSTRAINT "unique_param_proposal" UNIQUE("key","registered_tx_id")' ;
EXECUTE 'ALTER TABLE "param_proposal" ADD CONSTRAINT "param_proposal_registered_tx_id_fkey" FOREIGN KEY("registered_tx_id") REFERENCES "tx"("id")' ;
EXECUTE 'CREATe TABLE "epoch_param"("id" SERIAL8 PRIMARY KEY UNIQUE,"epoch_no" uinteger NOT NULL,"min_fee_a" uinteger NOT NULL,"min_fee_b" uinteger NOT NULL,"max_block_size" uinteger NOT NULL,"max_tx_size" uinteger NOT NULL,"max_bh_size" uinteger NOT NULL,"key_deposit" lovelace NOT NULL,"pool_deposit" lovelace NOT NULL,"max_epoch" uinteger NOT NULL,"optimal_pool_count" uinteger NOT NULL,"influence" DOUBLE PRECISION NOT NULL,"monetary_expand_rate" DOUBLE PRECISION NOT NULL,"treasury_growth_rate" DOUBLE PRECISION NOT NULL,"decentralisation" DOUBLE PRECISION NOT NULL,"entropy" hash32type NULL,"protocol_major" uinteger NOT NULL,"protocol_minor" uinteger NOT NULL,"min_utxo_value" lovelace NOT NULL,"min_pool_cost" lovelace NOT NULL,"block_id" INT8 NOT NULL)' ;
EXECUTE 'CREATe TABLE "epoch_param"("id" SERIAL8 PRIMARY KEY UNIQUE,"epoch_no" uinteger NOT NULL,"min_fee_a" uinteger NOT NULL,"min_fee_b" uinteger NOT NULL,"max_block_size" uinteger NOT NULL,"max_tx_size" uinteger NOT NULL,"max_bh_size" uinteger NOT NULL,"key_deposit" lovelace NOT NULL,"pool_deposit" lovelace NOT NULL,"max_epoch" uinteger NOT NULL,"optimal_pool_count" uinteger NOT NULL,"influence" DOUBLE PRECISION NOT NULL,"monetary_expand_rate" DOUBLE PRECISION NOT NULL,"treasury_growth_rate" DOUBLE PRECISION NOT NULL,"decentralisation" DOUBLE PRECISION NOT NULL,"entropy" hash32type NULL,"protocol_major" uinteger NOT NULL,"protocol_minor" uinteger NOT NULL,"min_utxo_value" lovelace NOT NULL,"min_pool_cost" lovelace NOT NULL,"nonce" hash32type NULL,"block_id" INT8 NOT NULL)' ;
EXECUTE 'ALTER TABLE "epoch_param" ADD CONSTRAINT "unique_epoch_param" UNIQUE("epoch_no","block_id")' ;
EXECUTE 'ALTER TABLE "epoch_param" ADD CONSTRAINT "epoch_param_block_id_fkey" FOREIGN KEY("block_id") REFERENCES "block"("id")' ;
-- Hand written SQL statements can be added here.
Expand Down

0 comments on commit c729d55

Please sign in to comment.