auth.AccountStore assumes go-wire; Remove GetTxBytes() from Tx
This commit is contained in:
parent
6d3b5cb402
commit
8fda920de0
@ -30,7 +30,6 @@ func (tx testTx) Get(key interface{}) (value interface{}) { return nil }
|
||||
func (tx testTx) GetSignBytes() []byte { return nil }
|
||||
func (tx testTx) ValidateBasic() error { return nil }
|
||||
func (tx testTx) GetSigners() []crypto.Address { return nil }
|
||||
func (tx testTx) GetTxBytes() []byte { return nil }
|
||||
func (tx testTx) GetFeePayer() crypto.Address { return nil }
|
||||
func (tx testTx) GetSignatures() []sdk.StdSignature { return nil }
|
||||
|
||||
|
||||
@ -38,8 +38,18 @@ func (app *BasecoinApp) initMultiStore() {
|
||||
|
||||
// depends on initKeys()
|
||||
func (app *BasecoinApp) initAppStore() {
|
||||
app.accStore = auth.NewAccountStore(
|
||||
app.mainStoreKey,
|
||||
types.NewAppAccountCodecFromWireCodec(app.cdc),
|
||||
accStore := auth.NewAccountStore(
|
||||
app.mainStoreKey, // where accounts are persisted.
|
||||
&types.AppAccount{}, // prototype sdk.Account.
|
||||
)
|
||||
|
||||
// If there are additional interfaces & concrete types that need to be
|
||||
// registered w/ wire.Codec, they can be registered here before the
|
||||
// accStore is sealed.
|
||||
//
|
||||
// cdc := accStore.WireCodec()
|
||||
// cdc.RegisterInterface(...)
|
||||
// cdc.RegisterConcrete(...)
|
||||
|
||||
app.accStore = accStore.Seal()
|
||||
}
|
||||
|
||||
@ -1,8 +1,6 @@
|
||||
package types
|
||||
|
||||
import (
|
||||
wire "github.com/tendermint/go-wire"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/auth"
|
||||
)
|
||||
@ -12,7 +10,11 @@ var _ sdk.Account = (*AppAccount)(nil)
|
||||
type AppAccount struct {
|
||||
auth.BaseAccount
|
||||
|
||||
// Custom extensions for this application.
|
||||
// Custom extensions for this application. This is just an example of
|
||||
// extending auth.BaseAccount with custom fields.
|
||||
//
|
||||
// This is compatible with the stock auth.AccountStore, since
|
||||
// auth.AccountStore uses the flexible go-wire library.
|
||||
Name string
|
||||
}
|
||||
|
||||
@ -23,27 +25,3 @@ func (acc AppAccount) GetName() string {
|
||||
func (acc *AppAccount) SetName(name string) {
|
||||
acc.Name = name
|
||||
}
|
||||
|
||||
//----------------------------------------
|
||||
|
||||
type AppAccountCodec struct {
|
||||
cdc *wire.Codec
|
||||
}
|
||||
|
||||
func NewAppAccountCodecFromWireCodec(cdc *wire.Codec) AppAccountCodec {
|
||||
return AppAccountCodec{cdc}
|
||||
}
|
||||
|
||||
func (_ AppAccountCodec) Prototype() interface{} {
|
||||
return &AppAccount{}
|
||||
}
|
||||
|
||||
func (aac AppAccountCodec) Encode(o interface{}) (bz []byte, err error) {
|
||||
return aac.cdc.MarshalBinary(o)
|
||||
}
|
||||
|
||||
func (aac AppAccountCodec) Decode(bz []byte) (o interface{}, err error) {
|
||||
o = aac.Prototype()
|
||||
err = aac.cdc.UnmarshalBinary(bz, o)
|
||||
return o, err
|
||||
}
|
||||
|
||||
@ -101,10 +101,6 @@ func (tx dummyTx) GetSigners() []crypto.Address {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (tx dummyTx) GetTxBytes() []byte {
|
||||
return tx.bytes
|
||||
}
|
||||
|
||||
func (tx dummyTx) GetSignatures() []sdk.StdSignature {
|
||||
return nil
|
||||
}
|
||||
|
||||
@ -1,14 +0,0 @@
|
||||
package types
|
||||
|
||||
// A generic codec for a fixed type.
|
||||
type Codec interface {
|
||||
|
||||
// Returns a prototype (empty) object.
|
||||
Prototype() interface{}
|
||||
|
||||
// Encodes the object.
|
||||
Encode(o interface{}) ([]byte, error)
|
||||
|
||||
// Decodes an object.
|
||||
Decode(bz []byte) (interface{}, error)
|
||||
}
|
||||
@ -2,7 +2,6 @@ package types
|
||||
|
||||
import (
|
||||
crypto "github.com/tendermint/go-crypto"
|
||||
wire "github.com/tendermint/go-wire"
|
||||
)
|
||||
|
||||
type Msg interface {
|
||||
@ -34,10 +33,6 @@ type Tx interface {
|
||||
// deducted before the Msg is processed.
|
||||
GetFeePayer() crypto.Address
|
||||
|
||||
// Get the canonical byte representation of the Tx.
|
||||
// Includes any signatures (or empty slots).
|
||||
GetTxBytes() []byte
|
||||
|
||||
// Signatures returns the signature of signers who signed the Msg.
|
||||
// CONTRACT: Length returned is same as length of
|
||||
// pubkeys returned from MsgKeySigners, and the order
|
||||
@ -55,14 +50,7 @@ type StdTx struct {
|
||||
Signatures []StdSignature
|
||||
}
|
||||
|
||||
func (tx StdTx) GetFeePayer() crypto.Address { return tx.Signatures[0].PubKey.Address() }
|
||||
func (tx StdTx) GetTxBytes() []byte {
|
||||
bz, err := wire.MarshalBinary(tx) // XXX: this is bad
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bz
|
||||
}
|
||||
func (tx StdTx) GetFeePayer() crypto.Address { return tx.Signatures[0].PubKey.Address() }
|
||||
func (tx StdTx) GetSignatures() []StdSignature { return tx.Signatures }
|
||||
|
||||
type TxDecoder func(txBytes []byte) (Tx, error)
|
||||
|
||||
116
x/auth/store.go
116
x/auth/store.go
@ -1,52 +1,134 @@
|
||||
package auth
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
|
||||
crypto "github.com/tendermint/go-crypto"
|
||||
wire "github.com/tendermint/go-wire"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
)
|
||||
|
||||
// Implements sdk.AccountStore
|
||||
// Implements sdk.AccountStore.
|
||||
// This AccountStore encodes/decodes accounts using the
|
||||
// go-wire (binary) encoding/decoding library.
|
||||
type accountStore struct {
|
||||
key sdk.SubstoreKey
|
||||
codec sdk.Codec
|
||||
|
||||
// The (unexposed) key used to access the store from the Context.
|
||||
key sdk.SubstoreKey
|
||||
|
||||
// The prototypical sdk.Account concrete type.
|
||||
proto sdk.Account
|
||||
|
||||
// The wire codec for binary encoding/decoding of accounts.
|
||||
cdc *wire.Codec
|
||||
}
|
||||
|
||||
func NewAccountStore(key sdk.SubstoreKey, codec sdk.Codec) accountStore {
|
||||
// NewAccountStore returns a new sdk.AccountStore that
|
||||
// uses go-wire to (binary) encode and decode concrete sdk.Accounts.
|
||||
func NewAccountStore(key sdk.SubstoreKey, proto sdk.Account) accountStore {
|
||||
return accountStore{
|
||||
key: key,
|
||||
codec: codec,
|
||||
proto: proto,
|
||||
cdc: wire.NewCodec(),
|
||||
}
|
||||
}
|
||||
|
||||
// Implements sdk.AccountStore
|
||||
// Returns the go-wire codec. You may need to register interfaces
|
||||
// and concrete types here, if your app's sdk.Account
|
||||
// implementation includes interface fields.
|
||||
// NOTE: It is not secure to expose the codec, so check out
|
||||
// .Seal().
|
||||
func (as accountStore) WireCodec() *wire.Codec {
|
||||
return as.cdc
|
||||
}
|
||||
|
||||
// Returns a "sealed" accountStore.
|
||||
// The codec is not accessible from a sealedAccountStore
|
||||
func (as accountStore) Seal() sealedAccountStore {
|
||||
return sealedAccountStore{as}
|
||||
}
|
||||
|
||||
// Implements sdk.AccountStore.
|
||||
func (as accountStore) NewAccountWithAddress(ctx sdk.Context, addr crypto.Address) sdk.Account {
|
||||
acc := as.codec.Prototype().(sdk.Account)
|
||||
acc := as.clonePrototype()
|
||||
acc.SetAddress(addr)
|
||||
return acc
|
||||
}
|
||||
|
||||
// Implements sdk.AccountStore
|
||||
// Implements sdk.AccountStore.
|
||||
func (as accountStore) GetAccount(ctx sdk.Context, addr crypto.Address) sdk.Account {
|
||||
store := ctx.KVStore(as.key)
|
||||
bz := store.Get(addr)
|
||||
if bz == nil {
|
||||
return nil // XXX
|
||||
return nil
|
||||
}
|
||||
o, err := as.codec.Decode(bz)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return o.(sdk.Account)
|
||||
acc := as.decodeAccount(bz)
|
||||
return acc
|
||||
}
|
||||
|
||||
// Implements sdk.AccountStore
|
||||
// Implements sdk.AccountStore.
|
||||
func (as accountStore) SetAccount(ctx sdk.Context, acc sdk.Account) {
|
||||
addr := acc.GetAddress()
|
||||
store := ctx.KVStore(as.key)
|
||||
bz, err := as.codec.Encode(acc)
|
||||
bz := as.encodeAccount(acc)
|
||||
store.Set(addr, bz)
|
||||
}
|
||||
|
||||
//----------------------------------------
|
||||
// misc.
|
||||
|
||||
// Creates a new struct (or pointer to struct) from as.proto.
|
||||
func (as accountStore) clonePrototype() sdk.Account {
|
||||
protoRt := reflect.TypeOf(as.proto)
|
||||
if protoRt.Kind() == reflect.Ptr {
|
||||
protoCrt := protoRt.Elem()
|
||||
if protoCrt.Kind() != reflect.Struct {
|
||||
panic("AccountStore requires a struct proto sdk.Account, or a pointer to one")
|
||||
}
|
||||
protoRv := reflect.New(protoCrt)
|
||||
clone, ok := protoRv.Interface().(sdk.Account)
|
||||
if !ok {
|
||||
panic(fmt.Sprintf("AccountStore requires a proto sdk.Account, but %v doesn't implement sdk.Account", protoRt))
|
||||
}
|
||||
return clone
|
||||
} else {
|
||||
protoRv := reflect.New(protoRt).Elem()
|
||||
clone, ok := protoRv.Interface().(sdk.Account)
|
||||
if !ok {
|
||||
panic(fmt.Sprintf("AccountStore requires a proto sdk.Account, but %v doesn't implement sdk.Account", protoRt))
|
||||
}
|
||||
return clone
|
||||
}
|
||||
}
|
||||
|
||||
func (as accountStore) encodeAccount(acc sdk.Account) []byte {
|
||||
bz, err := as.cdc.MarshalBinary(acc)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
store.Set(addr, bz)
|
||||
return bz
|
||||
}
|
||||
|
||||
func (as accountStore) decodeAccount(bz []byte) sdk.Account {
|
||||
acc := as.clonePrototype()
|
||||
err := as.cdc.UnmarshalBinary(bz, &acc)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return acc
|
||||
}
|
||||
|
||||
//----------------------------------------
|
||||
// sealedAccountStore
|
||||
|
||||
type sealedAccountStore struct {
|
||||
accountStore
|
||||
}
|
||||
|
||||
// There's no way for external modules to mutate the
|
||||
// sas.accountStore.ctx from here, even with reflection.
|
||||
func (sas sealedAccountStore) WireCodec() *wire.Codec {
|
||||
panic("accountStore is sealed")
|
||||
}
|
||||
|
||||
Loading…
Reference in New Issue
Block a user