package keeper import ( "fmt" gogotypes "github.com/gogo/protobuf/types" "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/libs/log" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/exported" "github.com/cosmos/cosmos-sdk/x/auth/types" paramtypes "github.com/cosmos/cosmos-sdk/x/params/types" ) // AccountKeeper encodes/decodes accounts using the go-amino (binary) // encoding/decoding library. type AccountKeeper struct { key sdk.StoreKey cdc types.Codec paramSubspace paramtypes.Subspace // The prototypical Account constructor. proto func() exported.Account } // NewAccountKeeper returns a new sdk.AccountKeeper that uses go-amino to // (binary) encode and decode concrete sdk.Accounts. func NewAccountKeeper( cdc types.Codec, key sdk.StoreKey, paramstore paramtypes.Subspace, proto func() exported.Account, ) AccountKeeper { return AccountKeeper{ key: key, proto: proto, cdc: cdc, paramSubspace: paramstore.WithKeyTable(types.ParamKeyTable()), } } // Logger returns a module-specific logger. func (ak AccountKeeper) Logger(ctx sdk.Context) log.Logger { return ctx.Logger().With("module", fmt.Sprintf("x/%s", types.ModuleName)) } // GetPubKey Returns the PubKey of the account at address func (ak AccountKeeper) GetPubKey(ctx sdk.Context, addr sdk.AccAddress) (crypto.PubKey, error) { acc := ak.GetAccount(ctx, addr) if acc == nil { return nil, sdkerrors.Wrapf(sdkerrors.ErrUnknownAddress, "account %s does not exist", addr) } return acc.GetPubKey(), nil } // GetSequence Returns the Sequence of the account at address func (ak AccountKeeper) GetSequence(ctx sdk.Context, addr sdk.AccAddress) (uint64, error) { acc := ak.GetAccount(ctx, addr) if acc == nil { return 0, sdkerrors.Wrapf(sdkerrors.ErrUnknownAddress, "account %s does not exist", addr) } return acc.GetSequence(), nil } // GetNextAccountNumber returns and increments the global account number counter. // If the global account number is not set, it initializes it with value 0. func (ak AccountKeeper) GetNextAccountNumber(ctx sdk.Context) uint64 { var accNumber uint64 store := ctx.KVStore(ak.key) bz := store.Get(types.GlobalAccountNumberKey) if bz == nil { // initialize the account numbers accNumber = 0 } else { val := gogotypes.UInt64Value{} err := ak.cdc.UnmarshalBinaryBare(bz, &val) if err != nil { panic(err) } accNumber = val.GetValue() } bz = ak.cdc.MustMarshalBinaryBare(&gogotypes.UInt64Value{Value: accNumber + 1}) store.Set(types.GlobalAccountNumberKey, bz) return accNumber } func (ak AccountKeeper) decodeAccount(bz []byte) exported.Account { acc, err := ak.cdc.UnmarshalAccount(bz) if err != nil { panic(err) } return acc }