347 lines
11 KiB
Go
347 lines
11 KiB
Go
|
package app
|
||
|
|
||
|
import (
|
||
|
"encoding/json"
|
||
|
"io"
|
||
|
"os"
|
||
|
|
||
|
abci "github.com/tendermint/tendermint/abci/types"
|
||
|
"github.com/tendermint/tendermint/libs/log"
|
||
|
tmos "github.com/tendermint/tendermint/libs/os"
|
||
|
dbm "github.com/tendermint/tm-db"
|
||
|
|
||
|
bam "github.com/cosmos/cosmos-sdk/baseapp"
|
||
|
"github.com/cosmos/cosmos-sdk/codec"
|
||
|
"github.com/cosmos/cosmos-sdk/simapp"
|
||
|
sdk "github.com/cosmos/cosmos-sdk/types"
|
||
|
"github.com/cosmos/cosmos-sdk/types/module"
|
||
|
"github.com/cosmos/cosmos-sdk/version"
|
||
|
"github.com/cosmos/cosmos-sdk/x/auth"
|
||
|
"github.com/cosmos/cosmos-sdk/x/auth/vesting"
|
||
|
"github.com/cosmos/cosmos-sdk/x/bank"
|
||
|
distr "github.com/cosmos/cosmos-sdk/x/distribution"
|
||
|
"github.com/cosmos/cosmos-sdk/x/genutil"
|
||
|
"github.com/cosmos/cosmos-sdk/x/params"
|
||
|
"github.com/cosmos/cosmos-sdk/x/slashing"
|
||
|
"github.com/cosmos/cosmos-sdk/x/staking"
|
||
|
"github.com/cosmos/cosmos-sdk/x/supply"
|
||
|
|
||
|
"github.com/changtong1996/djzh/x/djzh"
|
||
|
)
|
||
|
|
||
|
const appName = "app"
|
||
|
|
||
|
var (
|
||
|
// TODO: rename your cli
|
||
|
|
||
|
// DefaultCLIHome default home directories for the application CLI
|
||
|
DefaultCLIHome = os.ExpandEnv("$HOME/.djzhcli")
|
||
|
|
||
|
// TODO: rename your daemon
|
||
|
|
||
|
// DefaultNodeHome sets the folder where the applcation data and configuration will be stored
|
||
|
DefaultNodeHome = os.ExpandEnv("$HOME/.djzhd")
|
||
|
|
||
|
// ModuleBasics The module BasicManager is in charge of setting up basic,
|
||
|
// non-dependant module elements, such as codec registration
|
||
|
// and genesis verification.
|
||
|
ModuleBasics = module.NewBasicManager(
|
||
|
genutil.AppModuleBasic{},
|
||
|
auth.AppModuleBasic{},
|
||
|
bank.AppModuleBasic{},
|
||
|
staking.AppModuleBasic{},
|
||
|
distr.AppModuleBasic{},
|
||
|
params.AppModuleBasic{},
|
||
|
slashing.AppModuleBasic{},
|
||
|
supply.AppModuleBasic{},
|
||
|
// TODO: Add your module(s) AppModuleBasic
|
||
|
djzh.AppModuleBasic{},
|
||
|
)
|
||
|
|
||
|
// module account permissions
|
||
|
maccPerms = map[string][]string{
|
||
|
auth.FeeCollectorName: nil,
|
||
|
distr.ModuleName: nil,
|
||
|
staking.BondedPoolName: {supply.Burner, supply.Staking},
|
||
|
staking.NotBondedPoolName: {supply.Burner, supply.Staking},
|
||
|
}
|
||
|
)
|
||
|
|
||
|
// MakeCodec creates the application codec. The codec is sealed before it is
|
||
|
// returned.
|
||
|
func MakeCodec() *codec.Codec {
|
||
|
var cdc = codec.New()
|
||
|
|
||
|
ModuleBasics.RegisterCodec(cdc)
|
||
|
vesting.RegisterCodec(cdc)
|
||
|
sdk.RegisterCodec(cdc)
|
||
|
codec.RegisterCrypto(cdc)
|
||
|
|
||
|
return cdc.Seal()
|
||
|
}
|
||
|
|
||
|
// NewApp extended ABCI application
|
||
|
type NewApp struct {
|
||
|
*bam.BaseApp
|
||
|
cdc *codec.Codec
|
||
|
|
||
|
invCheckPeriod uint
|
||
|
|
||
|
// keys to access the substores
|
||
|
keys map[string]*sdk.KVStoreKey
|
||
|
tKeys map[string]*sdk.TransientStoreKey
|
||
|
|
||
|
// subspaces
|
||
|
subspaces map[string]params.Subspace
|
||
|
|
||
|
// keepers
|
||
|
accountKeeper auth.AccountKeeper
|
||
|
bankKeeper bank.Keeper
|
||
|
stakingKeeper staking.Keeper
|
||
|
slashingKeeper slashing.Keeper
|
||
|
distrKeeper distr.Keeper
|
||
|
supplyKeeper supply.Keeper
|
||
|
paramsKeeper params.Keeper
|
||
|
// TODO: Add your module(s)
|
||
|
djzhKeeper djzh.Keeper
|
||
|
|
||
|
// Module Manager
|
||
|
mm *module.Manager
|
||
|
|
||
|
// simulation manager
|
||
|
sm *module.SimulationManager
|
||
|
}
|
||
|
|
||
|
// verify app interface at compile time
|
||
|
var _ simapp.App = (*NewApp)(nil)
|
||
|
|
||
|
// NewdjzhApp is a constructor function for djzhApp
|
||
|
func NewInitApp(
|
||
|
logger log.Logger, db dbm.DB, traceStore io.Writer, loadLatest bool,
|
||
|
invCheckPeriod uint, baseAppOptions ...func(*bam.BaseApp),
|
||
|
) *NewApp {
|
||
|
// First define the top level codec that will be shared by the different modules
|
||
|
cdc := MakeCodec()
|
||
|
|
||
|
// BaseApp handles interactions with Tendermint through the ABCI protocol
|
||
|
bApp := bam.NewBaseApp(appName, logger, db, auth.DefaultTxDecoder(cdc), baseAppOptions...)
|
||
|
bApp.SetCommitMultiStoreTracer(traceStore)
|
||
|
bApp.SetAppVersion(version.Version)
|
||
|
|
||
|
// TODO: Add the keys that module requires
|
||
|
keys := sdk.NewKVStoreKeys(bam.MainStoreKey, auth.StoreKey, staking.StoreKey,
|
||
|
supply.StoreKey, distr.StoreKey, slashing.StoreKey, params.StoreKey, djzh.StoreKey)
|
||
|
|
||
|
tKeys := sdk.NewTransientStoreKeys(staking.TStoreKey, params.TStoreKey)
|
||
|
|
||
|
// Here you initialize your application with the store keys it requires
|
||
|
var app = &NewApp{
|
||
|
BaseApp: bApp,
|
||
|
cdc: cdc,
|
||
|
invCheckPeriod: invCheckPeriod,
|
||
|
keys: keys,
|
||
|
tKeys: tKeys,
|
||
|
subspaces: make(map[string]params.Subspace),
|
||
|
}
|
||
|
|
||
|
// The ParamsKeeper handles parameter storage for the application
|
||
|
app.paramsKeeper = params.NewKeeper(app.cdc, keys[params.StoreKey], tKeys[params.TStoreKey])
|
||
|
// Set specific supspaces
|
||
|
app.subspaces[auth.ModuleName] = app.paramsKeeper.Subspace(auth.DefaultParamspace)
|
||
|
app.subspaces[bank.ModuleName] = app.paramsKeeper.Subspace(bank.DefaultParamspace)
|
||
|
app.subspaces[staking.ModuleName] = app.paramsKeeper.Subspace(staking.DefaultParamspace)
|
||
|
app.subspaces[distr.ModuleName] = app.paramsKeeper.Subspace(distr.DefaultParamspace)
|
||
|
app.subspaces[slashing.ModuleName] = app.paramsKeeper.Subspace(slashing.DefaultParamspace)
|
||
|
|
||
|
// The AccountKeeper handles address -> account lookups
|
||
|
app.accountKeeper = auth.NewAccountKeeper(
|
||
|
app.cdc,
|
||
|
keys[auth.StoreKey],
|
||
|
app.subspaces[auth.ModuleName],
|
||
|
auth.ProtoBaseAccount,
|
||
|
)
|
||
|
|
||
|
// The BankKeeper allows you perform sdk.Coins interactions
|
||
|
app.bankKeeper = bank.NewBaseKeeper(
|
||
|
app.accountKeeper,
|
||
|
app.subspaces[bank.ModuleName],
|
||
|
app.ModuleAccountAddrs(),
|
||
|
)
|
||
|
|
||
|
// The SupplyKeeper collects transaction fees and renders them to the fee distribution module
|
||
|
app.supplyKeeper = supply.NewKeeper(
|
||
|
app.cdc,
|
||
|
keys[supply.StoreKey],
|
||
|
app.accountKeeper,
|
||
|
app.bankKeeper,
|
||
|
maccPerms,
|
||
|
)
|
||
|
|
||
|
// The staking keeper
|
||
|
stakingKeeper := staking.NewKeeper(
|
||
|
app.cdc,
|
||
|
keys[staking.StoreKey],
|
||
|
app.supplyKeeper,
|
||
|
app.subspaces[staking.ModuleName],
|
||
|
)
|
||
|
|
||
|
app.distrKeeper = distr.NewKeeper(
|
||
|
app.cdc,
|
||
|
keys[distr.StoreKey],
|
||
|
app.subspaces[distr.ModuleName],
|
||
|
&stakingKeeper,
|
||
|
app.supplyKeeper,
|
||
|
auth.FeeCollectorName,
|
||
|
app.ModuleAccountAddrs(),
|
||
|
)
|
||
|
|
||
|
app.slashingKeeper = slashing.NewKeeper(
|
||
|
app.cdc,
|
||
|
keys[slashing.StoreKey],
|
||
|
&stakingKeeper,
|
||
|
app.subspaces[slashing.ModuleName],
|
||
|
)
|
||
|
|
||
|
// register the staking hooks
|
||
|
// NOTE: stakingKeeper above is passed by reference, so that it will contain these hooks
|
||
|
app.stakingKeeper = *stakingKeeper.SetHooks(
|
||
|
staking.NewMultiStakingHooks(
|
||
|
app.distrKeeper.Hooks(),
|
||
|
app.slashingKeeper.Hooks()),
|
||
|
)
|
||
|
|
||
|
// TODO: Add your module(s) keepers
|
||
|
app.djzhKeeper = djzh.NewKeeper(
|
||
|
app.bankKeeper,
|
||
|
keys[djzh.StoreKey],
|
||
|
app.cdc,
|
||
|
)
|
||
|
|
||
|
// NOTE: Any module instantiated in the module manager that is later modified
|
||
|
// must be passed by reference here.
|
||
|
app.mm = module.NewManager(
|
||
|
genutil.NewAppModule(app.accountKeeper, app.stakingKeeper, app.BaseApp.DeliverTx),
|
||
|
auth.NewAppModule(app.accountKeeper),
|
||
|
bank.NewAppModule(app.bankKeeper, app.accountKeeper),
|
||
|
supply.NewAppModule(app.supplyKeeper, app.accountKeeper),
|
||
|
distr.NewAppModule(app.distrKeeper, app.accountKeeper, app.supplyKeeper, app.stakingKeeper),
|
||
|
slashing.NewAppModule(app.slashingKeeper, app.accountKeeper, app.stakingKeeper),
|
||
|
// TODO: Add your module(s)
|
||
|
staking.NewAppModule(app.stakingKeeper, app.accountKeeper, app.supplyKeeper),
|
||
|
djzh.NewAppModule(app.djzhKeeper, app.bankKeeper),
|
||
|
|
||
|
)
|
||
|
// During begin block slashing happens after distr.BeginBlocker so that
|
||
|
// there is nothing left over in the validator fee pool, so as to keep the
|
||
|
// CanWithdrawInvariant invariant.
|
||
|
|
||
|
app.mm.SetOrderBeginBlockers(distr.ModuleName, slashing.ModuleName)
|
||
|
app.mm.SetOrderEndBlockers(staking.ModuleName)
|
||
|
|
||
|
// Sets the order of Genesis - Order matters, genutil is to always come last
|
||
|
// NOTE: The genutils module must occur after staking so that pools are
|
||
|
// properly initialized with tokens from genesis accounts.
|
||
|
app.mm.SetOrderInitGenesis(
|
||
|
distr.ModuleName,
|
||
|
staking.ModuleName,
|
||
|
auth.ModuleName,
|
||
|
bank.ModuleName,
|
||
|
slashing.ModuleName,
|
||
|
// TODO: Add your module(s)
|
||
|
supply.ModuleName,
|
||
|
genutil.ModuleName,
|
||
|
djzh.ModuleName,
|
||
|
)
|
||
|
|
||
|
// register all module routes and module queriers
|
||
|
app.mm.RegisterRoutes(app.Router(), app.QueryRouter())
|
||
|
|
||
|
// The initChainer handles translating the genesis.json file into initial state for the network
|
||
|
app.SetInitChainer(app.InitChainer)
|
||
|
app.SetBeginBlocker(app.BeginBlocker)
|
||
|
app.SetEndBlocker(app.EndBlocker)
|
||
|
|
||
|
// The AnteHandler handles signature verification and transaction pre-processing
|
||
|
app.SetAnteHandler(
|
||
|
auth.NewAnteHandler(
|
||
|
app.accountKeeper,
|
||
|
app.supplyKeeper,
|
||
|
auth.DefaultSigVerificationGasConsumer,
|
||
|
),
|
||
|
)
|
||
|
|
||
|
// initialize stores
|
||
|
app.MountKVStores(keys)
|
||
|
app.MountTransientStores(tKeys)
|
||
|
|
||
|
if loadLatest {
|
||
|
err := app.LoadLatestVersion(app.keys[bam.MainStoreKey])
|
||
|
if err != nil {
|
||
|
tmos.Exit(err.Error())
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return app
|
||
|
}
|
||
|
|
||
|
// GenesisState represents chain state at the start of the chain. Any initial state (account balances) are stored here.
|
||
|
type GenesisState map[string]json.RawMessage
|
||
|
|
||
|
// NewDefaultGenesisState generates the default state for the application.
|
||
|
func NewDefaultGenesisState() GenesisState {
|
||
|
return ModuleBasics.DefaultGenesis()
|
||
|
}
|
||
|
|
||
|
// InitChainer application update at chain initialization
|
||
|
func (app *NewApp) InitChainer(ctx sdk.Context, req abci.RequestInitChain) abci.ResponseInitChain {
|
||
|
var genesisState simapp.GenesisState
|
||
|
|
||
|
app.cdc.MustUnmarshalJSON(req.AppStateBytes, &genesisState)
|
||
|
|
||
|
return app.mm.InitGenesis(ctx, genesisState)
|
||
|
}
|
||
|
|
||
|
// BeginBlocker application updates every begin block
|
||
|
func (app *NewApp) BeginBlocker(ctx sdk.Context, req abci.RequestBeginBlock) abci.ResponseBeginBlock {
|
||
|
return app.mm.BeginBlock(ctx, req)
|
||
|
}
|
||
|
|
||
|
// EndBlocker application updates every end block
|
||
|
func (app *NewApp) EndBlocker(ctx sdk.Context, req abci.RequestEndBlock) abci.ResponseEndBlock {
|
||
|
return app.mm.EndBlock(ctx, req)
|
||
|
}
|
||
|
|
||
|
// LoadHeight loads a particular height
|
||
|
func (app *NewApp) LoadHeight(height int64) error {
|
||
|
return app.LoadVersion(height, app.keys[bam.MainStoreKey])
|
||
|
}
|
||
|
|
||
|
// ModuleAccountAddrs returns all the app's module account addresses.
|
||
|
func (app *NewApp) ModuleAccountAddrs() map[string]bool {
|
||
|
modAccAddrs := make(map[string]bool)
|
||
|
for acc := range maccPerms {
|
||
|
modAccAddrs[supply.NewModuleAddress(acc).String()] = true
|
||
|
}
|
||
|
|
||
|
return modAccAddrs
|
||
|
}
|
||
|
|
||
|
// Codec returns the application's sealed codec.
|
||
|
func (app *NewApp) Codec() *codec.Codec {
|
||
|
return app.cdc
|
||
|
}
|
||
|
|
||
|
// SimulationManager implements the SimulationApp interface
|
||
|
func (app *NewApp) SimulationManager() *module.SimulationManager {
|
||
|
return app.sm
|
||
|
}
|
||
|
|
||
|
// GetMaccPerms returns a mapping of the application's module account permissions.
|
||
|
func GetMaccPerms() map[string][]string {
|
||
|
modAccPerms := make(map[string][]string)
|
||
|
for k, v := range maccPerms {
|
||
|
modAccPerms[k] = v
|
||
|
}
|
||
|
return modAccPerms
|
||
|
}
|