Merge PR #4847: Sim refactor 1 move store decoders to modules
* move store decoders to modules * fix * module pattern * compile * update Decoders params * fix * address @colin-axner comments * Update cmd_test.go * simulation manager * mino fixes * cleanup * Apply suggestions from code review Co-Authored-By: frog power 4000 <rigel.rozanski@gmail.com> * address @rigelrozanski comments * changelog * Apply suggestions from code review Co-Authored-By: colin axner <colinaxner@berkeley.edu> * restructure modules simulation pkgs * address @alexanderbez comments * fix
This commit is contained in:
parent
81f86fefe5
commit
c441ce2fab
|
@ -60,6 +60,9 @@ longer panics if the store to load contains substores that we didn't explicitly
|
|||
* (simulation) [\#4824](https://github.com/cosmos/cosmos-sdk/issues/4824) PrintAllInvariants flag will print all failed invariants
|
||||
* (simulation) [\#4490](https://github.com/cosmos/cosmos-sdk/issues/4490) add `InitialBlockHeight` flag to resume a simulation from a given block
|
||||
* Support exporting the simulation stats to a given JSON file
|
||||
* (simulation) [\#4847](https://github.com/cosmos/cosmos-sdk/issues/4847) `SimApp` and simulation refactors
|
||||
* Implement `SimulationManager` for executing modules' simulation functionalities in a modularized way
|
||||
* Add `DecodeStore` to the `SimulationManager` for decoding each module's types
|
||||
* (simulation) [\#4893](https://github.com/cosmos/cosmos-sdk/issues/4893) Change SimApp keepers to be public and add getter functions for keys and codec
|
||||
* (store) [\#4792](https://github.com/cosmos/cosmos-sdk/issues/4792) panic on non-registered store
|
||||
* (types) [\#4821](https://github.com/cosmos/cosmos-sdk/issues/4821) types/errors package added with support for stacktraces. It is meant as a more feature-rich replacement for sdk.Errors in the mid-term.
|
||||
|
|
|
@ -1,4 +1,3 @@
|
|||
// nolint: misspell
|
||||
package client_test
|
||||
|
||||
import (
|
||||
|
@ -38,10 +37,10 @@ func TestValidateCmd(t *testing.T) {
|
|||
args []string
|
||||
wantErr bool
|
||||
}{
|
||||
{"misspelled command", []string{"comission"}, true},
|
||||
{"misspelled command", []string{"comission"}, true}, // nolint: misspell
|
||||
{"no command provided", []string{}, false},
|
||||
{"help flag", []string{"comission", "--help"}, false},
|
||||
{"shorthand help flag", []string{"comission", "-h"}, false},
|
||||
{"help flag", []string{"comission", "--help"}, false}, // nolint: misspell
|
||||
{"shorthand help flag", []string{"comission", "-h"}, false}, // nolint: misspell
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
|
|
|
@ -103,6 +103,9 @@ type SimApp struct {
|
|||
|
||||
// the module manager
|
||||
mm *module.Manager
|
||||
|
||||
// simulation manager
|
||||
sm *module.SimulationManager
|
||||
}
|
||||
|
||||
// NewSimApp returns a reference to an initialized SimApp.
|
||||
|
@ -202,6 +205,9 @@ func NewSimApp(
|
|||
app.mm.RegisterInvariants(&app.CrisisKeeper)
|
||||
app.mm.RegisterRoutes(app.Router(), app.QueryRouter())
|
||||
|
||||
app.sm = module.NewSimulationManager(app.mm.Modules)
|
||||
app.sm.RegisterStoreDecoders()
|
||||
|
||||
// initialize stores
|
||||
app.MountKVStores(keys)
|
||||
app.MountTransientStores(tkeys)
|
||||
|
|
|
@ -20,20 +20,20 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/baseapp"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth"
|
||||
authsim "github.com/cosmos/cosmos-sdk/x/auth/simulation"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank"
|
||||
authsimops "github.com/cosmos/cosmos-sdk/x/auth/simulation/operations"
|
||||
banksimops "github.com/cosmos/cosmos-sdk/x/bank/simulation/operations"
|
||||
distr "github.com/cosmos/cosmos-sdk/x/distribution"
|
||||
distrsim "github.com/cosmos/cosmos-sdk/x/distribution/simulation"
|
||||
distrsimops "github.com/cosmos/cosmos-sdk/x/distribution/simulation/operations"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov"
|
||||
govsim "github.com/cosmos/cosmos-sdk/x/gov/simulation"
|
||||
govsimops "github.com/cosmos/cosmos-sdk/x/gov/simulation/operations"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint"
|
||||
"github.com/cosmos/cosmos-sdk/x/params"
|
||||
paramsim "github.com/cosmos/cosmos-sdk/x/params/simulation"
|
||||
paramsimops "github.com/cosmos/cosmos-sdk/x/params/simulation/operations"
|
||||
"github.com/cosmos/cosmos-sdk/x/simulation"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing"
|
||||
slashingsim "github.com/cosmos/cosmos-sdk/x/slashing/simulation"
|
||||
slashingsimops "github.com/cosmos/cosmos-sdk/x/slashing/simulation/operations"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking"
|
||||
stakingsim "github.com/cosmos/cosmos-sdk/x/staking/simulation"
|
||||
stakingsimops "github.com/cosmos/cosmos-sdk/x/staking/simulation/operations"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply"
|
||||
)
|
||||
|
||||
|
@ -184,7 +184,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
authsim.SimulateDeductFee(app.AccountKeeper, app.SupplyKeeper),
|
||||
authsimops.SimulateDeductFee(app.AccountKeeper, app.SupplyKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -195,7 +195,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
bank.SimulateMsgSend(app.AccountKeeper, app.BankKeeper),
|
||||
banksimops.SimulateMsgSend(app.AccountKeeper, app.BankKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -206,7 +206,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
bank.SimulateSingleInputMsgMultiSend(app.AccountKeeper, app.BankKeeper),
|
||||
banksimops.SimulateSingleInputMsgMultiSend(app.AccountKeeper, app.BankKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -217,7 +217,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
distrsim.SimulateMsgSetWithdrawAddress(app.AccountKeeper, app.DistrKeeper),
|
||||
distrsimops.SimulateMsgSetWithdrawAddress(app.DistrKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -228,7 +228,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
distrsim.SimulateMsgWithdrawDelegatorReward(app.AccountKeeper, app.DistrKeeper),
|
||||
distrsimops.SimulateMsgWithdrawDelegatorReward(app.DistrKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -239,7 +239,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
distrsim.SimulateMsgWithdrawValidatorCommission(app.AccountKeeper, app.DistrKeeper),
|
||||
distrsimops.SimulateMsgWithdrawValidatorCommission(app.DistrKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -250,7 +250,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
govsim.SimulateSubmittingVotingAndSlashingForProposal(app.GovKeeper, govsim.SimulateTextProposalContent),
|
||||
govsimops.SimulateSubmittingVotingAndSlashingForProposal(app.GovKeeper, govsimops.SimulateTextProposalContent),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -261,7 +261,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
govsim.SimulateSubmittingVotingAndSlashingForProposal(app.GovKeeper, distrsim.SimulateCommunityPoolSpendProposalContent(app.DistrKeeper)),
|
||||
govsimops.SimulateSubmittingVotingAndSlashingForProposal(app.GovKeeper, distrsimops.SimulateCommunityPoolSpendProposalContent(app.DistrKeeper)),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -272,7 +272,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
govsim.SimulateSubmittingVotingAndSlashingForProposal(app.GovKeeper, paramsim.SimulateParamChangeProposalContent),
|
||||
govsimops.SimulateSubmittingVotingAndSlashingForProposal(app.GovKeeper, paramsimops.SimulateParamChangeProposalContent),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -283,7 +283,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
govsim.SimulateMsgDeposit(app.GovKeeper),
|
||||
govsimops.SimulateMsgDeposit(app.GovKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -294,7 +294,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
stakingsim.SimulateMsgCreateValidator(app.AccountKeeper, app.StakingKeeper),
|
||||
stakingsimops.SimulateMsgCreateValidator(app.AccountKeeper, app.StakingKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -305,7 +305,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
stakingsim.SimulateMsgEditValidator(app.StakingKeeper),
|
||||
stakingsimops.SimulateMsgEditValidator(app.StakingKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -316,7 +316,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
stakingsim.SimulateMsgDelegate(app.AccountKeeper, app.StakingKeeper),
|
||||
stakingsimops.SimulateMsgDelegate(app.AccountKeeper, app.StakingKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -327,7 +327,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
stakingsim.SimulateMsgUndelegate(app.AccountKeeper, app.StakingKeeper),
|
||||
stakingsimops.SimulateMsgUndelegate(app.AccountKeeper, app.StakingKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -338,7 +338,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
stakingsim.SimulateMsgBeginRedelegate(app.AccountKeeper, app.StakingKeeper),
|
||||
stakingsimops.SimulateMsgBeginRedelegate(app.AccountKeeper, app.StakingKeeper),
|
||||
},
|
||||
{
|
||||
func(_ *rand.Rand) int {
|
||||
|
@ -349,7 +349,7 @@ func testAndRunTxs(app *SimApp) []simulation.WeightedOperation {
|
|||
})
|
||||
return v
|
||||
}(nil),
|
||||
slashingsim.SimulateMsgUnjail(app.SlashingKeeper),
|
||||
slashingsimops.SimulateMsgUnjail(app.SlashingKeeper),
|
||||
},
|
||||
}
|
||||
}
|
||||
|
@ -597,11 +597,15 @@ func TestAppImportExport(t *testing.T) {
|
|||
storeKeyA := storeKeysPrefix.A
|
||||
storeKeyB := storeKeysPrefix.B
|
||||
prefixes := storeKeysPrefix.Prefixes
|
||||
|
||||
storeA := ctxA.KVStore(storeKeyA)
|
||||
storeB := ctxB.KVStore(storeKeyB)
|
||||
failedKVs := sdk.DiffKVStores(storeA, storeB, prefixes)
|
||||
fmt.Printf("Compared %d key/value pairs between %s and %s\n", len(failedKVs)/2, storeKeyA, storeKeyB)
|
||||
require.Len(t, failedKVs, 0, GetSimulationLog(storeKeyA.Name(), app.cdc, newApp.cdc, failedKVs))
|
||||
|
||||
failedKVAs, failedKVBs := sdk.DiffKVStores(storeA, storeB, prefixes)
|
||||
require.Equal(t, len(failedKVAs), len(failedKVBs), "unequal sets of key-values to compare")
|
||||
|
||||
fmt.Printf("Compared %d key/value pairs between %s and %s\n", len(failedKVAs), storeKeyA, storeKeyB)
|
||||
require.Len(t, failedKVAs, 0, GetSimulationLog(storeKeyA.Name(), app.sm.StoreDecoders, app.cdc, failedKVAs, failedKVBs))
|
||||
}
|
||||
|
||||
}
|
||||
|
|
240
simapp/utils.go
240
simapp/utils.go
|
@ -2,8 +2,6 @@
|
|||
package simapp
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/binary"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io"
|
||||
|
@ -11,7 +9,6 @@ import (
|
|||
"math/rand"
|
||||
"time"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto"
|
||||
"github.com/tendermint/tendermint/crypto/secp256k1"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
|
@ -500,242 +497,21 @@ func GenStakingGenesisState(
|
|||
|
||||
// GetSimulationLog unmarshals the KVPair's Value to the corresponding type based on the
|
||||
// each's module store key and the prefix bytes of the KVPair's key.
|
||||
func GetSimulationLog(storeName string, cdcA, cdcB *codec.Codec, kvs []cmn.KVPair) (log string) {
|
||||
var kvA, kvB cmn.KVPair
|
||||
for i := 0; i < len(kvs); i += 2 {
|
||||
kvA = kvs[i]
|
||||
kvB = kvs[i+1]
|
||||
func GetSimulationLog(storeName string, sdr sdk.StoreDecoderRegistry, cdc *codec.Codec, kvAs, kvBs []cmn.KVPair) (log string) {
|
||||
for i := 0; i < len(kvAs); i++ {
|
||||
|
||||
if len(kvA.Value) == 0 && len(kvB.Value) == 0 {
|
||||
if len(kvAs[i].Value) == 0 && len(kvBs[i].Value) == 0 {
|
||||
// skip if the value doesn't have any bytes
|
||||
continue
|
||||
}
|
||||
|
||||
switch storeName {
|
||||
case auth.StoreKey:
|
||||
log += DecodeAccountStore(cdcA, cdcB, kvA, kvB)
|
||||
case mint.StoreKey:
|
||||
log += DecodeMintStore(cdcA, cdcB, kvA, kvB)
|
||||
case staking.StoreKey:
|
||||
log += DecodeStakingStore(cdcA, cdcB, kvA, kvB)
|
||||
case slashing.StoreKey:
|
||||
log += DecodeSlashingStore(cdcA, cdcB, kvA, kvB)
|
||||
case gov.StoreKey:
|
||||
log += DecodeGovStore(cdcA, cdcB, kvA, kvB)
|
||||
case distribution.StoreKey:
|
||||
log += DecodeDistributionStore(cdcA, cdcB, kvA, kvB)
|
||||
case supply.StoreKey:
|
||||
log += DecodeSupplyStore(cdcA, cdcB, kvA, kvB)
|
||||
default:
|
||||
log += fmt.Sprintf("store A %X => %X\nstore B %X => %X\n", kvA.Key, kvA.Value, kvB.Key, kvB.Value)
|
||||
decoder, ok := sdr[storeName]
|
||||
if ok {
|
||||
log += decoder(cdc, kvAs[i], kvBs[i])
|
||||
} else {
|
||||
log += fmt.Sprintf("store A %X => %X\nstore B %X => %X\n", kvAs[i].Key, kvAs[i].Value, kvBs[i].Key, kvBs[i].Value)
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// DecodeAccountStore unmarshals the KVPair's Value to the corresponding auth type
|
||||
func DecodeAccountStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], auth.AddressStoreKeyPrefix):
|
||||
var accA, accB auth.Account
|
||||
cdcA.MustUnmarshalBinaryBare(kvA.Value, &accA)
|
||||
cdcB.MustUnmarshalBinaryBare(kvB.Value, &accB)
|
||||
return fmt.Sprintf("%v\n%v", accA, accB)
|
||||
case bytes.Equal(kvA.Key, auth.GlobalAccountNumberKey):
|
||||
var globalAccNumberA, globalAccNumberB uint64
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &globalAccNumberA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &globalAccNumberB)
|
||||
return fmt.Sprintf("GlobalAccNumberA: %d\nGlobalAccNumberB: %d", globalAccNumberA, globalAccNumberB)
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid account key %X", kvA.Key))
|
||||
}
|
||||
}
|
||||
|
||||
// DecodeMintStore unmarshals the KVPair's Value to the corresponding mint type
|
||||
func DecodeMintStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key, mint.MinterKey):
|
||||
var minterA, minterB mint.Minter
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &minterA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &minterB)
|
||||
return fmt.Sprintf("%v\n%v", minterA, minterB)
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid mint key %X", kvA.Key))
|
||||
}
|
||||
}
|
||||
|
||||
// DecodeDistributionStore unmarshals the KVPair's Value to the corresponding distribution type
|
||||
func DecodeDistributionStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], distribution.FeePoolKey):
|
||||
var feePoolA, feePoolB distribution.FeePool
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &feePoolA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &feePoolB)
|
||||
return fmt.Sprintf("%v\n%v", feePoolA, feePoolB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.ProposerKey):
|
||||
return fmt.Sprintf("%v\n%v", sdk.ConsAddress(kvA.Value), sdk.ConsAddress(kvB.Value))
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.ValidatorOutstandingRewardsPrefix):
|
||||
var rewardsA, rewardsB distribution.ValidatorOutstandingRewards
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &rewardsA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &rewardsB)
|
||||
return fmt.Sprintf("%v\n%v", rewardsA, rewardsB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.DelegatorWithdrawAddrPrefix):
|
||||
return fmt.Sprintf("%v\n%v", sdk.AccAddress(kvA.Value), sdk.AccAddress(kvB.Value))
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.DelegatorStartingInfoPrefix):
|
||||
var infoA, infoB distribution.DelegatorStartingInfo
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &infoA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &infoB)
|
||||
return fmt.Sprintf("%v\n%v", infoA, infoB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.ValidatorHistoricalRewardsPrefix):
|
||||
var rewardsA, rewardsB distribution.ValidatorHistoricalRewards
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &rewardsA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &rewardsB)
|
||||
return fmt.Sprintf("%v\n%v", rewardsA, rewardsB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.ValidatorCurrentRewardsPrefix):
|
||||
var rewardsA, rewardsB distribution.ValidatorCurrentRewards
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &rewardsA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &rewardsB)
|
||||
return fmt.Sprintf("%v\n%v", rewardsA, rewardsB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.ValidatorAccumulatedCommissionPrefix):
|
||||
var commissionA, commissionB distribution.ValidatorAccumulatedCommission
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &commissionA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &commissionB)
|
||||
return fmt.Sprintf("%v\n%v", commissionA, commissionB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], distribution.ValidatorSlashEventPrefix):
|
||||
var eventA, eventB distribution.ValidatorSlashEvent
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &eventA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &eventB)
|
||||
return fmt.Sprintf("%v\n%v", eventA, eventB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid distribution key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
||||
|
||||
// DecodeStakingStore unmarshals the KVPair's Value to the corresponding staking type
|
||||
func DecodeStakingStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], staking.LastTotalPowerKey):
|
||||
var powerA, powerB sdk.Int
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &powerA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &powerB)
|
||||
return fmt.Sprintf("%v\n%v", powerA, powerB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], staking.ValidatorsKey):
|
||||
var validatorA, validatorB staking.Validator
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &validatorA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &validatorB)
|
||||
return fmt.Sprintf("%v\n%v", validatorA, validatorB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], staking.LastValidatorPowerKey),
|
||||
bytes.Equal(kvA.Key[:1], staking.ValidatorsByConsAddrKey),
|
||||
bytes.Equal(kvA.Key[:1], staking.ValidatorsByPowerIndexKey):
|
||||
return fmt.Sprintf("%v\n%v", sdk.ValAddress(kvA.Value), sdk.ValAddress(kvB.Value))
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], staking.DelegationKey):
|
||||
var delegationA, delegationB staking.Delegation
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &delegationA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &delegationB)
|
||||
return fmt.Sprintf("%v\n%v", delegationA, delegationB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], staking.UnbondingDelegationKey),
|
||||
bytes.Equal(kvA.Key[:1], staking.UnbondingDelegationByValIndexKey):
|
||||
var ubdA, ubdB staking.UnbondingDelegation
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &ubdA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &ubdB)
|
||||
return fmt.Sprintf("%v\n%v", ubdA, ubdB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], staking.RedelegationKey),
|
||||
bytes.Equal(kvA.Key[:1], staking.RedelegationByValSrcIndexKey):
|
||||
var redA, redB staking.Redelegation
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &redA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &redB)
|
||||
return fmt.Sprintf("%v\n%v", redA, redB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid staking key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
||||
|
||||
// DecodeSlashingStore unmarshals the KVPair's Value to the corresponding slashing type
|
||||
func DecodeSlashingStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], slashing.ValidatorSigningInfoKey):
|
||||
var infoA, infoB slashing.ValidatorSigningInfo
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &infoA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &infoB)
|
||||
return fmt.Sprintf("%v\n%v", infoA, infoB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], slashing.ValidatorMissedBlockBitArrayKey):
|
||||
var missedA, missedB bool
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &missedA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &missedB)
|
||||
return fmt.Sprintf("missedA: %v\nmissedB: %v", missedA, missedB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], slashing.AddrPubkeyRelationKey):
|
||||
var pubKeyA, pubKeyB crypto.PubKey
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &pubKeyA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &pubKeyB)
|
||||
bechPKA := sdk.MustBech32ifyAccPub(pubKeyA)
|
||||
bechPKB := sdk.MustBech32ifyAccPub(pubKeyB)
|
||||
return fmt.Sprintf("PubKeyA: %s\nPubKeyB: %s", bechPKA, bechPKB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid slashing key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
||||
|
||||
// DecodeGovStore unmarshals the KVPair's Value to the corresponding gov type
|
||||
func DecodeGovStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], gov.ProposalsKeyPrefix):
|
||||
var proposalA, proposalB gov.Proposal
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &proposalA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &proposalB)
|
||||
return fmt.Sprintf("%v\n%v", proposalA, proposalB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], gov.ActiveProposalQueuePrefix),
|
||||
bytes.Equal(kvA.Key[:1], gov.InactiveProposalQueuePrefix),
|
||||
bytes.Equal(kvA.Key[:1], gov.ProposalIDKey):
|
||||
proposalIDA := binary.LittleEndian.Uint64(kvA.Value)
|
||||
proposalIDB := binary.LittleEndian.Uint64(kvB.Value)
|
||||
return fmt.Sprintf("proposalIDA: %d\nProposalIDB: %d", proposalIDA, proposalIDB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], gov.DepositsKeyPrefix):
|
||||
var depositA, depositB gov.Deposit
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &depositA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &depositB)
|
||||
return fmt.Sprintf("%v\n%v", depositA, depositB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], gov.VotesKeyPrefix):
|
||||
var voteA, voteB gov.Vote
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &voteA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &voteB)
|
||||
return fmt.Sprintf("%v\n%v", voteA, voteB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid governance key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
||||
|
||||
// DecodeSupplyStore unmarshals the KVPair's Value to the corresponding supply type
|
||||
func DecodeSupplyStore(cdcA, cdcB *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], supply.SupplyKey):
|
||||
var supplyA, supplyB supply.Supply
|
||||
cdcA.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &supplyA)
|
||||
cdcB.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &supplyB)
|
||||
return fmt.Sprintf("%v\n%v", supplyB, supplyB)
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid supply key %X", kvA.Key))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,10 +1,7 @@
|
|||
package simapp
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
@ -15,13 +12,6 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/x/auth"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution"
|
||||
distr "github.com/cosmos/cosmos-sdk/x/distribution"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
)
|
||||
|
@ -38,322 +28,40 @@ func makeTestCodec() (cdc *codec.Codec) {
|
|||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
auth.RegisterCodec(cdc)
|
||||
distr.RegisterCodec(cdc)
|
||||
gov.RegisterCodec(cdc)
|
||||
staking.RegisterCodec(cdc)
|
||||
supply.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestGetSimulationLog(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
decoders := make(sdk.StoreDecoderRegistry)
|
||||
decoders[auth.StoreKey] = func(cdc *codec.Codec, kvAs, kvBs cmn.KVPair) string { return "10" }
|
||||
|
||||
tests := []struct {
|
||||
store string
|
||||
kvPairs []cmn.KVPair
|
||||
expectedLog string
|
||||
}{
|
||||
{auth.StoreKey, []cmn.KVPair{
|
||||
{Key: auth.AddressStoreKey(delAddr1), Value: cdc.MustMarshalBinaryBare(auth.BaseAccount{})},
|
||||
{Key: auth.AddressStoreKey(delAddr1), Value: cdc.MustMarshalBinaryBare(auth.BaseAccount{})},
|
||||
}},
|
||||
{mint.StoreKey, []cmn.KVPair{
|
||||
{Key: mint.MinterKey, Value: cdc.MustMarshalBinaryLengthPrefixed(mint.Minter{})},
|
||||
{Key: mint.MinterKey, Value: cdc.MustMarshalBinaryLengthPrefixed(mint.Minter{})},
|
||||
}},
|
||||
{staking.StoreKey, []cmn.KVPair{
|
||||
{Key: staking.LastValidatorPowerKey, Value: valAddr1.Bytes()},
|
||||
{Key: staking.LastValidatorPowerKey, Value: valAddr1.Bytes()},
|
||||
}},
|
||||
{gov.StoreKey, []cmn.KVPair{
|
||||
{Key: gov.VoteKey(1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(gov.Vote{})},
|
||||
{Key: gov.VoteKey(1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(gov.Vote{})},
|
||||
}},
|
||||
{distribution.StoreKey, []cmn.KVPair{
|
||||
{Key: distr.ProposerKey, Value: consAddr1.Bytes()},
|
||||
{Key: distr.ProposerKey, Value: consAddr1.Bytes()},
|
||||
}},
|
||||
{slashing.StoreKey, []cmn.KVPair{
|
||||
{Key: slashing.GetValidatorMissedBlockBitArrayKey(consAddr1, 6), Value: cdc.MustMarshalBinaryLengthPrefixed(true)},
|
||||
{Key: slashing.GetValidatorMissedBlockBitArrayKey(consAddr1, 6), Value: cdc.MustMarshalBinaryLengthPrefixed(true)},
|
||||
}},
|
||||
{supply.StoreKey, []cmn.KVPair{
|
||||
{Key: supply.SupplyKey, Value: cdc.MustMarshalBinaryLengthPrefixed(supply.NewSupply(sdk.Coins{}))},
|
||||
{Key: supply.SupplyKey, Value: cdc.MustMarshalBinaryLengthPrefixed(supply.NewSupply(sdk.Coins{}))},
|
||||
}},
|
||||
{"Empty", []cmn.KVPair{{}, {}}},
|
||||
{"OtherStore", []cmn.KVPair{
|
||||
{Key: []byte("key"), Value: []byte("value")},
|
||||
{Key: []byte("key"), Value: []byte("other_value")},
|
||||
}},
|
||||
{
|
||||
"Empty",
|
||||
[]cmn.KVPair{{}},
|
||||
"",
|
||||
},
|
||||
{
|
||||
auth.StoreKey,
|
||||
[]cmn.KVPair{{Key: auth.GlobalAccountNumberKey, Value: cdc.MustMarshalBinaryLengthPrefixed(uint64(10))}},
|
||||
"10",
|
||||
},
|
||||
{
|
||||
"OtherStore",
|
||||
[]cmn.KVPair{{Key: []byte("key"), Value: []byte("value")}},
|
||||
fmt.Sprintf("store A %X => %X\nstore B %X => %X\n", []byte("key"), []byte("value"), []byte("key"), []byte("value")),
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.store, func(t *testing.T) {
|
||||
require.NotPanics(t, func() { GetSimulationLog(tt.store, cdc, cdc, tt.kvPairs) }, tt.store)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeAccountStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
acc := auth.NewBaseAccountWithAddress(delAddr1)
|
||||
globalAccNumber := uint64(10)
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: auth.AddressStoreKey(delAddr1), Value: cdc.MustMarshalBinaryBare(acc)},
|
||||
cmn.KVPair{Key: auth.GlobalAccountNumberKey, Value: cdc.MustMarshalBinaryLengthPrefixed(globalAccNumber)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"Minter", fmt.Sprintf("%v\n%v", acc, acc)},
|
||||
{"GlobalAccNumber", fmt.Sprintf("GlobalAccNumberA: %d\nGlobalAccNumberB: %d", globalAccNumber, globalAccNumber)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeAccountStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeAccountStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeMintStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
minter := mint.NewMinter(sdk.OneDec(), sdk.NewDec(15))
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: mint.MinterKey, Value: cdc.MustMarshalBinaryLengthPrefixed(minter)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"Minter", fmt.Sprintf("%v\n%v", minter, minter)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeMintStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeMintStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeDistributionStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
decCoins := sdk.DecCoins{sdk.NewDecCoinFromDec(sdk.DefaultBondDenom, sdk.OneDec())}
|
||||
feePool := distr.InitialFeePool()
|
||||
feePool.CommunityPool = decCoins
|
||||
info := distr.NewDelegatorStartingInfo(2, sdk.OneDec(), 200)
|
||||
outstanding := distr.ValidatorOutstandingRewards{decCoins[0]}
|
||||
commission := distr.ValidatorAccumulatedCommission{decCoins[0]}
|
||||
historicalRewards := distr.NewValidatorHistoricalRewards(decCoins, 100)
|
||||
currentRewards := distr.NewValidatorCurrentRewards(decCoins, 5)
|
||||
slashEvent := distr.NewValidatorSlashEvent(10, sdk.OneDec())
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: distr.FeePoolKey, Value: cdc.MustMarshalBinaryLengthPrefixed(feePool)},
|
||||
cmn.KVPair{Key: distr.ProposerKey, Value: consAddr1.Bytes()},
|
||||
cmn.KVPair{Key: distr.GetValidatorOutstandingRewardsKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(outstanding)},
|
||||
cmn.KVPair{Key: distr.GetDelegatorWithdrawAddrKey(delAddr1), Value: delAddr1.Bytes()},
|
||||
cmn.KVPair{Key: distr.GetDelegatorStartingInfoKey(valAddr1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(info)},
|
||||
cmn.KVPair{Key: distr.GetValidatorHistoricalRewardsKey(valAddr1, 100), Value: cdc.MustMarshalBinaryLengthPrefixed(historicalRewards)},
|
||||
cmn.KVPair{Key: distr.GetValidatorCurrentRewardsKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(currentRewards)},
|
||||
cmn.KVPair{Key: distr.GetValidatorAccumulatedCommissionKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(commission)},
|
||||
cmn.KVPair{Key: distr.GetValidatorSlashEventKeyPrefix(valAddr1, 13), Value: cdc.MustMarshalBinaryLengthPrefixed(slashEvent)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"FeePool", fmt.Sprintf("%v\n%v", feePool, feePool)},
|
||||
{"Proposer", fmt.Sprintf("%v\n%v", consAddr1, consAddr1)},
|
||||
{"ValidatorOutstandingRewards", fmt.Sprintf("%v\n%v", outstanding, outstanding)},
|
||||
{"DelegatorWithdrawAddr", fmt.Sprintf("%v\n%v", delAddr1, delAddr1)},
|
||||
{"DelegatorStartingInfo", fmt.Sprintf("%v\n%v", info, info)},
|
||||
{"ValidatorHistoricalRewards", fmt.Sprintf("%v\n%v", historicalRewards, historicalRewards)},
|
||||
{"ValidatorCurrentRewards", fmt.Sprintf("%v\n%v", currentRewards, currentRewards)},
|
||||
{"ValidatorAccumulatedCommission", fmt.Sprintf("%v\n%v", commission, commission)},
|
||||
{"ValidatorSlashEvent", fmt.Sprintf("%v\n%v", slashEvent, slashEvent)},
|
||||
{"other", ""},
|
||||
}
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeDistributionStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeDistributionStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeStakingStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
bondTime := time.Now().UTC()
|
||||
|
||||
val := staking.NewValidator(valAddr1, delPk1, staking.NewDescription("test", "test", "test", "test", "test"))
|
||||
del := staking.NewDelegation(delAddr1, valAddr1, sdk.OneDec())
|
||||
ubd := staking.NewUnbondingDelegation(delAddr1, valAddr1, 15, bondTime, sdk.OneInt())
|
||||
red := staking.NewRedelegation(delAddr1, valAddr1, valAddr1, 12, bondTime, sdk.OneInt(), sdk.OneDec())
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: staking.LastTotalPowerKey, Value: cdc.MustMarshalBinaryLengthPrefixed(sdk.OneInt())},
|
||||
cmn.KVPair{Key: staking.GetValidatorKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(val)},
|
||||
cmn.KVPair{Key: staking.LastValidatorPowerKey, Value: valAddr1.Bytes()},
|
||||
cmn.KVPair{Key: staking.GetDelegationKey(delAddr1, valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(del)},
|
||||
cmn.KVPair{Key: staking.GetUBDKey(delAddr1, valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(ubd)},
|
||||
cmn.KVPair{Key: staking.GetREDKey(delAddr1, valAddr1, valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(red)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"LastTotalPower", fmt.Sprintf("%v\n%v", sdk.OneInt(), sdk.OneInt())},
|
||||
{"Validator", fmt.Sprintf("%v\n%v", val, val)},
|
||||
{"LastValidatorPower/ValidatorsByConsAddr/ValidatorsByPowerIndex", fmt.Sprintf("%v\n%v", valAddr1, valAddr1)},
|
||||
{"Delegation", fmt.Sprintf("%v\n%v", del, del)},
|
||||
{"UnbondingDelegation", fmt.Sprintf("%v\n%v", ubd, ubd)},
|
||||
{"Redelegation", fmt.Sprintf("%v\n%v", red, red)},
|
||||
{"other", ""},
|
||||
}
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStakingStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStakingStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeSlashingStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
info := slashing.NewValidatorSigningInfo(consAddr1, 0, 1, time.Now().UTC(), false, 0)
|
||||
bechPK := sdk.MustBech32ifyAccPub(delPk1)
|
||||
missed := true
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: slashing.GetValidatorSigningInfoKey(consAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(info)},
|
||||
cmn.KVPair{Key: slashing.GetValidatorMissedBlockBitArrayKey(consAddr1, 6), Value: cdc.MustMarshalBinaryLengthPrefixed(missed)},
|
||||
cmn.KVPair{Key: slashing.GetAddrPubkeyRelationKey(delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(delPk1)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"ValidatorSigningInfo", fmt.Sprintf("%v\n%v", info, info)},
|
||||
{"ValidatorMissedBlockBitArray", fmt.Sprintf("missedA: %v\nmissedB: %v", missed, missed)},
|
||||
{"AddrPubkeyRelation", fmt.Sprintf("PubKeyA: %s\nPubKeyB: %s", bechPK, bechPK)},
|
||||
{"other", ""},
|
||||
}
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeSlashingStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeSlashingStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeGovStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
endTime := time.Now().UTC()
|
||||
|
||||
content := gov.ContentFromProposalType("test", "test", gov.ProposalTypeText)
|
||||
proposal := gov.NewProposal(content, 1, endTime, endTime.Add(24*time.Hour))
|
||||
proposalIDBz := make([]byte, 8)
|
||||
binary.LittleEndian.PutUint64(proposalIDBz, 1)
|
||||
deposit := gov.NewDeposit(1, delAddr1, sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, sdk.OneInt())))
|
||||
vote := gov.NewVote(1, delAddr1, gov.OptionYes)
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: gov.ProposalKey(1), Value: cdc.MustMarshalBinaryLengthPrefixed(proposal)},
|
||||
cmn.KVPair{Key: gov.InactiveProposalQueueKey(1, endTime), Value: proposalIDBz},
|
||||
cmn.KVPair{Key: gov.DepositKey(1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(deposit)},
|
||||
cmn.KVPair{Key: gov.VoteKey(1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(vote)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"proposals", fmt.Sprintf("%v\n%v", proposal, proposal)},
|
||||
{"proposal IDs", "proposalIDA: 1\nProposalIDB: 1"},
|
||||
{"deposits", fmt.Sprintf("%v\n%v", deposit, deposit)},
|
||||
{"votes", fmt.Sprintf("%v\n%v", vote, vote)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeGovStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeGovStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestDecodeSupplyStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
totalSupply := supply.NewSupply(sdk.NewCoins(sdk.NewInt64Coin(sdk.DefaultBondDenom, 1000)))
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: supply.SupplyKey, Value: cdc.MustMarshalBinaryLengthPrefixed(totalSupply)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"Supply", fmt.Sprintf("%v\n%v", totalSupply, totalSupply)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeSupplyStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeSupplyStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
require.Equal(t, tt.expectedLog, GetSimulationLog(tt.store, decoders, cdc, tt.kvPairs, tt.kvPairs), tt.store)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
|
|
@ -18,7 +18,7 @@ func KVStoreReversePrefixIterator(kvs KVStore, prefix []byte) Iterator {
|
|||
|
||||
// DiffKVStores compares two KVstores and returns all the key/value pairs
|
||||
// that differ from one another. It also skips value comparison for a set of provided prefixes
|
||||
func DiffKVStores(a KVStore, b KVStore, prefixesToSkip [][]byte) (kvs []cmn.KVPair) {
|
||||
func DiffKVStores(a KVStore, b KVStore, prefixesToSkip [][]byte) (kvAs, kvBs []cmn.KVPair) {
|
||||
iterA := a.Iterator(nil, nil)
|
||||
iterB := b.Iterator(nil, nil)
|
||||
|
||||
|
@ -36,7 +36,8 @@ func DiffKVStores(a KVStore, b KVStore, prefixesToSkip [][]byte) (kvs []cmn.KVPa
|
|||
iterB.Next()
|
||||
}
|
||||
if !bytes.Equal(kvA.Key, kvB.Key) {
|
||||
kvs = append(kvs, []cmn.KVPair{kvA, kvB}...)
|
||||
kvAs = append(kvAs, kvA)
|
||||
kvBs = append(kvBs, kvB)
|
||||
}
|
||||
compareValue := true
|
||||
for _, prefix := range prefixesToSkip {
|
||||
|
@ -46,7 +47,8 @@ func DiffKVStores(a KVStore, b KVStore, prefixesToSkip [][]byte) (kvs []cmn.KVPa
|
|||
}
|
||||
}
|
||||
if compareValue && !bytes.Equal(kvA.Value, kvB.Value) {
|
||||
kvs = append(kvs, []cmn.KVPair{kvA, kvB}...)
|
||||
kvAs = append(kvAs, kvA)
|
||||
kvBs = append(kvBs, kvB)
|
||||
}
|
||||
}
|
||||
return
|
||||
|
|
|
@ -3,6 +3,7 @@ Package module contains application module patterns and associated "manager" fun
|
|||
The module pattern has been broken down by:
|
||||
- independent module functionality (AppModuleBasic)
|
||||
- inter-dependent module genesis functionality (AppModuleGenesis)
|
||||
- inter-dependent module simulation functionality (AppModuleSimulation)
|
||||
- inter-dependent module full functionality (AppModule)
|
||||
|
||||
inter-dependent module functionality is module functionality which somehow
|
||||
|
@ -41,6 +42,7 @@ import (
|
|||
)
|
||||
|
||||
//__________________________________________________________________________________________
|
||||
|
||||
// AppModuleBasic is the standard form for basic non-dependant elements of an application module.
|
||||
type AppModuleBasic interface {
|
||||
Name() string
|
||||
|
@ -56,9 +58,10 @@ type AppModuleBasic interface {
|
|||
GetQueryCmd(*codec.Codec) *cobra.Command
|
||||
}
|
||||
|
||||
// collections of AppModuleBasic
|
||||
// BasicManager is a collection of AppModuleBasic
|
||||
type BasicManager map[string]AppModuleBasic
|
||||
|
||||
// NewBasicManager creates a new BasicManager object
|
||||
func NewBasicManager(modules ...AppModuleBasic) BasicManager {
|
||||
moduleMap := make(map[string]AppModuleBasic)
|
||||
for _, module := range modules {
|
||||
|
@ -67,14 +70,14 @@ func NewBasicManager(modules ...AppModuleBasic) BasicManager {
|
|||
return moduleMap
|
||||
}
|
||||
|
||||
// RegisterCodecs registers all module codecs
|
||||
// RegisterCodec registers all module codecs
|
||||
func (bm BasicManager) RegisterCodec(cdc *codec.Codec) {
|
||||
for _, b := range bm {
|
||||
b.RegisterCodec(cdc)
|
||||
}
|
||||
}
|
||||
|
||||
// Provided default genesis information for all modules
|
||||
// DefaultGenesis provides default genesis information for all modules
|
||||
func (bm BasicManager) DefaultGenesis() map[string]json.RawMessage {
|
||||
genesis := make(map[string]json.RawMessage)
|
||||
for _, b := range bm {
|
||||
|
@ -83,7 +86,7 @@ func (bm BasicManager) DefaultGenesis() map[string]json.RawMessage {
|
|||
return genesis
|
||||
}
|
||||
|
||||
// Provided default genesis information for all modules
|
||||
// ValidateGenesis performs genesis state validation for all modules
|
||||
func (bm BasicManager) ValidateGenesis(genesis map[string]json.RawMessage) error {
|
||||
for _, b := range bm {
|
||||
if err := b.ValidateGenesis(genesis[b.Name()]); err != nil {
|
||||
|
@ -93,14 +96,14 @@ func (bm BasicManager) ValidateGenesis(genesis map[string]json.RawMessage) error
|
|||
return nil
|
||||
}
|
||||
|
||||
// RegisterRestRoutes registers all module rest routes
|
||||
// RegisterRESTRoutes registers all module rest routes
|
||||
func (bm BasicManager) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
for _, b := range bm {
|
||||
b.RegisterRESTRoutes(ctx, rtr)
|
||||
}
|
||||
}
|
||||
|
||||
// add all tx commands to the rootTxCmd
|
||||
// AddTxCommands adds all tx commands to the rootTxCmd
|
||||
func (bm BasicManager) AddTxCommands(rootTxCmd *cobra.Command, cdc *codec.Codec) {
|
||||
for _, b := range bm {
|
||||
if cmd := b.GetTxCmd(cdc); cmd != nil {
|
||||
|
@ -109,7 +112,7 @@ func (bm BasicManager) AddTxCommands(rootTxCmd *cobra.Command, cdc *codec.Codec)
|
|||
}
|
||||
}
|
||||
|
||||
// add all query commands to the rootQueryCmd
|
||||
// AddQueryCommands adds all query commands to the rootQueryCmd
|
||||
func (bm BasicManager) AddQueryCommands(rootQueryCmd *cobra.Command, cdc *codec.Codec) {
|
||||
for _, b := range bm {
|
||||
if cmd := b.GetQueryCmd(cdc); cmd != nil {
|
||||
|
@ -119,6 +122,7 @@ func (bm BasicManager) AddQueryCommands(rootQueryCmd *cobra.Command, cdc *codec.
|
|||
}
|
||||
|
||||
//_________________________________________________________
|
||||
|
||||
// AppModuleGenesis is the standard form for an application module genesis functions
|
||||
type AppModuleGenesis interface {
|
||||
AppModuleBasic
|
||||
|
@ -126,9 +130,17 @@ type AppModuleGenesis interface {
|
|||
ExportGenesis(sdk.Context) json.RawMessage
|
||||
}
|
||||
|
||||
// AppModuleSimulation defines the standard functions that every module should expose
|
||||
// for the SDK blockchain simulator
|
||||
type AppModuleSimulation interface {
|
||||
// register a func to decode the each module's defined types from their corresponding store key
|
||||
RegisterStoreDecoder(sdk.StoreDecoderRegistry)
|
||||
}
|
||||
|
||||
// AppModule is the standard form for an application module
|
||||
type AppModule interface {
|
||||
AppModuleGenesis
|
||||
AppModuleSimulation
|
||||
|
||||
// registers
|
||||
RegisterInvariants(sdk.InvariantRegistry)
|
||||
|
@ -139,12 +151,14 @@ type AppModule interface {
|
|||
QuerierRoute() string
|
||||
NewQuerierHandler() sdk.Querier
|
||||
|
||||
// ABCI
|
||||
BeginBlock(sdk.Context, abci.RequestBeginBlock)
|
||||
EndBlock(sdk.Context, abci.RequestEndBlock) []abci.ValidatorUpdate
|
||||
}
|
||||
|
||||
//___________________________
|
||||
// app module
|
||||
|
||||
// GenesisOnlyAppModule is an AppModule that only has import/export functionality
|
||||
type GenesisOnlyAppModule struct {
|
||||
AppModuleGenesis
|
||||
}
|
||||
|
@ -156,31 +170,35 @@ func NewGenesisOnlyAppModule(amg AppModuleGenesis) AppModule {
|
|||
}
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants is a placeholder function register no invariants
|
||||
func (GenesisOnlyAppModule) RegisterInvariants(_ sdk.InvariantRegistry) {}
|
||||
|
||||
// module message route ngame
|
||||
// RegisterStoreDecoder empty store decoder registry
|
||||
func (GenesisOnlyAppModule) RegisterStoreDecoder(_ sdk.StoreDecoderRegistry) {}
|
||||
|
||||
// Route empty module message route
|
||||
func (GenesisOnlyAppModule) Route() string { return "" }
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an empty module handler
|
||||
func (GenesisOnlyAppModule) NewHandler() sdk.Handler { return nil }
|
||||
|
||||
// module querier route ngame
|
||||
// QuerierRoute returns an empty module querier route
|
||||
func (GenesisOnlyAppModule) QuerierRoute() string { return "" }
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns an empty module querier
|
||||
func (gam GenesisOnlyAppModule) NewQuerierHandler() sdk.Querier { return nil }
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns an empty module begin-block
|
||||
func (gam GenesisOnlyAppModule) BeginBlock(ctx sdk.Context, req abci.RequestBeginBlock) {}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns an empty module end-block
|
||||
func (GenesisOnlyAppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
// module manager provides the high level utility for managing and executing
|
||||
|
||||
// Manager defines a module manager that provides the high level utility for managing and executing
|
||||
// operations for a group of modules
|
||||
type Manager struct {
|
||||
Modules map[string]AppModule
|
||||
|
@ -190,7 +208,7 @@ type Manager struct {
|
|||
OrderEndBlockers []string
|
||||
}
|
||||
|
||||
// NewModuleManager creates a new Manager object
|
||||
// NewManager creates a new Manager object
|
||||
func NewManager(modules ...AppModule) *Manager {
|
||||
|
||||
moduleMap := make(map[string]AppModule)
|
||||
|
@ -209,34 +227,34 @@ func NewManager(modules ...AppModule) *Manager {
|
|||
}
|
||||
}
|
||||
|
||||
// set the order of init genesis calls
|
||||
// SetOrderInitGenesis sets the order of init genesis calls
|
||||
func (m *Manager) SetOrderInitGenesis(moduleNames ...string) {
|
||||
m.OrderInitGenesis = moduleNames
|
||||
}
|
||||
|
||||
// set the order of export genesis calls
|
||||
// SetOrderExportGenesis sets the order of export genesis calls
|
||||
func (m *Manager) SetOrderExportGenesis(moduleNames ...string) {
|
||||
m.OrderExportGenesis = moduleNames
|
||||
}
|
||||
|
||||
// set the order of set begin-blocker calls
|
||||
// SetOrderBeginBlockers sets the order of set begin-blocker calls
|
||||
func (m *Manager) SetOrderBeginBlockers(moduleNames ...string) {
|
||||
m.OrderBeginBlockers = moduleNames
|
||||
}
|
||||
|
||||
// set the order of set end-blocker calls
|
||||
// SetOrderEndBlockers sets the order of set end-blocker calls
|
||||
func (m *Manager) SetOrderEndBlockers(moduleNames ...string) {
|
||||
m.OrderEndBlockers = moduleNames
|
||||
}
|
||||
|
||||
// register all module routes and module querier routes
|
||||
// RegisterInvariants registers all module routes and module querier routes
|
||||
func (m *Manager) RegisterInvariants(ir sdk.InvariantRegistry) {
|
||||
for _, module := range m.Modules {
|
||||
module.RegisterInvariants(ir)
|
||||
}
|
||||
}
|
||||
|
||||
// register all module routes and module querier routes
|
||||
// RegisterRoutes registers all module routes and module querier routes
|
||||
func (m *Manager) RegisterRoutes(router sdk.Router, queryRouter sdk.QueryRouter) {
|
||||
for _, module := range m.Modules {
|
||||
if module.Route() != "" {
|
||||
|
@ -248,7 +266,7 @@ func (m *Manager) RegisterRoutes(router sdk.Router, queryRouter sdk.QueryRouter)
|
|||
}
|
||||
}
|
||||
|
||||
// perform init genesis functionality for modules
|
||||
// InitGenesis performs init genesis functionality for modules
|
||||
func (m *Manager) InitGenesis(ctx sdk.Context, genesisData map[string]json.RawMessage) abci.ResponseInitChain {
|
||||
var validatorUpdates []abci.ValidatorUpdate
|
||||
for _, moduleName := range m.OrderInitGenesis {
|
||||
|
@ -271,7 +289,7 @@ func (m *Manager) InitGenesis(ctx sdk.Context, genesisData map[string]json.RawMe
|
|||
}
|
||||
}
|
||||
|
||||
// perform export genesis functionality for modules
|
||||
// ExportGenesis performs export genesis functionality for modules
|
||||
func (m *Manager) ExportGenesis(ctx sdk.Context) map[string]json.RawMessage {
|
||||
genesisData := make(map[string]json.RawMessage)
|
||||
for _, moduleName := range m.OrderExportGenesis {
|
||||
|
@ -321,5 +339,3 @@ func (m *Manager) EndBlock(ctx sdk.Context, req abci.RequestEndBlock) abci.Respo
|
|||
Events: ctx.EventManager().ABCIEvents(),
|
||||
}
|
||||
}
|
||||
|
||||
// DONTCOVER
|
||||
|
|
|
@ -0,0 +1,27 @@
|
|||
package module
|
||||
|
||||
import (
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
)
|
||||
|
||||
// SimulationManager defines a simulation manager that provides the high level utility
|
||||
// for managing and executing simulation functionalities for a group of modules
|
||||
type SimulationManager struct {
|
||||
Modules map[string]AppModule
|
||||
StoreDecoders sdk.StoreDecoderRegistry
|
||||
}
|
||||
|
||||
// NewSimulationManager creates a new SimulationManager object
|
||||
func NewSimulationManager(moduleMap map[string]AppModule) *SimulationManager {
|
||||
return &SimulationManager{
|
||||
Modules: moduleMap,
|
||||
StoreDecoders: make(sdk.StoreDecoderRegistry),
|
||||
}
|
||||
}
|
||||
|
||||
// RegisterStoreDecoders registers each of the modules' store decoders into a map
|
||||
func (sm *SimulationManager) RegisterStoreDecoders() {
|
||||
for _, module := range sm.Modules {
|
||||
module.RegisterStoreDecoder(sm.StoreDecoders)
|
||||
}
|
||||
}
|
|
@ -3,6 +3,7 @@ package types
|
|||
import (
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
"github.com/cosmos/cosmos-sdk/store/types"
|
||||
)
|
||||
|
||||
|
@ -24,6 +25,10 @@ type (
|
|||
Iterator = types.Iterator
|
||||
)
|
||||
|
||||
// StoreDecoderRegistry defines each of the modules store decoders. Used for ImportExport
|
||||
// simulation.
|
||||
type StoreDecoderRegistry map[string]func(cdc *codec.Codec, kvA, kvB cmn.KVPair) string
|
||||
|
||||
// Iterator over all the keys with a certain prefix in ascending order
|
||||
func KVStorePrefixIterator(kvs KVStore, prefix []byte) Iterator {
|
||||
return types.KVStorePrefixIterator(kvs, prefix)
|
||||
|
@ -36,7 +41,7 @@ func KVStoreReversePrefixIterator(kvs KVStore, prefix []byte) Iterator {
|
|||
|
||||
// DiffKVStores compares two KVstores and returns all the key/value pairs
|
||||
// that differ from one another. It also skips value comparison for a set of provided prefixes
|
||||
func DiffKVStores(a KVStore, b KVStore, prefixesToSkip [][]byte) []cmn.KVPair {
|
||||
func DiffKVStores(a KVStore, b KVStore, prefixesToSkip [][]byte) (kvAs, kvBs []cmn.KVPair) {
|
||||
return types.DiffKVStores(a, b, prefixesToSkip)
|
||||
}
|
||||
|
||||
|
|
|
@ -13,33 +13,36 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/types/module"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/simulation"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/types"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the auth module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the auth module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return types.ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the auth module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
types.RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the auth
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return types.ModuleCdc.MustMarshalJSON(types.DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the auth module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data types.GenesisState
|
||||
err := types.ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -49,25 +52,38 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return types.ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the auth module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr, types.StoreKey)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the auth module.
|
||||
func (AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetTxCmd(cdc)
|
||||
}
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns the root query command for the auth module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(cdc)
|
||||
}
|
||||
|
||||
//___________________________
|
||||
// app module object
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the auth module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for auth module's types
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the auth module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
accountKeeper AccountKeeper
|
||||
}
|
||||
|
||||
|
@ -75,35 +91,37 @@ type AppModule struct {
|
|||
func NewAppModule(accountKeeper AccountKeeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
accountKeeper: accountKeeper,
|
||||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the auth module's name.
|
||||
func (AppModule) Name() string {
|
||||
return types.ModuleName
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants performs a no-op.
|
||||
func (AppModule) RegisterInvariants(_ sdk.InvariantRegistry) {}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the auth module.
|
||||
func (AppModule) Route() string { return "" }
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the auth module.
|
||||
func (AppModule) NewHandler() sdk.Handler { return nil }
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the auth module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return types.QuerierRoute
|
||||
}
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the auth module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.accountKeeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the auth module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
types.ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -111,16 +129,18 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the auth
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.accountKeeper)
|
||||
return types.ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns the begin blocker for the auth module.
|
||||
func (AppModule) BeginBlock(_ sdk.Context, _ abci.RequestBeginBlock) {}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the auth module. It returns no validator
|
||||
// updates.
|
||||
func (AppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,30 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/exported"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding auth type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], types.AddressStoreKeyPrefix):
|
||||
var accA, accB exported.Account
|
||||
cdc.MustUnmarshalBinaryBare(kvA.Value, &accA)
|
||||
cdc.MustUnmarshalBinaryBare(kvB.Value, &accB)
|
||||
return fmt.Sprintf("%v\n%v", accA, accB)
|
||||
case bytes.Equal(kvA.Key, types.GlobalAccountNumberKey):
|
||||
var globalAccNumberA, globalAccNumberB uint64
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &globalAccNumberA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &globalAccNumberB)
|
||||
return fmt.Sprintf("GlobalAccNumberA: %d\nGlobalAccNumberB: %d", globalAccNumberA, globalAccNumberB)
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid account key %X", kvA.Key))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,61 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto/ed25519"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth/types"
|
||||
)
|
||||
|
||||
var (
|
||||
delPk1 = ed25519.GenPrivKey().PubKey()
|
||||
delAddr1 = sdk.AccAddress(delPk1.Address())
|
||||
valAddr1 = sdk.ValAddress(delPk1.Address())
|
||||
consAddr1 = sdk.ConsAddress(delPk1.Address().Bytes())
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
types.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestDecodeStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
acc := types.NewBaseAccountWithAddress(delAddr1)
|
||||
globalAccNumber := uint64(10)
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: types.AddressStoreKey(delAddr1), Value: cdc.MustMarshalBinaryBare(acc)},
|
||||
cmn.KVPair{Key: types.GlobalAccountNumberKey, Value: cdc.MustMarshalBinaryLengthPrefixed(globalAccNumber)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"Account", fmt.Sprintf("%v\n%v", acc, acc)},
|
||||
{"GlobalAccNumber", fmt.Sprintf("GlobalAccNumberA: %d\nGlobalAccNumberB: %d", globalAccNumber, globalAccNumber)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package simulation
|
||||
package operations
|
||||
|
||||
import (
|
||||
"errors"
|
|
@ -21,23 +21,25 @@ import (
|
|||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the bank module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the bank module's name.
|
||||
func (AppModuleBasic) Name() string { return ModuleName }
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the bank module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) { RegisterCodec(cdc) }
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the bank
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the bank module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -47,23 +49,34 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the bank module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the bank module.
|
||||
func (AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetTxCmd(cdc)
|
||||
}
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the bank module.
|
||||
func (AppModuleBasic) GetQueryCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
//___________________________
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the bank module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder performs a no-op.
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(_ sdk.StoreDecoderRegistry) {}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the bank module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
accountKeeper types.AccountKeeper
|
||||
}
|
||||
|
@ -72,34 +85,36 @@ type AppModule struct {
|
|||
func NewAppModule(keeper Keeper, accountKeeper types.AccountKeeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
accountKeeper: accountKeeper,
|
||||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the bank module's name.
|
||||
func (AppModule) Name() string { return ModuleName }
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants registers the bank module invariants.
|
||||
func (am AppModule) RegisterInvariants(ir sdk.InvariantRegistry) {
|
||||
keeper.RegisterInvariants(ir, am.accountKeeper)
|
||||
}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the bank module.
|
||||
func (AppModule) Route() string { return RouterKey }
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the bank module.
|
||||
func (am AppModule) NewHandler() sdk.Handler { return NewHandler(am.keeper) }
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the bank module's querier route name.
|
||||
func (AppModule) QuerierRoute() string { return RouterKey }
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the bank module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return keeper.NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the bank module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -107,16 +122,18 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the bank
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock performs a no-op.
|
||||
func (AppModule) BeginBlock(_ sdk.Context, _ abci.RequestBeginBlock) {}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the bank module. It returns no validator
|
||||
// updates.
|
||||
func (AppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package bank
|
||||
package operations
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
@ -8,16 +8,16 @@ import (
|
|||
|
||||
"github.com/cosmos/cosmos-sdk/baseapp"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank/internal/keeper"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank/internal/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/mock"
|
||||
"github.com/cosmos/cosmos-sdk/x/simulation"
|
||||
)
|
||||
|
||||
// SendTx tests and runs a single msg send where both
|
||||
// SimulateMsgSend tests and runs a single msg send where both
|
||||
// accounts already exist.
|
||||
func SimulateMsgSend(mapper types.AccountKeeper, bk keeper.Keeper) simulation.Operation {
|
||||
handler := NewHandler(bk)
|
||||
func SimulateMsgSend(mapper types.AccountKeeper, bk bank.Keeper) simulation.Operation {
|
||||
handler := bank.NewHandler(bk)
|
||||
return func(r *rand.Rand, app *baseapp.BaseApp, ctx sdk.Context, accs []simulation.Account) (
|
||||
opMsg simulation.OperationMsg, fOps []simulation.FutureOperation, err error) {
|
||||
|
||||
|
@ -108,10 +108,10 @@ func sendAndVerifyMsgSend(app *baseapp.BaseApp, mapper types.AccountKeeper, msg
|
|||
return nil
|
||||
}
|
||||
|
||||
// SingleInputSendMsg tests and runs a single msg multisend, with one input and one output, where both
|
||||
// SimulateSingleInputMsgMultiSend tests and runs a single msg multisend, with one input and one output, where both
|
||||
// accounts already exist.
|
||||
func SimulateSingleInputMsgMultiSend(mapper types.AccountKeeper, bk keeper.Keeper) simulation.Operation {
|
||||
handler := NewHandler(bk)
|
||||
func SimulateSingleInputMsgMultiSend(mapper types.AccountKeeper, bk bank.Keeper) simulation.Operation {
|
||||
handler := bank.NewHandler(bk)
|
||||
return func(r *rand.Rand, app *baseapp.BaseApp, ctx sdk.Context, accs []simulation.Account) (
|
||||
opMsg simulation.OperationMsg, fOps []simulation.FutureOperation, err error) {
|
||||
|
|
@ -20,6 +20,7 @@ import (
|
|||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// AppModuleBasic defines the basic application module used by the crisis module.
|
||||
|
@ -61,9 +62,20 @@ func (AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
|||
// GetQueryCmd returns no root query command for the crisis module.
|
||||
func (AppModuleBasic) GetQueryCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the crisis module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder performs a no-op.
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(_ sdk.StoreDecoderRegistry) {}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the crisis module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
// NOTE: We store a reference to the keeper here so that after a module
|
||||
// manager is created, the invariants can be properly registered and
|
||||
|
@ -75,6 +87,7 @@ type AppModule struct {
|
|||
func NewAppModule(keeper *keeper.Keeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
}
|
||||
}
|
||||
|
@ -121,7 +134,7 @@ func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
|||
return types.ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// BeginBlock returns the begin blocker for the crisis module.
|
||||
// BeginBlock performs a no-op.
|
||||
func (AppModule) BeginBlock(_ sdk.Context, _ abci.RequestBeginBlock) {}
|
||||
|
||||
// EndBlock returns the end blocker for the crisis module. It returns no validator
|
||||
|
|
|
@ -14,33 +14,36 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/types/module"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/simulation"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/types"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the distribution module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the distribution module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the distribution module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the distribution
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the distribution module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -50,24 +53,38 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the distribution module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr, StoreKey)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the distribution module.
|
||||
func (AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetTxCmd(StoreKey, cdc)
|
||||
}
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns the root query command for the distribution module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(StoreKey, cdc)
|
||||
}
|
||||
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the distribution module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for distribution module's types
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the distribution module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
supplyKeeper types.SupplyKeeper
|
||||
}
|
||||
|
@ -76,42 +93,44 @@ type AppModule struct {
|
|||
func NewAppModule(keeper Keeper, supplyKeeper types.SupplyKeeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
supplyKeeper: supplyKeeper,
|
||||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the distribution module's name.
|
||||
func (AppModule) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants registers the distribution module invariants.
|
||||
func (am AppModule) RegisterInvariants(ir sdk.InvariantRegistry) {
|
||||
RegisterInvariants(ir, am.keeper)
|
||||
}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the distribution module.
|
||||
func (AppModule) Route() string {
|
||||
return RouterKey
|
||||
}
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the distribution module.
|
||||
func (am AppModule) NewHandler() sdk.Handler {
|
||||
return NewHandler(am.keeper)
|
||||
}
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the distribution module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return QuerierRoute
|
||||
}
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the distribution module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the distribution module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -119,18 +138,20 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the distribution
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns the begin blocker for the distribution module.
|
||||
func (am AppModule) BeginBlock(ctx sdk.Context, req abci.RequestBeginBlock) {
|
||||
BeginBlocker(ctx, req, am.keeper)
|
||||
}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the distribution module. It returns no validator
|
||||
// updates.
|
||||
func (AppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,70 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/keeper"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding distribution type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], keeper.FeePoolKey):
|
||||
var feePoolA, feePoolB types.FeePool
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &feePoolA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &feePoolB)
|
||||
return fmt.Sprintf("%v\n%v", feePoolA, feePoolB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.ProposerKey):
|
||||
return fmt.Sprintf("%v\n%v", sdk.ConsAddress(kvA.Value), sdk.ConsAddress(kvB.Value))
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.ValidatorOutstandingRewardsPrefix):
|
||||
var rewardsA, rewardsB types.ValidatorOutstandingRewards
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &rewardsA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &rewardsB)
|
||||
return fmt.Sprintf("%v\n%v", rewardsA, rewardsB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.DelegatorWithdrawAddrPrefix):
|
||||
return fmt.Sprintf("%v\n%v", sdk.AccAddress(kvA.Value), sdk.AccAddress(kvB.Value))
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.DelegatorStartingInfoPrefix):
|
||||
var infoA, infoB types.DelegatorStartingInfo
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &infoA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &infoB)
|
||||
return fmt.Sprintf("%v\n%v", infoA, infoB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.ValidatorHistoricalRewardsPrefix):
|
||||
var rewardsA, rewardsB types.ValidatorHistoricalRewards
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &rewardsA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &rewardsB)
|
||||
return fmt.Sprintf("%v\n%v", rewardsA, rewardsB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.ValidatorCurrentRewardsPrefix):
|
||||
var rewardsA, rewardsB types.ValidatorCurrentRewards
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &rewardsA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &rewardsB)
|
||||
return fmt.Sprintf("%v\n%v", rewardsA, rewardsB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.ValidatorAccumulatedCommissionPrefix):
|
||||
var commissionA, commissionB types.ValidatorAccumulatedCommission
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &commissionA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &commissionB)
|
||||
return fmt.Sprintf("%v\n%v", commissionA, commissionB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], keeper.ValidatorSlashEventPrefix):
|
||||
var eventA, eventB types.ValidatorSlashEvent
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &eventA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &eventB)
|
||||
return fmt.Sprintf("%v\n%v", eventA, eventB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid distribution key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,84 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto/ed25519"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/keeper"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution/types"
|
||||
)
|
||||
|
||||
var (
|
||||
delPk1 = ed25519.GenPrivKey().PubKey()
|
||||
delAddr1 = sdk.AccAddress(delPk1.Address())
|
||||
valAddr1 = sdk.ValAddress(delPk1.Address())
|
||||
consAddr1 = sdk.ConsAddress(delPk1.Address().Bytes())
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
types.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestDecodeDistributionStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
decCoins := sdk.DecCoins{sdk.NewDecCoinFromDec(sdk.DefaultBondDenom, sdk.OneDec())}
|
||||
feePool := types.InitialFeePool()
|
||||
feePool.CommunityPool = decCoins
|
||||
info := types.NewDelegatorStartingInfo(2, sdk.OneDec(), 200)
|
||||
outstanding := types.ValidatorOutstandingRewards{decCoins[0]}
|
||||
commission := types.ValidatorAccumulatedCommission{decCoins[0]}
|
||||
historicalRewards := types.NewValidatorHistoricalRewards(decCoins, 100)
|
||||
currentRewards := types.NewValidatorCurrentRewards(decCoins, 5)
|
||||
slashEvent := types.NewValidatorSlashEvent(10, sdk.OneDec())
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: keeper.FeePoolKey, Value: cdc.MustMarshalBinaryLengthPrefixed(feePool)},
|
||||
cmn.KVPair{Key: keeper.ProposerKey, Value: consAddr1.Bytes()},
|
||||
cmn.KVPair{Key: keeper.GetValidatorOutstandingRewardsKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(outstanding)},
|
||||
cmn.KVPair{Key: keeper.GetDelegatorWithdrawAddrKey(delAddr1), Value: delAddr1.Bytes()},
|
||||
cmn.KVPair{Key: keeper.GetDelegatorStartingInfoKey(valAddr1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(info)},
|
||||
cmn.KVPair{Key: keeper.GetValidatorHistoricalRewardsKey(valAddr1, 100), Value: cdc.MustMarshalBinaryLengthPrefixed(historicalRewards)},
|
||||
cmn.KVPair{Key: keeper.GetValidatorCurrentRewardsKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(currentRewards)},
|
||||
cmn.KVPair{Key: keeper.GetValidatorAccumulatedCommissionKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(commission)},
|
||||
cmn.KVPair{Key: keeper.GetValidatorSlashEventKeyPrefix(valAddr1, 13), Value: cdc.MustMarshalBinaryLengthPrefixed(slashEvent)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"FeePool", fmt.Sprintf("%v\n%v", feePool, feePool)},
|
||||
{"Proposer", fmt.Sprintf("%v\n%v", consAddr1, consAddr1)},
|
||||
{"ValidatorOutstandingRewards", fmt.Sprintf("%v\n%v", outstanding, outstanding)},
|
||||
{"DelegatorWithdrawAddr", fmt.Sprintf("%v\n%v", delAddr1, delAddr1)},
|
||||
{"DelegatorStartingInfo", fmt.Sprintf("%v\n%v", info, info)},
|
||||
{"ValidatorHistoricalRewards", fmt.Sprintf("%v\n%v", historicalRewards, historicalRewards)},
|
||||
{"ValidatorCurrentRewards", fmt.Sprintf("%v\n%v", currentRewards, currentRewards)},
|
||||
{"ValidatorAccumulatedCommission", fmt.Sprintf("%v\n%v", commission, commission)},
|
||||
{"ValidatorSlashEvent", fmt.Sprintf("%v\n%v", slashEvent, slashEvent)},
|
||||
{"other", ""},
|
||||
}
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package simulation
|
||||
package operations
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
@ -6,15 +6,14 @@ import (
|
|||
|
||||
"github.com/cosmos/cosmos-sdk/baseapp"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth"
|
||||
"github.com/cosmos/cosmos-sdk/x/distribution"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov"
|
||||
govsim "github.com/cosmos/cosmos-sdk/x/gov/simulation"
|
||||
govsimops "github.com/cosmos/cosmos-sdk/x/gov/simulation/operations"
|
||||
"github.com/cosmos/cosmos-sdk/x/simulation"
|
||||
)
|
||||
|
||||
// SimulateMsgSetWithdrawAddress generates a MsgSetWithdrawAddress with random values.
|
||||
func SimulateMsgSetWithdrawAddress(m auth.AccountKeeper, k distribution.Keeper) simulation.Operation {
|
||||
func SimulateMsgSetWithdrawAddress(k distribution.Keeper) simulation.Operation {
|
||||
handler := distribution.NewHandler(k)
|
||||
return func(r *rand.Rand, app *baseapp.BaseApp, ctx sdk.Context,
|
||||
accs []simulation.Account) (opMsg simulation.OperationMsg, fOps []simulation.FutureOperation, err error) {
|
||||
|
@ -39,7 +38,7 @@ func SimulateMsgSetWithdrawAddress(m auth.AccountKeeper, k distribution.Keeper)
|
|||
}
|
||||
|
||||
// SimulateMsgWithdrawDelegatorReward generates a MsgWithdrawDelegatorReward with random values.
|
||||
func SimulateMsgWithdrawDelegatorReward(m auth.AccountKeeper, k distribution.Keeper) simulation.Operation {
|
||||
func SimulateMsgWithdrawDelegatorReward(k distribution.Keeper) simulation.Operation {
|
||||
handler := distribution.NewHandler(k)
|
||||
return func(r *rand.Rand, app *baseapp.BaseApp, ctx sdk.Context,
|
||||
accs []simulation.Account) (opMsg simulation.OperationMsg, fOps []simulation.FutureOperation, err error) {
|
||||
|
@ -64,7 +63,7 @@ func SimulateMsgWithdrawDelegatorReward(m auth.AccountKeeper, k distribution.Kee
|
|||
}
|
||||
|
||||
// SimulateMsgWithdrawValidatorCommission generates a MsgWithdrawValidatorCommission with random values.
|
||||
func SimulateMsgWithdrawValidatorCommission(m auth.AccountKeeper, k distribution.Keeper) simulation.Operation {
|
||||
func SimulateMsgWithdrawValidatorCommission(k distribution.Keeper) simulation.Operation {
|
||||
handler := distribution.NewHandler(k)
|
||||
return func(r *rand.Rand, app *baseapp.BaseApp, ctx sdk.Context,
|
||||
accs []simulation.Account) (opMsg simulation.OperationMsg, fOps []simulation.FutureOperation, err error) {
|
||||
|
@ -88,7 +87,7 @@ func SimulateMsgWithdrawValidatorCommission(m auth.AccountKeeper, k distribution
|
|||
}
|
||||
|
||||
// SimulateCommunityPoolSpendProposalContent generates random community-pool-spend proposal content
|
||||
func SimulateCommunityPoolSpendProposalContent(k distribution.Keeper) govsim.ContentSimulator {
|
||||
func SimulateCommunityPoolSpendProposalContent(k distribution.Keeper) govsimops.ContentSimulator {
|
||||
return func(r *rand.Rand, _ *baseapp.BaseApp, ctx sdk.Context, accs []simulation.Account) gov.Content {
|
||||
recipientAcc := simulation.RandomAcc(r, accs)
|
||||
coins := sdk.Coins{}
|
|
@ -19,25 +19,27 @@ import (
|
|||
var (
|
||||
_ module.AppModuleGenesis = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the genesis accounts module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the genesis accounts module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec performs a no-op.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the genesis accounts
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(GenesisState{})
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the genesis accounts module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -47,17 +49,18 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers no REST routes for the genesis accounts module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(_ context.CLIContext, _ *mux.Router) {}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns no root tx command for the genesis accounts module.
|
||||
func (AppModuleBasic) GetTxCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the genesis accounts module.
|
||||
func (AppModuleBasic) GetQueryCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
// extra function from sdk.AppModuleBasic
|
||||
// iterate the genesis accounts and perform an operation at each of them
|
||||
|
||||
// IterateGenesisAccounts iterates over the genesis accounts and perform an operation at each of them
|
||||
// - to used by other modules
|
||||
func (AppModuleBasic) IterateGenesisAccounts(cdc *codec.Codec, appGenesis map[string]json.RawMessage,
|
||||
iterateFn func(exported.Account) (stop bool)) {
|
||||
|
@ -71,10 +74,21 @@ func (AppModuleBasic) IterateGenesisAccounts(cdc *codec.Codec, appGenesis map[st
|
|||
}
|
||||
}
|
||||
|
||||
//___________________________
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the genesis accounts module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder performs a no-op.
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(_ sdk.StoreDecoderRegistry) {}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the genesis accounts module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
accountKeeper types.AccountKeeper
|
||||
}
|
||||
|
||||
|
@ -83,11 +97,13 @@ func NewAppModule(accountKeeper types.AccountKeeper) module.AppModule {
|
|||
|
||||
return module.NewGenesisOnlyAppModule(AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
accountKeeper: accountKeeper,
|
||||
})
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the genesis accounts module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -95,7 +111,8 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the genesis accounts
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.accountKeeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
|
|
|
@ -18,25 +18,27 @@ import (
|
|||
var (
|
||||
_ module.AppModuleGenesis = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the genutil module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the genutil module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the genutil module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the genutil
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(GenesisState{})
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the genutil module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -46,19 +48,30 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the genutil module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(_ context.CLIContext, _ *mux.Router) {}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns no root tx command for the genutil module.
|
||||
func (AppModuleBasic) GetTxCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the genutil module.
|
||||
func (AppModuleBasic) GetQueryCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
//___________________________
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the auth module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for genutil module's types
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(_ sdk.StoreDecoderRegistry) {}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the genutil module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
accountKeeper types.AccountKeeper
|
||||
stakingKeeper types.StakingKeeper
|
||||
deliverTx deliverTxfn
|
||||
|
@ -70,20 +83,23 @@ func NewAppModule(accountKeeper types.AccountKeeper,
|
|||
|
||||
return module.NewGenesisOnlyAppModule(AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
accountKeeper: accountKeeper,
|
||||
stakingKeeper: stakingKeeper,
|
||||
deliverTx: deliverTx,
|
||||
})
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the genutil module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
return InitGenesis(ctx, ModuleCdc, am.stakingKeeper, am.deliverTx, genesisState)
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the genutil
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -17,15 +17,17 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/x/gov/client"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/simulation"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/types"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// AppModuleBasic - app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the gov module.
|
||||
type AppModuleBasic struct {
|
||||
proposalHandlers []client.ProposalHandler // proposal handlers which live in governance cli and rest
|
||||
}
|
||||
|
@ -37,24 +39,23 @@ func NewAppModuleBasic(proposalHandlers ...client.ProposalHandler) AppModuleBasi
|
|||
}
|
||||
}
|
||||
|
||||
var _ module.AppModuleBasic = AppModuleBasic{}
|
||||
|
||||
// Name - module name
|
||||
// Name returns the gov module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return types.ModuleName
|
||||
}
|
||||
|
||||
// RegisterCodec -register module codec
|
||||
// RegisterCodec registers the gov module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// DefaultGenesis - default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the gov
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// ValidateGenesis - module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the gov module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -64,7 +65,7 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// RegisterRESTRoutes - register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the gov module.
|
||||
func (a AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
var proposalRESTHandlers []rest.ProposalRESTHandler
|
||||
for _, proposalHandler := range a.proposalHandlers {
|
||||
|
@ -74,7 +75,7 @@ func (a AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Rout
|
|||
rest.RegisterRoutes(ctx, rtr, proposalRESTHandlers)
|
||||
}
|
||||
|
||||
// GetTxCmd gets the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the gov module.
|
||||
func (a AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
||||
|
||||
var proposalCLIHandlers []*cobra.Command
|
||||
|
@ -85,16 +86,28 @@ func (a AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
|||
return cli.GetTxCmd(StoreKey, cdc, proposalCLIHandlers)
|
||||
}
|
||||
|
||||
// GetQueryCmd gets the root query command of this module
|
||||
// GetQueryCmd returns the root query command for the gov module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(StoreKey, cdc)
|
||||
}
|
||||
|
||||
//___________________________
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule - app module object
|
||||
// AppModuleSimulation defines the module simulation functions used by the gov module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder performs a no-op.
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the gov module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
supplyKeeper types.SupplyKeeper
|
||||
}
|
||||
|
@ -103,12 +116,13 @@ type AppModule struct {
|
|||
func NewAppModule(keeper Keeper, supplyKeeper types.SupplyKeeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
supplyKeeper: supplyKeeper,
|
||||
}
|
||||
}
|
||||
|
||||
// Name - module name
|
||||
// Name returns the gov module's name.
|
||||
func (AppModule) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
@ -118,27 +132,28 @@ func (am AppModule) RegisterInvariants(ir sdk.InvariantRegistry) {
|
|||
RegisterInvariants(ir, am.keeper)
|
||||
}
|
||||
|
||||
// Route - module message route name
|
||||
// Route returns the message routing key for the gov module.
|
||||
func (AppModule) Route() string {
|
||||
return RouterKey
|
||||
}
|
||||
|
||||
// NewHandler - module handler
|
||||
// NewHandler returns an sdk.Handler for the gov module.
|
||||
func (am AppModule) NewHandler() sdk.Handler {
|
||||
return NewHandler(am.keeper)
|
||||
}
|
||||
|
||||
// QuerierRoute - module querier route name
|
||||
// QuerierRoute returns the gov module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return QuerierRoute
|
||||
}
|
||||
|
||||
// NewQuerierHandler - module querier
|
||||
// NewQuerierHandler returns no sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// InitGenesis - module init-genesis
|
||||
// InitGenesis performs genesis initialization for the gov module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -146,16 +161,18 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// ExportGenesis - module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the gov
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// BeginBlock - module begin-block
|
||||
// BeginBlock performs a no-op.
|
||||
func (AppModule) BeginBlock(_ sdk.Context, _ abci.RequestBeginBlock) {}
|
||||
|
||||
// EndBlock - module end-block
|
||||
// EndBlock returns the end blocker for the gov module. It returns no validator
|
||||
// updates.
|
||||
func (am AppModule) EndBlock(ctx sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
EndBlocker(ctx, am.keeper)
|
||||
return []abci.ValidatorUpdate{}
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/binary"
|
||||
"fmt"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding gov type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], types.ProposalsKeyPrefix):
|
||||
var proposalA, proposalB types.Proposal
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &proposalA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &proposalB)
|
||||
return fmt.Sprintf("%v\n%v", proposalA, proposalB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.ActiveProposalQueuePrefix),
|
||||
bytes.Equal(kvA.Key[:1], types.InactiveProposalQueuePrefix),
|
||||
bytes.Equal(kvA.Key[:1], types.ProposalIDKey):
|
||||
proposalIDA := binary.LittleEndian.Uint64(kvA.Value)
|
||||
proposalIDB := binary.LittleEndian.Uint64(kvB.Value)
|
||||
return fmt.Sprintf("proposalIDA: %d\nProposalIDB: %d", proposalIDA, proposalIDB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.DepositsKeyPrefix):
|
||||
var depositA, depositB types.Deposit
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &depositA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &depositB)
|
||||
return fmt.Sprintf("%v\n%v", depositA, depositB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.VotesKeyPrefix):
|
||||
var voteA, voteB types.Vote
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &voteA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &voteB)
|
||||
return fmt.Sprintf("%v\n%v", voteA, voteB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid governance key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,75 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
"fmt"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto/ed25519"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/gov/types"
|
||||
)
|
||||
|
||||
var (
|
||||
delPk1 = ed25519.GenPrivKey().PubKey()
|
||||
delAddr1 = sdk.AccAddress(delPk1.Address())
|
||||
valAddr1 = sdk.ValAddress(delPk1.Address())
|
||||
consAddr1 = sdk.ConsAddress(delPk1.Address().Bytes())
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
types.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestDecodeStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
endTime := time.Now().UTC()
|
||||
|
||||
content := types.ContentFromProposalType("test", "test", types.ProposalTypeText)
|
||||
proposal := types.NewProposal(content, 1, endTime, endTime.Add(24*time.Hour))
|
||||
proposalIDBz := make([]byte, 8)
|
||||
binary.LittleEndian.PutUint64(proposalIDBz, 1)
|
||||
deposit := types.NewDeposit(1, delAddr1, sdk.NewCoins(sdk.NewCoin(sdk.DefaultBondDenom, sdk.OneInt())))
|
||||
vote := types.NewVote(1, delAddr1, types.OptionYes)
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: types.ProposalKey(1), Value: cdc.MustMarshalBinaryLengthPrefixed(proposal)},
|
||||
cmn.KVPair{Key: types.InactiveProposalQueueKey(1, endTime), Value: proposalIDBz},
|
||||
cmn.KVPair{Key: types.DepositKey(1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(deposit)},
|
||||
cmn.KVPair{Key: types.VoteKey(1, delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(vote)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"proposals", fmt.Sprintf("%v\n%v", proposal, proposal)},
|
||||
{"proposal IDs", "proposalIDA: 1\nProposalIDB: 1"},
|
||||
{"deposits", fmt.Sprintf("%v\n%v", deposit, deposit)},
|
||||
{"votes", fmt.Sprintf("%v\n%v", vote, vote)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package simulation
|
||||
package operations
|
||||
|
||||
import (
|
||||
"fmt"
|
|
@ -14,32 +14,35 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/types/module"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint/simulation"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the mint module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
var _ module.AppModuleBasic = AppModuleBasic{}
|
||||
|
||||
// module name
|
||||
// Name returns the mint module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the mint module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the mint
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the mint module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -49,23 +52,36 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the mint module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns no root tx command for the mint module.
|
||||
func (AppModuleBasic) GetTxCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns the root query command for the mint module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(cdc)
|
||||
}
|
||||
|
||||
//___________________________
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the mint module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for mint module's types.
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the mint module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
}
|
||||
|
||||
|
@ -73,35 +89,37 @@ type AppModule struct {
|
|||
func NewAppModule(keeper Keeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the mint module's name.
|
||||
func (AppModule) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants registers the mint module invariants.
|
||||
func (am AppModule) RegisterInvariants(_ sdk.InvariantRegistry) {}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the mint module.
|
||||
func (AppModule) Route() string { return "" }
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the mint module.
|
||||
func (am AppModule) NewHandler() sdk.Handler { return nil }
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the mint module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return QuerierRoute
|
||||
}
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the mint module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the mint module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -109,18 +127,20 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the mint
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns the begin blocker for the mint module.
|
||||
func (am AppModule) BeginBlock(ctx sdk.Context, _ abci.RequestBeginBlock) {
|
||||
BeginBlocker(ctx, am.keeper)
|
||||
}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the mint module. It returns no validator
|
||||
// updates.
|
||||
func (AppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,24 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint/internal/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding mint type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key, types.MinterKey):
|
||||
var minterA, minterB types.Minter
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &minterA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &minterB)
|
||||
return fmt.Sprintf("%v\n%v", minterA, minterB)
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid mint key %X", kvA.Key))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,48 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/mint/internal/types"
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestDecodeStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
minter := types.NewMinter(sdk.OneDec(), sdk.NewDec(15))
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: types.MinterKey, Value: cdc.MustMarshalBinaryLengthPrefixed(minter)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"Minter", fmt.Sprintf("%v\n%v", minter, minter)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
|
@ -16,32 +16,31 @@ var (
|
|||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
)
|
||||
|
||||
const moduleName = "params"
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the params module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the params module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return moduleName
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the params module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
types.RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the params
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage { return nil }
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the params module.
|
||||
func (AppModuleBasic) ValidateGenesis(_ json.RawMessage) error { return nil }
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the params module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(_ context.CLIContext, _ *mux.Router) {}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns no root tx command for the params module.
|
||||
func (AppModuleBasic) GetTxCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the params module.
|
||||
func (AppModuleBasic) GetQueryCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
package simulation
|
||||
package operations
|
||||
|
||||
import (
|
||||
"encoding/json"
|
|
@ -15,34 +15,37 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/x/slashing/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing/internal/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing/simulation"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the slashing module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
var _ module.AppModuleBasic = AppModuleBasic{}
|
||||
|
||||
// module name
|
||||
// Name returns the slashing module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return types.ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the slashing module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the slashing
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the slashing module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -52,25 +55,38 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the slashing module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the slashing module.
|
||||
func (AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetTxCmd(cdc)
|
||||
}
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the slashing module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(StoreKey, cdc)
|
||||
}
|
||||
|
||||
//___________________________
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the slashing module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for slashing module's types
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the slashing module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
stakingKeeper types.StakingKeeper
|
||||
}
|
||||
|
@ -79,40 +95,42 @@ type AppModule struct {
|
|||
func NewAppModule(keeper Keeper, stakingKeeper types.StakingKeeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
stakingKeeper: stakingKeeper,
|
||||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the slashing module's name.
|
||||
func (AppModule) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants registers the slashing module invariants.
|
||||
func (am AppModule) RegisterInvariants(_ sdk.InvariantRegistry) {}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the slashing module.
|
||||
func (AppModule) Route() string {
|
||||
return RouterKey
|
||||
}
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the slashing module.
|
||||
func (am AppModule) NewHandler() sdk.Handler {
|
||||
return NewHandler(am.keeper)
|
||||
}
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the slashing module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return QuerierRoute
|
||||
}
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the slashing module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the slashing module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -120,18 +138,20 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the slashing
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns the begin blocker for the slashing module.
|
||||
func (am AppModule) BeginBlock(ctx sdk.Context, req abci.RequestBeginBlock) {
|
||||
BeginBlocker(ctx, req, am.keeper)
|
||||
}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the slashing module. It returns no validator
|
||||
// updates.
|
||||
func (AppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing/internal/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding slashing type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], types.ValidatorSigningInfoKey):
|
||||
var infoA, infoB types.ValidatorSigningInfo
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &infoA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &infoB)
|
||||
return fmt.Sprintf("%v\n%v", infoA, infoB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.ValidatorMissedBlockBitArrayKey):
|
||||
var missedA, missedB bool
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &missedA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &missedB)
|
||||
return fmt.Sprintf("missedA: %v\nmissedB: %v", missedA, missedB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.AddrPubkeyRelationKey):
|
||||
var pubKeyA, pubKeyB crypto.PubKey
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &pubKeyA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &pubKeyB)
|
||||
bechPKA := sdk.MustBech32ifyAccPub(pubKeyA)
|
||||
bechPKB := sdk.MustBech32ifyAccPub(pubKeyB)
|
||||
return fmt.Sprintf("PubKeyA: %s\nPubKeyB: %s", bechPKA, bechPKB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid slashing key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,66 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto/ed25519"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/slashing/internal/types"
|
||||
)
|
||||
|
||||
var (
|
||||
delPk1 = ed25519.GenPrivKey().PubKey()
|
||||
delAddr1 = sdk.AccAddress(delPk1.Address())
|
||||
valAddr1 = sdk.ValAddress(delPk1.Address())
|
||||
consAddr1 = sdk.ConsAddress(delPk1.Address().Bytes())
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
types.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestDecodeStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
info := types.NewValidatorSigningInfo(consAddr1, 0, 1, time.Now().UTC(), false, 0)
|
||||
bechPK := sdk.MustBech32ifyAccPub(delPk1)
|
||||
missed := true
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: types.GetValidatorSigningInfoKey(consAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(info)},
|
||||
cmn.KVPair{Key: types.GetValidatorMissedBlockBitArrayKey(consAddr1, 6), Value: cdc.MustMarshalBinaryLengthPrefixed(missed)},
|
||||
cmn.KVPair{Key: types.GetAddrPubkeyRelationKey(delAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(delPk1)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"ValidatorSigningInfo", fmt.Sprintf("%v\n%v", info, info)},
|
||||
{"ValidatorMissedBlockBitArray", fmt.Sprintf("missedA: %v\nmissedB: %v", missed, missed)},
|
||||
{"AddrPubkeyRelation", fmt.Sprintf("PubKeyA: %s\nPubKeyB: %s", bechPK, bechPK)},
|
||||
{"other", ""},
|
||||
}
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package simulation
|
||||
package operations
|
||||
|
||||
import (
|
||||
"fmt"
|
|
@ -18,35 +18,38 @@ import (
|
|||
authtypes "github.com/cosmos/cosmos-sdk/x/auth/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking/simulation"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking/types"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the staking module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
var _ module.AppModuleBasic = AppModuleBasic{}
|
||||
|
||||
// module name
|
||||
// Name returns the staking module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the staking module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the staking
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the staking module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -56,17 +59,17 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the staking module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the staking module.
|
||||
func (AppModuleBasic) GetTxCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetTxCmd(StoreKey, cdc)
|
||||
}
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the staking module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(StoreKey, cdc)
|
||||
}
|
||||
|
@ -92,9 +95,23 @@ func (AppModuleBasic) BuildCreateValidatorMsg(cliCtx context.CLIContext,
|
|||
return cli.BuildCreateValidatorMsg(cliCtx, txBldr)
|
||||
}
|
||||
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the staking module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for staking module's types
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the staking module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
distrKeeper types.DistributionKeeper
|
||||
accKeeper types.AccountKeeper
|
||||
|
@ -107,6 +124,7 @@ func NewAppModule(keeper Keeper, distrKeeper types.DistributionKeeper, accKeeper
|
|||
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
distrKeeper: distrKeeper,
|
||||
accKeeper: accKeeper,
|
||||
|
@ -114,53 +132,56 @@ func NewAppModule(keeper Keeper, distrKeeper types.DistributionKeeper, accKeeper
|
|||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the staking module's name.
|
||||
func (AppModule) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants registers the staking module invariants.
|
||||
func (am AppModule) RegisterInvariants(ir sdk.InvariantRegistry) {
|
||||
RegisterInvariants(ir, am.keeper)
|
||||
}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the staking module.
|
||||
func (AppModule) Route() string {
|
||||
return RouterKey
|
||||
}
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the staking module.
|
||||
func (am AppModule) NewHandler() sdk.Handler {
|
||||
return NewHandler(am.keeper)
|
||||
}
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the staking module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return QuerierRoute
|
||||
}
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the staking module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the staking module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
return InitGenesis(ctx, am.keeper, am.accKeeper, am.supplyKeeper, genesisState)
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the staking
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns the begin blocker for the staking module.
|
||||
func (AppModule) BeginBlock(_ sdk.Context, _ abci.RequestBeginBlock) {}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the staking module. It returns no validator
|
||||
// updates.
|
||||
func (am AppModule) EndBlock(ctx sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return EndBlocker(ctx, am.keeper)
|
||||
}
|
||||
|
|
|
@ -0,0 +1,57 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding staking type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], types.LastTotalPowerKey):
|
||||
var powerA, powerB sdk.Int
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &powerA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &powerB)
|
||||
return fmt.Sprintf("%v\n%v", powerA, powerB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.ValidatorsKey):
|
||||
var validatorA, validatorB types.Validator
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &validatorA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &validatorB)
|
||||
return fmt.Sprintf("%v\n%v", validatorA, validatorB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.LastValidatorPowerKey),
|
||||
bytes.Equal(kvA.Key[:1], types.ValidatorsByConsAddrKey),
|
||||
bytes.Equal(kvA.Key[:1], types.ValidatorsByPowerIndexKey):
|
||||
return fmt.Sprintf("%v\n%v", sdk.ValAddress(kvA.Value), sdk.ValAddress(kvB.Value))
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.DelegationKey):
|
||||
var delegationA, delegationB types.Delegation
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &delegationA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &delegationB)
|
||||
return fmt.Sprintf("%v\n%v", delegationA, delegationB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.UnbondingDelegationKey),
|
||||
bytes.Equal(kvA.Key[:1], types.UnbondingDelegationByValIndexKey):
|
||||
var ubdA, ubdB types.UnbondingDelegation
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &ubdA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &ubdB)
|
||||
return fmt.Sprintf("%v\n%v", ubdA, ubdB)
|
||||
|
||||
case bytes.Equal(kvA.Key[:1], types.RedelegationKey),
|
||||
bytes.Equal(kvA.Key[:1], types.RedelegationByValSrcIndexKey):
|
||||
var redA, redB types.Redelegation
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &redA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &redB)
|
||||
return fmt.Sprintf("%v\n%v", redA, redB)
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid staking key prefix %X", kvA.Key[:1]))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,75 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/crypto/ed25519"
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/staking/types"
|
||||
)
|
||||
|
||||
var (
|
||||
delPk1 = ed25519.GenPrivKey().PubKey()
|
||||
delAddr1 = sdk.AccAddress(delPk1.Address())
|
||||
valAddr1 = sdk.ValAddress(delPk1.Address())
|
||||
consAddr1 = sdk.ConsAddress(delPk1.Address().Bytes())
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
types.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
|
||||
func TestDecodeStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
bondTime := time.Now().UTC()
|
||||
|
||||
val := types.NewValidator(valAddr1, delPk1, types.NewDescription("test", "test", "test", "test", "test"))
|
||||
del := types.NewDelegation(delAddr1, valAddr1, sdk.OneDec())
|
||||
ubd := types.NewUnbondingDelegation(delAddr1, valAddr1, 15, bondTime, sdk.OneInt())
|
||||
red := types.NewRedelegation(delAddr1, valAddr1, valAddr1, 12, bondTime, sdk.OneInt(), sdk.OneDec())
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: types.LastTotalPowerKey, Value: cdc.MustMarshalBinaryLengthPrefixed(sdk.OneInt())},
|
||||
cmn.KVPair{Key: types.GetValidatorKey(valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(val)},
|
||||
cmn.KVPair{Key: types.LastValidatorPowerKey, Value: valAddr1.Bytes()},
|
||||
cmn.KVPair{Key: types.GetDelegationKey(delAddr1, valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(del)},
|
||||
cmn.KVPair{Key: types.GetUBDKey(delAddr1, valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(ubd)},
|
||||
cmn.KVPair{Key: types.GetREDKey(delAddr1, valAddr1, valAddr1), Value: cdc.MustMarshalBinaryLengthPrefixed(red)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"LastTotalPower", fmt.Sprintf("%v\n%v", sdk.OneInt(), sdk.OneInt())},
|
||||
{"Validator", fmt.Sprintf("%v\n%v", val, val)},
|
||||
{"LastValidatorPower/ValidatorsByConsAddr/ValidatorsByPowerIndex", fmt.Sprintf("%v\n%v", valAddr1, valAddr1)},
|
||||
{"Delegation", fmt.Sprintf("%v\n%v", del, del)},
|
||||
{"UnbondingDelegation", fmt.Sprintf("%v\n%v", ubd, ubd)},
|
||||
{"Redelegation", fmt.Sprintf("%v\n%v", red, red)},
|
||||
{"other", ""},
|
||||
}
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
package simulation
|
||||
package operations
|
||||
|
||||
import (
|
||||
"fmt"
|
|
@ -15,32 +15,35 @@ import (
|
|||
"github.com/cosmos/cosmos-sdk/x/supply/client/cli"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/client/rest"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/internal/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/simulation"
|
||||
)
|
||||
|
||||
var (
|
||||
_ module.AppModule = AppModule{}
|
||||
_ module.AppModuleBasic = AppModuleBasic{}
|
||||
_ module.AppModuleSimulation = AppModuleSimulation{}
|
||||
)
|
||||
|
||||
// app module basics object
|
||||
// AppModuleBasic defines the basic application module used by the supply module.
|
||||
type AppModuleBasic struct{}
|
||||
|
||||
// module name
|
||||
// Name returns the supply module's name.
|
||||
func (AppModuleBasic) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register module codec
|
||||
// RegisterCodec registers the supply module's types for the given codec.
|
||||
func (AppModuleBasic) RegisterCodec(cdc *codec.Codec) {
|
||||
RegisterCodec(cdc)
|
||||
}
|
||||
|
||||
// default genesis state
|
||||
// DefaultGenesis returns default genesis state as raw bytes for the supply
|
||||
// module.
|
||||
func (AppModuleBasic) DefaultGenesis() json.RawMessage {
|
||||
return ModuleCdc.MustMarshalJSON(DefaultGenesisState())
|
||||
}
|
||||
|
||||
// module validate genesis
|
||||
// ValidateGenesis performs genesis state validation for the supply module.
|
||||
func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
||||
var data GenesisState
|
||||
err := ModuleCdc.UnmarshalJSON(bz, &data)
|
||||
|
@ -50,22 +53,36 @@ func (AppModuleBasic) ValidateGenesis(bz json.RawMessage) error {
|
|||
return ValidateGenesis(data)
|
||||
}
|
||||
|
||||
// register rest routes
|
||||
// RegisterRESTRoutes registers the REST routes for the supply module.
|
||||
func (AppModuleBasic) RegisterRESTRoutes(ctx context.CLIContext, rtr *mux.Router) {
|
||||
rest.RegisterRoutes(ctx, rtr)
|
||||
}
|
||||
|
||||
// get the root tx command of this module
|
||||
// GetTxCmd returns the root tx command for the supply module.
|
||||
func (AppModuleBasic) GetTxCmd(_ *codec.Codec) *cobra.Command { return nil }
|
||||
|
||||
// get the root query command of this module
|
||||
// GetQueryCmd returns no root query command for the supply module.
|
||||
func (AppModuleBasic) GetQueryCmd(cdc *codec.Codec) *cobra.Command {
|
||||
return cli.GetQueryCmd(cdc)
|
||||
}
|
||||
|
||||
// app module
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModuleSimulation defines the module simulation functions used by the supply module.
|
||||
type AppModuleSimulation struct{}
|
||||
|
||||
// RegisterStoreDecoder registers a decoder for supply module's types
|
||||
func (AppModuleSimulation) RegisterStoreDecoder(sdr sdk.StoreDecoderRegistry) {
|
||||
sdr[StoreKey] = simulation.DecodeStore
|
||||
}
|
||||
|
||||
//____________________________________________________________________________
|
||||
|
||||
// AppModule implements an application module for the supply module.
|
||||
type AppModule struct {
|
||||
AppModuleBasic
|
||||
AppModuleSimulation
|
||||
|
||||
keeper Keeper
|
||||
ak types.AccountKeeper
|
||||
}
|
||||
|
@ -74,40 +91,42 @@ type AppModule struct {
|
|||
func NewAppModule(keeper Keeper, ak types.AccountKeeper) AppModule {
|
||||
return AppModule{
|
||||
AppModuleBasic: AppModuleBasic{},
|
||||
AppModuleSimulation: AppModuleSimulation{},
|
||||
keeper: keeper,
|
||||
ak: ak,
|
||||
}
|
||||
}
|
||||
|
||||
// module name
|
||||
// Name returns the supply module's name.
|
||||
func (AppModule) Name() string {
|
||||
return ModuleName
|
||||
}
|
||||
|
||||
// register invariants
|
||||
// RegisterInvariants registers the supply module invariants.
|
||||
func (am AppModule) RegisterInvariants(ir sdk.InvariantRegistry) {
|
||||
RegisterInvariants(ir, am.keeper)
|
||||
}
|
||||
|
||||
// module message route name
|
||||
// Route returns the message routing key for the supply module.
|
||||
func (AppModule) Route() string {
|
||||
return RouterKey
|
||||
}
|
||||
|
||||
// module handler
|
||||
// NewHandler returns an sdk.Handler for the supply module.
|
||||
func (am AppModule) NewHandler() sdk.Handler { return nil }
|
||||
|
||||
// module querier route name
|
||||
// QuerierRoute returns the supply module's querier route name.
|
||||
func (AppModule) QuerierRoute() string {
|
||||
return QuerierRoute
|
||||
}
|
||||
|
||||
// module querier
|
||||
// NewQuerierHandler returns the supply module sdk.Querier.
|
||||
func (am AppModule) NewQuerierHandler() sdk.Querier {
|
||||
return NewQuerier(am.keeper)
|
||||
}
|
||||
|
||||
// module init-genesis
|
||||
// InitGenesis performs genesis initialization for the supply module. It returns
|
||||
// no validator updates.
|
||||
func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.ValidatorUpdate {
|
||||
var genesisState GenesisState
|
||||
ModuleCdc.MustUnmarshalJSON(data, &genesisState)
|
||||
|
@ -115,16 +134,18 @@ func (am AppModule) InitGenesis(ctx sdk.Context, data json.RawMessage) []abci.Va
|
|||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
||||
// module export genesis
|
||||
// ExportGenesis returns the exported genesis state as raw bytes for the supply
|
||||
// module.
|
||||
func (am AppModule) ExportGenesis(ctx sdk.Context) json.RawMessage {
|
||||
gs := ExportGenesis(ctx, am.keeper)
|
||||
return ModuleCdc.MustMarshalJSON(gs)
|
||||
}
|
||||
|
||||
// module begin-block
|
||||
// BeginBlock returns the begin blocker for the supply module.
|
||||
func (am AppModule) BeginBlock(_ sdk.Context, _ abci.RequestBeginBlock) {}
|
||||
|
||||
// module end-block
|
||||
// EndBlock returns the end blocker for the supply module. It returns no validator
|
||||
// updates.
|
||||
func (AppModule) EndBlock(_ sdk.Context, _ abci.RequestEndBlock) []abci.ValidatorUpdate {
|
||||
return []abci.ValidatorUpdate{}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,25 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/internal/keeper"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/internal/types"
|
||||
)
|
||||
|
||||
// DecodeStore unmarshals the KVPair's Value to the corresponding supply type
|
||||
func DecodeStore(cdc *codec.Codec, kvA, kvB cmn.KVPair) string {
|
||||
switch {
|
||||
case bytes.Equal(kvA.Key[:1], keeper.SupplyKey):
|
||||
var supplyA, supplyB types.Supply
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvA.Value, &supplyA)
|
||||
cdc.MustUnmarshalBinaryLengthPrefixed(kvB.Value, &supplyB)
|
||||
return fmt.Sprintf("%v\n%v", supplyB, supplyB)
|
||||
default:
|
||||
panic(fmt.Sprintf("invalid supply key %X", kvA.Key))
|
||||
}
|
||||
}
|
|
@ -0,0 +1,52 @@
|
|||
package simulation
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
cmn "github.com/tendermint/tendermint/libs/common"
|
||||
|
||||
"github.com/cosmos/cosmos-sdk/codec"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/internal/keeper"
|
||||
"github.com/cosmos/cosmos-sdk/x/supply/internal/types"
|
||||
)
|
||||
|
||||
func makeTestCodec() (cdc *codec.Codec) {
|
||||
cdc = codec.New()
|
||||
sdk.RegisterCodec(cdc)
|
||||
codec.RegisterCrypto(cdc)
|
||||
types.RegisterCodec(cdc)
|
||||
return
|
||||
}
|
||||
func TestDecodeStore(t *testing.T) {
|
||||
cdc := makeTestCodec()
|
||||
|
||||
totalSupply := types.NewSupply(sdk.NewCoins(sdk.NewInt64Coin(sdk.DefaultBondDenom, 1000)))
|
||||
|
||||
kvPairs := cmn.KVPairs{
|
||||
cmn.KVPair{Key: keeper.SupplyKey, Value: cdc.MustMarshalBinaryLengthPrefixed(totalSupply)},
|
||||
cmn.KVPair{Key: []byte{0x99}, Value: []byte{0x99}},
|
||||
}
|
||||
|
||||
tests := []struct {
|
||||
name string
|
||||
expectedLog string
|
||||
}{
|
||||
{"Supply", fmt.Sprintf("%v\n%v", totalSupply, totalSupply)},
|
||||
{"other", ""},
|
||||
}
|
||||
|
||||
for i, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
switch i {
|
||||
case len(tests) - 1:
|
||||
require.Panics(t, func() { DecodeStore(cdc, kvPairs[i], kvPairs[i]) }, tt.name)
|
||||
default:
|
||||
require.Equal(t, tt.expectedLog, DecodeStore(cdc, kvPairs[i], kvPairs[i]), tt.name)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue