Merge pull request #416 from cosmos/feature/initgen

Initialize Genesis State
This commit is contained in:
Ethan Buchman 2018-02-13 07:38:21 -05:00 committed by GitHub
commit 69c316f5de
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
20 changed files with 272 additions and 83 deletions

View File

@ -19,7 +19,7 @@ import (
var mainHeaderKey = []byte("header")
// BaseApp - The ABCI application
// The ABCI application
type BaseApp struct {
logger log.Logger
@ -32,33 +32,38 @@ type BaseApp struct {
// Main (uncached) state
cms sdk.CommitMultiStore
// Unmarshal []byte into sdk.Tx
// unmarshal []byte into sdk.Tx
txDecoder sdk.TxDecoder
// Ante handler for fee and auth.
// unmarshal rawjsonbytes to initialize the application
// TODO unexpose and call from InitChain
InitStater sdk.InitStater
// ante handler for fee and auth
defaultAnteHandler sdk.AnteHandler
// Handle any kind of message.
// handle any kind of message
router Router
//--------------------
// Volatile
// CheckTx state, a cache-wrap of `.cms`.
// CheckTx state, a cache-wrap of `.cms`
msCheck sdk.CacheMultiStore
// DeliverTx state, a cache-wrap of `.cms`.
// DeliverTx state, a cache-wrap of `.cms`
msDeliver sdk.CacheMultiStore
// Current block header
// current block header
header *abci.Header
// Cached validator changes from DeliverTx.
// cached validator changes from DeliverTx
valUpdates []abci.Validator
}
var _ abci.Application = &BaseApp{}
// Create and name new BaseApp
func NewBaseApp(name string) *BaseApp {
var baseapp = &BaseApp{
logger: makeDefaultLogger(),
@ -88,22 +93,26 @@ func (app *BaseApp) initMultiStore() {
app.cms = cms
}
// BaseApp Name
func (app *BaseApp) Name() string {
return app.name
}
// Mount a store to the provided key in the BaseApp multistore
func (app *BaseApp) MountStore(key sdk.StoreKey, typ sdk.StoreType) {
app.cms.MountStoreWithDB(key, typ, app.db)
}
// nolint
func (app *BaseApp) SetTxDecoder(txDecoder sdk.TxDecoder) {
app.txDecoder = txDecoder
}
func (app *BaseApp) SetInitStater(initStater sdk.InitStater) {
app.InitStater = initStater
}
func (app *BaseApp) SetDefaultAnteHandler(ah sdk.AnteHandler) {
app.defaultAnteHandler = ah
}
func (app *BaseApp) Router() Router {
return app.router
}
@ -111,14 +120,15 @@ func (app *BaseApp) Router() Router {
/* TODO consider:
func (app *BaseApp) SetBeginBlocker(...) {}
func (app *BaseApp) SetEndBlocker(...) {}
func (app *BaseApp) SetInitStater(...) {}
*/
// TODO add description
func (app *BaseApp) LoadLatestVersion(mainKey sdk.StoreKey) error {
app.cms.LoadLatestVersion()
return app.initFromStore(mainKey)
}
// Load application version
func (app *BaseApp) LoadVersion(version int64, mainKey sdk.StoreKey) error {
app.cms.LoadVersion(version)
return app.initFromStore(mainKey)
@ -174,7 +184,7 @@ func (app *BaseApp) initFromStore(mainKey sdk.StoreKey) error {
//----------------------------------------
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) Info(req abci.RequestInfo) abci.ResponseInfo {
lastCommitID := app.cms.LastCommitID()
@ -186,15 +196,16 @@ func (app *BaseApp) Info(req abci.RequestInfo) abci.ResponseInfo {
}
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) SetOption(req abci.RequestSetOption) (res abci.ResponseSetOption) {
// TODO: Implement
return
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) InitChain(req abci.RequestInitChain) (res abci.ResponseInitChain) {
// TODO: Use req.Validators
// TODO: Use req.AppStateJSON (?)
return
}
@ -209,7 +220,7 @@ func (app *BaseApp) Query(req abci.RequestQuery) (res abci.ResponseQuery) {
return queryable.Query(req)
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) BeginBlock(req abci.RequestBeginBlock) (res abci.ResponseBeginBlock) {
// NOTE: For consistency we should unset these upon EndBlock.
app.header = &req.Header
@ -219,7 +230,7 @@ func (app *BaseApp) BeginBlock(req abci.RequestBeginBlock) (res abci.ResponseBeg
return
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) CheckTx(txBytes []byte) (res abci.ResponseCheckTx) {
// Decode the Tx.
@ -245,7 +256,7 @@ func (app *BaseApp) CheckTx(txBytes []byte) (res abci.ResponseCheckTx) {
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) DeliverTx(txBytes []byte) (res abci.ResponseDeliverTx) {
// Decode the Tx.
@ -333,7 +344,7 @@ func (app *BaseApp) runTx(isCheckTx bool, txBytes []byte, tx sdk.Tx) (result sdk
return result
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) EndBlock(req abci.RequestEndBlock) (res abci.ResponseEndBlock) {
res.ValidatorUpdates = app.valUpdates
app.valUpdates = nil
@ -343,7 +354,7 @@ func (app *BaseApp) EndBlock(req abci.RequestEndBlock) (res abci.ResponseEndBloc
return
}
// Implements ABCI.
// Implements ABCI
func (app *BaseApp) Commit() (res abci.ResponseCommit) {
app.msDeliver.Write()
commitID := app.cms.Commit()
@ -361,9 +372,8 @@ func (app *BaseApp) Commit() (res abci.ResponseCommit) {
func (app *BaseApp) getMultiStore(isCheckTx bool) sdk.MultiStore {
if isCheckTx {
return app.msCheck
} else {
return app.msDeliver
}
return app.msDeliver
}
// Return index of list with validator of same PubKey, or -1 if no match

View File

@ -106,7 +106,7 @@ func TestBasic(t *testing.T) {
}
// Not matched.
j += 1
j++
}
}
assert.Equal(t, len(valUpdates), 0, "Some validator updates were unexpected")

View File

@ -1,6 +1,8 @@
package baseapp
import sdk "github.com/cosmos/cosmos-sdk/types"
import (
sdk "github.com/cosmos/cosmos-sdk/types"
)
// NewContext returns a new Context suitable for AnteHandler (and indirectly Handler) processing.
// NOTE: txBytes may be nil to support TestApp.RunCheckTx
@ -12,6 +14,7 @@ func (app *BaseApp) NewContext(isCheckTx bool, txBytes []byte) sdk.Context {
} else {
store = app.msDeliver
}
if store == nil {
panic("BaseApp.NewContext() requires BeginBlock(): missing store")
}

32
baseapp/genesis.go Normal file
View File

@ -0,0 +1,32 @@
package baseapp
import (
"encoding/json"
"io/ioutil"
)
// TODO: remove from here and pass the AppState
// through InitChain
// GenesisDoc defines the initial conditions for a tendermint blockchain, in particular its validator set.
type GenesisDoc struct {
AppState json.RawMessage `json:"app_state,omitempty"`
}
// GenesisDocFromFile reads JSON data from a file and unmarshalls it into a GenesisDoc.
func GenesisDocFromFile(genDocFile string) (*GenesisDoc, error) {
if genDocFile == "" {
var g GenesisDoc
return &g, nil
}
jsonBlob, err := ioutil.ReadFile(genDocFile)
if err != nil {
return nil, err
}
genDoc := GenesisDoc{}
err = json.Unmarshal(jsonBlob, &genDoc)
if err != nil {
return nil, err
}
return &genDoc, nil
}

View File

@ -6,6 +6,7 @@ import (
sdk "github.com/cosmos/cosmos-sdk/types"
)
// Router - TODO add description
type Router interface {
AddRoute(r string, h sdk.Handler)
Route(path string) (h sdk.Handler)
@ -20,6 +21,9 @@ type router struct {
routes []route
}
// nolint
// NewRouter - create new router
// TODO either make Function unexported or make return type (router) Exported
func NewRouter() *router {
return &router{
routes: make([]route, 0),
@ -28,6 +32,7 @@ func NewRouter() *router {
var isAlpha = regexp.MustCompile(`^[a-zA-Z]+$`).MatchString
// AddRoute - TODO add description
func (rtr *router) AddRoute(r string, h sdk.Handler) {
if !isAlpha(r) {
panic("route expressions can only contain alphanumeric characters")
@ -35,6 +40,7 @@ func (rtr *router) AddRoute(r string, h sdk.Handler) {
rtr.routes = append(rtr.routes, route{r, h})
}
// Route - TODO add description
// TODO handle expressive matches.
func (rtr *router) Route(path string) (h sdk.Handler) {
for _, route := range rtr.routes {

View File

@ -24,6 +24,7 @@ func NewTestApp(bapp *BaseApp) *TestApp {
return app
}
// execute BaseApp BeginBlock
func (tapp *TestApp) RunBeginBlock() {
if tapp.header != nil {
panic("TestApp.header not nil, BeginBlock already run, or EndBlock not yet run.")
@ -56,36 +57,43 @@ func (tapp *TestApp) ensureBeginBlock() {
}
}
// run tx through CheckTx of TestApp
func (tapp *TestApp) RunCheckTx(tx sdk.Tx) sdk.Result {
tapp.ensureBeginBlock()
return tapp.BaseApp.runTx(true, nil, tx)
}
// run tx through DeliverTx of TestApp
func (tapp *TestApp) RunDeliverTx(tx sdk.Tx) sdk.Result {
tapp.ensureBeginBlock()
return tapp.BaseApp.runTx(false, nil, tx)
}
// run tx through CheckTx of TestApp
// NOTE: Skips authentication by wrapping msg in testTx{}.
func (tapp *TestApp) RunCheckMsg(msg sdk.Msg) sdk.Result {
var tx = testTx{msg}
return tapp.RunCheckTx(tx)
}
// run tx through DeliverTx of TestApp
// NOTE: Skips authentication by wrapping msg in testTx{}.
func (tapp *TestApp) RunDeliverMsg(msg sdk.Msg) sdk.Result {
var tx = testTx{msg}
return tapp.RunDeliverTx(tx)
}
// return the commited multistore
func (tapp *TestApp) CommitMultiStore() sdk.CommitMultiStore {
return tapp.BaseApp.cms
}
// return a cache-wrap CheckTx state of multistore
func (tapp *TestApp) MultiStoreCheck() sdk.MultiStore {
return tapp.BaseApp.msCheck
}
// return a cache-wrap DeliverTx state of multistore
func (tapp *TestApp) MultiStoreDeliver() sdk.MultiStore {
return tapp.BaseApp.msDeliver
}
@ -97,11 +105,11 @@ type testTx struct {
sdk.Msg
}
// nolint
func (tx testTx) GetMsg() sdk.Msg { return tx.Msg }
func (tx testTx) GetSigners() []crypto.Address { return nil }
func (tx testTx) GetFeePayer() crypto.Address { return nil }
func (tx testTx) GetSignatures() []sdk.StdSignature { return nil }
func IsTestAppTx(tx sdk.Tx) bool {
_, ok := tx.(testTx)
return ok

View File

@ -6,18 +6,21 @@ import (
bam "github.com/cosmos/cosmos-sdk/baseapp"
sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/tendermint/abci/server"
abci "github.com/tendermint/abci/types"
"github.com/tendermint/go-wire"
cmn "github.com/tendermint/tmlibs/common"
)
const appName = "BasecoinApp"
// BasecoinApp - extended ABCI application
type BasecoinApp struct {
*bam.BaseApp
router bam.Router
cdc *wire.Codec
multiStore sdk.CommitMultiStore
multiStore sdk.CommitMultiStore //TODO distinguish this store from *bam.BaseApp.cms <- is this one master?? confused
// The key to access the substores.
capKeyMainStore *sdk.KVStoreKey
@ -27,25 +30,44 @@ type BasecoinApp struct {
accountMapper sdk.AccountMapper
}
// NewBasecoinApp - create new BasecoinApp
// TODO: This should take in more configuration options.
func NewBasecoinApp() *BasecoinApp {
// TODO: This should be moved into baseapp to isolate complexity
func NewBasecoinApp(genesisPath string) *BasecoinApp {
// Create and configure app.
var app = &BasecoinApp{}
app.initCapKeys() // ./init_capkeys.go
app.initBaseApp() // ./init_baseapp.go
app.initStores() // ./init_stores.go
// TODO open up out of functions, or introduce clarity,
// interdependancies are a nightmare to debug
app.initCapKeys() // ./init_capkeys.go
app.initBaseApp() // ./init_baseapp.go
app.initStores() // ./init_stores.go
app.initBaseAppInitStater()
app.initHandlers() // ./init_handlers.go
// TODO: Load genesis
// TODO: InitChain with validators
// TODO: Set the genesis accounts
genesisiDoc, err := bam.GenesisDocFromFile(genesisPath)
if err != nil {
panic(fmt.Errorf("error loading genesis state: %v", err))
}
// set up the cache store for ctx, get ctx
// TODO: can InitChain handle this too ?
app.BaseApp.BeginBlock(abci.RequestBeginBlock{Header: abci.Header{}})
ctx := app.BaseApp.NewContext(false, nil) // context for DeliverTx
// TODO: combine with InitChain and let tendermint invoke it.
err = app.BaseApp.InitStater(ctx, genesisiDoc.AppState)
if err != nil {
panic(fmt.Errorf("error initializing application genesis state: %v", err))
}
app.loadStores()
return app
}
// RunForever - BasecoinApp execution and cleanup
func (app *BasecoinApp) RunForever() {
// Start the ABCI server
@ -64,7 +86,7 @@ func (app *BasecoinApp) RunForever() {
}
// Load the stores.
// Load the stores
func (app *BasecoinApp) loadStores() {
if err := app.LoadLatestVersion(app.capKeyMainStore); err != nil {
fmt.Println(err)

View File

@ -1,11 +1,17 @@
package app
import (
"encoding/json"
"testing"
sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/x/bank"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"github.com/cosmos/cosmos-sdk/examples/basecoin/types"
sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/x/auth"
"github.com/cosmos/cosmos-sdk/x/bank"
crypto "github.com/tendermint/go-crypto"
)
@ -37,4 +43,32 @@ func TestSendMsg(t *testing.T) {
// Run a Deliver on SendMsg.
res = tba.RunDeliverMsg(msg)
assert.Equal(t, sdk.CodeUnrecognizedAddress, res.Code, res.Log)
// TODO seperate this test, need a closer on db? keep getting resource unavailable
// construct some genesis bytes to reflect basecoin/types/AppAccount
pk := crypto.GenPrivKeyEd25519().PubKey()
addr := pk.Address()
coins, err := sdk.ParseCoins("77foocoin,99barcoin")
require.Nil(t, err)
baseAcc := auth.BaseAccount{
Address: addr,
Coins: coins,
}
acc := &types.AppAccount{baseAcc, "foobart"}
genesisState := GenesisState{
Accounts: []*GenesisAccount{
NewGenesisAccount(acc),
},
}
bytes, err := json.MarshalIndent(genesisState, "", "\t")
app := tba.BasecoinApp
ctx := app.BaseApp.NewContext(false, nil) // context for DeliverTx
err = app.BaseApp.InitStater(ctx, bytes)
require.Nil(t, err)
res1 := app.accountMapper.GetAccount(ctx, baseAcc.Address)
assert.Equal(t, acc, res1)
}

View File

@ -1,8 +1,13 @@
package app
import (
"encoding/json"
"github.com/cosmos/cosmos-sdk/baseapp"
"github.com/cosmos/cosmos-sdk/examples/basecoin/types"
sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/x/auth"
crypto "github.com/tendermint/go-crypto"
)
// initCapKeys, initBaseApp, initStores, initHandlers.
@ -11,6 +16,7 @@ func (app *BasecoinApp) initBaseApp() {
app.BaseApp = bapp
app.router = bapp.Router()
app.initBaseAppTxDecoder()
app.initBaseAppInitStater()
}
func (app *BasecoinApp) initBaseAppTxDecoder() {
@ -26,3 +32,62 @@ func (app *BasecoinApp) initBaseAppTxDecoder() {
return tx, nil
})
}
// define the custom logic for basecoin initialization
func (app *BasecoinApp) initBaseAppInitStater() {
accountMapper := app.accountMapper
app.BaseApp.SetInitStater(func(ctx sdk.Context, state json.RawMessage) sdk.Error {
if state == nil {
return nil
}
genesisState := new(GenesisState)
err := json.Unmarshal(state, genesisState)
if err != nil {
return sdk.ErrGenesisParse("").TraceCause(err, "")
}
for _, gacc := range genesisState.Accounts {
acc, err := gacc.toAppAccount()
if err != nil {
return sdk.ErrGenesisParse("").TraceCause(err, "")
}
accountMapper.SetAccount(ctx, acc)
}
return nil
})
}
//-----------------------------------------------------
type GenesisState struct {
Accounts []*GenesisAccount `accounts`
}
// GenesisAccount doesn't need pubkey or sequence
type GenesisAccount struct {
Name string `json:"name"`
Address crypto.Address `json:"address"`
Coins sdk.Coins `json:"coins"`
}
func NewGenesisAccount(aa *types.AppAccount) *GenesisAccount {
return &GenesisAccount{
Name: aa.Name,
Address: aa.Address,
Coins: aa.Coins,
}
}
// convert GenesisAccount to AppAccount
func (ga *GenesisAccount) toAppAccount() (acc *types.AppAccount, err error) {
baseAcc := auth.BaseAccount{
Address: ga.Address,
Coins: ga.Coins,
}
return &types.AppAccount{
BaseAccount: baseAcc,
Name: ga.Name,
}, nil
}

View File

@ -10,7 +10,7 @@ type testBasecoinApp struct {
}
func newTestBasecoinApp() *testBasecoinApp {
app := NewBasecoinApp()
app := NewBasecoinApp("")
tba := &testBasecoinApp{
BasecoinApp: app,
}

View File

@ -1,9 +1,10 @@
package main
import (
"fmt"
)
import "github.com/cosmos/cosmos-sdk/examples/basecoin/app"
func main() {
fmt.Println("TODO: move examples/basecoin/main.go here and refactor")
// TODO CREATE CLI
bapp := app.NewBasecoinApp("")
bapp.RunForever()
}

View File

@ -184,6 +184,7 @@ func (coins Coins) IsNotNegative() bool {
return true
}
// Returns the amount of a denom from coins
func (coins Coins) AmountOf(denom string) int64 {
switch len(coins) {
case 0:
@ -192,9 +193,8 @@ func (coins Coins) AmountOf(denom string) int64 {
coin := coins[0]
if coin.Denom == denom {
return coin.Amount
} else {
return 0
}
return 0
default:
midIdx := len(coins) / 2 // 2:1, 3:1, 4:2
coin := coins[midIdx]

View File

@ -192,7 +192,7 @@ func TestAmountOf(t *testing.T) {
cases := []struct {
coins Coins
amountOf int64
amountOf_ int64
amountOfSpace int64
amountOfGAS int64
amountOfMINERAL int64
amountOfTREE int64
@ -210,7 +210,7 @@ func TestAmountOf(t *testing.T) {
for _, tc := range cases {
assert.Equal(t, tc.amountOf, tc.coins.AmountOf(""))
assert.Equal(t, tc.amountOf_, tc.coins.AmountOf(" "))
assert.Equal(t, tc.amountOfSpace, tc.coins.AmountOf(" "))
assert.Equal(t, tc.amountOfGAS, tc.coins.AmountOf("GAS"))
assert.Equal(t, tc.amountOfMINERAL, tc.coins.AmountOf("MINERAL"))
assert.Equal(t, tc.amountOfTREE, tc.coins.AmountOf("TREE"))

View File

@ -30,6 +30,7 @@ type Context struct {
// it's probably not what you want to do.
}
// create a new context
func NewContext(ms MultiStore, header abci.Header, isCheckTx bool, txBytes []byte) Context {
c := Context{
Context: context.Background(),
@ -45,6 +46,7 @@ func NewContext(ms MultiStore, header abci.Header, isCheckTx bool, txBytes []byt
return c
}
// is context nil
func (c Context) IsZero() bool {
return c.Context == nil
}
@ -52,6 +54,7 @@ func (c Context) IsZero() bool {
//----------------------------------------
// Getting a value
// context value for the provided key
func (c Context) Value(key interface{}) interface{} {
value := c.Context.Value(key)
if cloner, ok := value.(cloner); ok {
@ -71,34 +74,28 @@ func (c Context) KVStore(key StoreKey) KVStore {
//----------------------------------------
// With* (setting a value)
// nolint
func (c Context) WithValue(key interface{}, value interface{}) Context {
return c.withValue(key, value)
}
func (c Context) WithCloner(key interface{}, value cloner) Context {
return c.withValue(key, value)
}
func (c Context) WithCacheWrapper(key interface{}, value CacheWrapper) Context {
return c.withValue(key, value)
}
func (c Context) WithProtoMsg(key interface{}, value proto.Message) Context {
return c.withValue(key, value)
}
func (c Context) WithString(key interface{}, value string) Context {
return c.withValue(key, value)
}
func (c Context) WithInt32(key interface{}, value int32) Context {
return c.withValue(key, value)
}
func (c Context) WithUint32(key interface{}, value uint32) Context {
return c.withValue(key, value)
}
func (c Context) WithUint64(key interface{}, value uint64) Context {
return c.withValue(key, value)
}
@ -138,47 +135,38 @@ func (c Context) multiStore() MultiStore {
return c.Value(contextKeyMultiStore).(MultiStore)
}
// nolint
func (c Context) BlockHeader() abci.Header {
return c.Value(contextKeyBlockHeader).(abci.Header)
}
func (c Context) BlockHeight() int64 {
return c.Value(contextKeyBlockHeight).(int64)
}
func (c Context) ChainID() string {
return c.Value(contextKeyChainID).(string)
}
func (c Context) IsCheckTx() bool {
return c.Value(contextKeyIsCheckTx).(bool)
}
func (c Context) TxBytes() []byte {
return c.Value(contextKeyTxBytes).([]byte)
}
func (c Context) WithMultiStore(ms MultiStore) Context {
return c.withValue(contextKeyMultiStore, ms)
}
func (c Context) WithBlockHeader(header abci.Header) Context {
var _ proto.Message = &header // for cloning.
return c.withValue(contextKeyBlockHeader, header)
}
func (c Context) WithBlockHeight(height int64) Context {
return c.withValue(contextKeyBlockHeight, height)
}
func (c Context) WithChainID(chainID string) Context {
return c.withValue(contextKeyChainID, chainID)
}
func (c Context) WithIsCheckTx(isCheckTx bool) Context {
return c.withValue(contextKeyIsCheckTx, isCheckTx)
}
func (c Context) WithTxBytes(txBytes []byte) Context {
return c.withValue(contextKeyTxBytes, txBytes)
}
@ -199,6 +187,7 @@ type cloner interface {
Clone() interface{} // deep copy
}
// XXX add description
type Op struct {
// type is always 'with'
gen int
@ -221,7 +210,7 @@ func newThePast() *thePast {
func (pst *thePast) bump(op Op) {
pst.mtx.Lock()
pst.ver += 1
pst.ver++
pst.ops = append(pst.ops, op)
pst.mtx.Unlock()
}
@ -240,7 +229,6 @@ func (pst *thePast) getOp(ver int64) (Op, bool) {
l := int64(len(pst.ops))
if l < ver || ver <= 0 {
return Op{}, false
} else {
return pst.ops[ver-1], true
}
return pst.ops[ver-1], true
}

View File

@ -7,19 +7,20 @@ import (
"github.com/tendermint/go-crypto"
)
// ABCI Response Code
type CodeType uint32
// is everything okay?
func (code CodeType) IsOK() bool {
if code == CodeOK {
return true
} else {
return false
}
return false
}
// ABCI Response Codes
// Base SDK reserves 0 ~ 99.
const (
// ABCI Response Codes
// Base SDK reserves 0 ~ 99.
CodeOK CodeType = 0
CodeInternal CodeType = 1
CodeTxParse CodeType = 2
@ -29,6 +30,8 @@ const (
CodeUnknownRequest CodeType = 6
CodeUnrecognizedAddress CodeType = 7
CodeInvalidSequence CodeType = 8
CodeGenesisParse CodeType = 0xdead // TODO: remove ?
)
// NOTE: Don't stringer this, we'll put better messages in later.
@ -38,6 +41,8 @@ func CodeToDefaultMsg(code CodeType) string {
return "Internal error"
case CodeTxParse:
return "Tx parse error"
case CodeGenesisParse:
return "Genesis parse error"
case CodeBadNonce:
return "Bad nonce"
case CodeUnauthorized:
@ -59,34 +64,31 @@ func CodeToDefaultMsg(code CodeType) string {
// All errors are created via constructors so as to enable us to hijack them
// and inject stack traces if we really want to.
// nolint
func ErrInternal(msg string) Error {
return newError(CodeInternal, msg)
}
func ErrTxParse(msg string) Error {
return newError(CodeTxParse, msg)
}
func ErrGenesisParse(msg string) Error {
return newError(CodeGenesisParse, msg)
}
func ErrBadNonce(msg string) Error {
return newError(CodeBadNonce, msg)
}
func ErrUnauthorized(msg string) Error {
return newError(CodeUnauthorized, msg)
}
func ErrInsufficientFunds(msg string) Error {
return newError(CodeInsufficientFunds, msg)
}
func ErrUnknownRequest(msg string) Error {
return newError(CodeUnknownRequest, msg)
}
func ErrUnrecognizedAddress(addr crypto.Address) Error {
return newError(CodeUnrecognizedAddress, addr.String())
}
func ErrInvalidSequence(msg string) Error {
return newError(CodeInvalidSequence, msg)
}
@ -94,6 +96,7 @@ func ErrInvalidSequence(msg string) Error {
//----------------------------------------
// Error & sdkError
// sdk Error type
type Error interface {
Error() string
ABCICode() CodeType

6
types/genesis.go Normal file
View File

@ -0,0 +1,6 @@
package types
import "encoding/json"
// function variable used to initialize application state at genesis
type InitStater func(ctx Context, state json.RawMessage) Error

View File

@ -1,5 +1,6 @@
package types
// core function variable which application runs for transactions
type Handler func(ctx Context, msg Msg) Result
// If newCtx.IsZero(), ctx is used instead.

View File

@ -2,6 +2,7 @@ package types
import crypto "github.com/tendermint/go-crypto"
// Standard Signature
type StdSignature struct {
crypto.PubKey // optional
crypto.Signature

View File

@ -9,12 +9,12 @@ import (
// NOTE: These are implemented in cosmos-sdk/store.
type Store interface {
type Store interface { //nolint
GetStoreType() StoreType
CacheWrapper
}
// Something that can persist to disk.
// something that can persist to disk
type Committer interface {
Commit() CommitID
LastCommitID() CommitID
@ -37,7 +37,7 @@ type Queryable interface {
//----------------------------------------
// MultiStore
type MultiStore interface {
type MultiStore interface { //nolint
Store
// Cache wrap MultiStore.
@ -139,10 +139,6 @@ type CacheKVStore interface {
cache-wraps make no sense. It can return KVStore, HeapStore,
SpaceStore, etc.
*/
type CacheWrapper interface {
CacheWrap() CacheWrap
}
type CacheWrap interface {
// Write syncs with the underlying store.
@ -152,6 +148,10 @@ type CacheWrap interface {
CacheWrap() CacheWrap
}
type CacheWrapper interface { //nolint
CacheWrap() CacheWrap
}
//----------------------------------------
// CommitID
@ -161,7 +161,7 @@ type CommitID struct {
Hash []byte
}
func (cid CommitID) IsZero() bool {
func (cid CommitID) IsZero() bool { //nolint
return cid.Version == 0 && len(cid.Hash) == 0
}
@ -172,9 +172,11 @@ func (cid CommitID) String() string {
//----------------------------------------
// Store types
// kind of store
type StoreType int
const (
//nolint
StoreTypeMulti StoreType = iota
StoreTypeDB
StoreTypeIAVL

View File

@ -4,6 +4,7 @@ import (
crypto "github.com/tendermint/go-crypto"
)
// Transactions messages must fulfill the Msg
type Msg interface {
// Return the message type.
@ -26,6 +27,7 @@ type Msg interface {
GetSigners() []crypto.Address
}
// Transactions objects must fulfill the Tx
type Tx interface {
// Gets the Msg.
@ -47,13 +49,18 @@ type Tx interface {
var _ Tx = (*StdTx)(nil)
// standard transaction form
type StdTx struct {
Msg
Signatures []StdSignature
}
//nolint
func (tx StdTx) GetMsg() Msg { return tx.Msg }
func (tx StdTx) GetFeePayer() crypto.Address { return tx.Signatures[0].PubKey.Address() }
func (tx StdTx) GetSignatures() []StdSignature { return tx.Signatures }
//-------------------------------------
// Application function variable used to unmarshal transaction bytes
type TxDecoder func(txBytes []byte) (Tx, Error)