everything but IBC module
This commit is contained in:
parent
2fc5cc6bcd
commit
131289ce70
|
@ -59,12 +59,12 @@ func NewBasecoinApp(logger log.Logger, db dbm.DB) *BasecoinApp {
|
|||
coinKeeper := bank.NewCoinKeeper(app.accountMapper)
|
||||
coolKeeper := cool.NewKeeper(app.capKeyMainStore, coinKeeper)
|
||||
ibcMapper := ibc.NewIBCMapper(app.cdc, app.capKeyIBCStore)
|
||||
stakingMapper := staking.NewMapper(app.capKeyStakingStore)
|
||||
stakeKeeper := staking.NewKeeper(app.capKeyStakingStore, coinKeeper)
|
||||
app.Router().
|
||||
AddRoute("bank", coinKeeper.Handler).
|
||||
AddRoute("cool", coolKeeper.Handler).
|
||||
AddRoute("ibc", ibc.NewHandler(ibcMapper, coinKeeper)).
|
||||
AddRoute("staking", staking.NewHandler(stakingMapper, coinKeeper))
|
||||
AddRoute("staking", stakeKeeper.Handler)
|
||||
|
||||
// initialize BaseApp
|
||||
app.SetTxDecoder(app.txDecoder)
|
||||
|
|
|
@ -6,11 +6,16 @@ import (
|
|||
|
||||
const (
|
||||
// Staking errors reserve 300 - 399.
|
||||
CodeEmptyValidator sdk.CodeType = 300
|
||||
CodeInvalidUnbond sdk.CodeType = 301
|
||||
CodeEmptyStake sdk.CodeType = 302
|
||||
CodeEmptyValidator sdk.CodeType = 300
|
||||
CodeInvalidUnbond sdk.CodeType = 301
|
||||
CodeEmptyStake sdk.CodeType = 302
|
||||
CodeIncorrectStakingToken sdk.CodeType = 303
|
||||
)
|
||||
|
||||
func ErrIncorrectStakingToken() sdk.Error {
|
||||
return newError(CodeIncorrectStakingToken, "")
|
||||
}
|
||||
|
||||
func ErrEmptyValidator() sdk.Error {
|
||||
return newError(CodeEmptyValidator, "")
|
||||
}
|
||||
|
|
|
@ -4,29 +4,21 @@ import (
|
|||
abci "github.com/tendermint/abci/types"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank"
|
||||
)
|
||||
|
||||
func NewHandler(sm StakingMapper, ck bank.CoinKeeper) sdk.Handler {
|
||||
return func(ctx sdk.Context, msg sdk.Msg) sdk.Result {
|
||||
switch msg := msg.(type) {
|
||||
case BondMsg:
|
||||
return handleBondMsg(ctx, sm, ck, msg)
|
||||
case UnbondMsg:
|
||||
return handleUnbondMsg(ctx, sm, ck, msg)
|
||||
default:
|
||||
return sdk.ErrUnknownRequest("No match for message type.").Result()
|
||||
}
|
||||
func (k Keeper) Handler(ctx sdk.Context, msg sdk.Msg) sdk.Result {
|
||||
switch msg := msg.(type) {
|
||||
case BondMsg:
|
||||
return handleBondMsg(ctx, k, msg)
|
||||
case UnbondMsg:
|
||||
return handleUnbondMsg(ctx, k, msg)
|
||||
default:
|
||||
return sdk.ErrUnknownRequest("No match for message type.").Result()
|
||||
}
|
||||
}
|
||||
|
||||
func handleBondMsg(ctx sdk.Context, sm StakingMapper, ck bank.CoinKeeper, msg BondMsg) sdk.Result {
|
||||
_, err := ck.SubtractCoins(ctx, msg.Address, []sdk.Coin{msg.Stake})
|
||||
if err != nil {
|
||||
return err.Result()
|
||||
}
|
||||
|
||||
power, err := sm.Bond(ctx, msg.Address, msg.PubKey, msg.Stake.Amount)
|
||||
func handleBondMsg(ctx sdk.Context, k Keeper, msg BondMsg) sdk.Result {
|
||||
_, err := k.Bond(ctx, msg.Address, msg.Stake)
|
||||
if err != nil {
|
||||
return err.Result()
|
||||
}
|
||||
|
@ -42,8 +34,8 @@ func handleBondMsg(ctx sdk.Context, sm StakingMapper, ck bank.CoinKeeper, msg Bo
|
|||
}
|
||||
}
|
||||
|
||||
func handleUnbondMsg(ctx sdk.Context, sm StakingMapper, ck bank.CoinKeeper, msg UnbondMsg) sdk.Result {
|
||||
pubKey, power, err := sm.Unbond(ctx, msg.Address)
|
||||
func handleUnbondMsg(ctx sdk.Context, k Keeper, msg UnbondMsg) sdk.Result {
|
||||
pubKey, power, err := k.Unbond(ctx, msg.Address)
|
||||
if err != nil {
|
||||
return err.Result()
|
||||
}
|
||||
|
@ -52,7 +44,7 @@ func handleUnbondMsg(ctx sdk.Context, sm StakingMapper, ck bank.CoinKeeper, msg
|
|||
Denom: "mycoin",
|
||||
Amount: power,
|
||||
}
|
||||
_, err = ck.AddCoins(ctx, msg.Address, sdk.Coins{stake})
|
||||
_, err = k.ck.AddCoins(ctx, msg.Address, sdk.Coins{stake})
|
||||
if err != nil {
|
||||
return err.Result()
|
||||
}
|
||||
|
|
|
@ -0,0 +1,88 @@
|
|||
package staking
|
||||
|
||||
import (
|
||||
crypto "github.com/tendermint/go-crypto"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/wire"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank"
|
||||
)
|
||||
|
||||
const stakingToken = "steak"
|
||||
|
||||
type Keeper struct {
|
||||
ck bank.CoinKeeper
|
||||
|
||||
key sdk.StoreKey
|
||||
cdc *wire.Codec
|
||||
}
|
||||
|
||||
func NewKeeper(key sdk.StoreKey, coinKeeper bank.CoinKeeper) Keeper {
|
||||
cdc := wire.NewCodec()
|
||||
return Keeper{
|
||||
key: key,
|
||||
cdc: cdc,
|
||||
ck: coinKeeper,
|
||||
}
|
||||
}
|
||||
|
||||
func (k Keeper) getBondInfo(ctx sdk.Context, addr sdk.Address) bondInfo {
|
||||
store := ctx.KVStore(k.key)
|
||||
bz := store.Get(addr)
|
||||
if bz == nil {
|
||||
return bondInfo{}
|
||||
}
|
||||
var bi bondInfo
|
||||
err := k.cdc.UnmarshalBinary(bz, &bi)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bi
|
||||
}
|
||||
|
||||
func (k Keeper) setBondInfo(ctx sdk.Context, addr sdk.Address, bi bondInfo) {
|
||||
store := ctx.KVStore(k.key)
|
||||
bz, err := k.cdc.MarshalBinary(bi)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
store.Set(addr, bz)
|
||||
}
|
||||
|
||||
func (k Keeper) deleteBondInfo(ctx sdk.Context, addr sdk.Address) {
|
||||
store := ctx.KVStore(k.key)
|
||||
store.Delete(addr)
|
||||
}
|
||||
|
||||
func (k Keeper) Bond(ctx sdk.Context, addr sdk.Address, pubKey crypto.PubKey, stake sdk.Coin) (int64, sdk.Error) {
|
||||
if stake.Denom != stakingToken {
|
||||
return 0, ErrIncorrectStakingToken()
|
||||
}
|
||||
|
||||
_, err := k.ck.SubtractCoins(ctx, addr, []sdk.Coin{stake})
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
|
||||
bi := k.getBondInfo(ctx, addr)
|
||||
if bi.isEmpty() {
|
||||
bi = bondInfo{
|
||||
PubKey: pubKey,
|
||||
Power: 0,
|
||||
}
|
||||
}
|
||||
|
||||
bi.Power = bi.Power + stake.Amount
|
||||
|
||||
k.setBondInfo(ctx, addr, bi)
|
||||
return bi.Power, nil
|
||||
}
|
||||
|
||||
func (k Keeper) Unbond(ctx sdk.Context, addr sdk.Address) (crypto.PubKey, int64, sdk.Error) {
|
||||
bi := k.getBondInfo(ctx, addr)
|
||||
if bi.isEmpty() {
|
||||
return crypto.PubKey{}, 0, ErrInvalidUnbond()
|
||||
}
|
||||
k.deleteBondInfo(ctx, addr)
|
||||
return bi.PubKey, bi.Power, nil
|
||||
}
|
|
@ -13,6 +13,7 @@ import (
|
|||
|
||||
"github.com/cosmos/cosmos-sdk/store"
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
"github.com/cosmos/cosmos-sdk/x/bank"
|
||||
)
|
||||
|
||||
func setupMultiStore() (sdk.MultiStore, *sdk.KVStoreKey) {
|
||||
|
@ -24,14 +25,14 @@ func setupMultiStore() (sdk.MultiStore, *sdk.KVStoreKey) {
|
|||
return ms, capKey
|
||||
}
|
||||
|
||||
func TestStakingMapperGetSet(t *testing.T) {
|
||||
func TestKeeperGetSet(t *testing.T) {
|
||||
ms, capKey := setupMultiStore()
|
||||
|
||||
ctx := sdk.NewContext(ms, abci.Header{}, false, nil)
|
||||
stakingMapper := NewMapper(capKey)
|
||||
stakeKeeper := NewKeeper(capKey, bank.NewCoinKeeper(nil))
|
||||
addr := sdk.Address([]byte("some-address"))
|
||||
|
||||
bi := stakingMapper.getBondInfo(ctx, addr)
|
||||
bi := stakeKeeper.getBondInfo(ctx, addr)
|
||||
assert.Equal(t, bi, bondInfo{})
|
||||
|
||||
privKey := crypto.GenPrivKeyEd25519()
|
||||
|
@ -41,9 +42,9 @@ func TestStakingMapperGetSet(t *testing.T) {
|
|||
Power: int64(10),
|
||||
}
|
||||
fmt.Printf("Pubkey: %v\n", privKey.PubKey())
|
||||
stakingMapper.setBondInfo(ctx, addr, bi)
|
||||
stakeKeeper.setBondInfo(ctx, addr, bi)
|
||||
|
||||
savedBi := stakingMapper.getBondInfo(ctx, addr)
|
||||
savedBi := stakeKeeper.getBondInfo(ctx, addr)
|
||||
assert.NotNil(t, savedBi)
|
||||
fmt.Printf("Bond Info: %v\n", savedBi)
|
||||
assert.Equal(t, int64(10), savedBi.Power)
|
||||
|
@ -53,24 +54,24 @@ func TestBonding(t *testing.T) {
|
|||
ms, capKey := setupMultiStore()
|
||||
|
||||
ctx := sdk.NewContext(ms, abci.Header{}, false, nil)
|
||||
stakingMapper := NewMapper(capKey)
|
||||
stakeKeeper := NewKeeper(capKey, bank.NewCoinKeeper(nil))
|
||||
addr := sdk.Address([]byte("some-address"))
|
||||
privKey := crypto.GenPrivKeyEd25519()
|
||||
pubKey := privKey.PubKey()
|
||||
|
||||
_, _, err := stakingMapper.Unbond(ctx, addr)
|
||||
_, _, err := stakeKeeper.Unbond(ctx, addr)
|
||||
assert.Equal(t, err, ErrInvalidUnbond())
|
||||
|
||||
_, err = stakingMapper.Bond(ctx, addr, pubKey, 10)
|
||||
_, err = stakeKeeper.Bond(ctx, addr, pubKey, 10)
|
||||
assert.Nil(t, err)
|
||||
|
||||
power, err := stakingMapper.Bond(ctx, addr, pubKey, 10)
|
||||
power, err := stakeKeeper.Bond(ctx, addr, pubKey, 10)
|
||||
assert.Equal(t, int64(20), power)
|
||||
|
||||
pk, _, err := stakingMapper.Unbond(ctx, addr)
|
||||
pk, _, err := stakeKeeper.Unbond(ctx, addr)
|
||||
assert.Nil(t, err)
|
||||
assert.Equal(t, pubKey, pk)
|
||||
|
||||
_, _, err = stakingMapper.Unbond(ctx, addr)
|
||||
_, _, err = stakeKeeper.Unbond(ctx, addr)
|
||||
assert.Equal(t, err, ErrInvalidUnbond())
|
||||
}
|
|
@ -1,92 +0,0 @@
|
|||
package staking
|
||||
|
||||
import (
|
||||
crypto "github.com/tendermint/go-crypto"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
wire "github.com/cosmos/cosmos-sdk/wire"
|
||||
)
|
||||
|
||||
type StakingMapper struct {
|
||||
key sdk.StoreKey
|
||||
cdc *wire.Codec
|
||||
}
|
||||
|
||||
func NewMapper(key sdk.StoreKey) StakingMapper {
|
||||
cdc := wire.NewCodec()
|
||||
return StakingMapper{
|
||||
key: key,
|
||||
cdc: cdc,
|
||||
}
|
||||
}
|
||||
|
||||
func (sm StakingMapper) getBondInfo(ctx sdk.Context, addr sdk.Address) bondInfo {
|
||||
store := ctx.KVStore(sm.key)
|
||||
bz := store.Get(addr)
|
||||
if bz == nil {
|
||||
return bondInfo{}
|
||||
}
|
||||
var bi bondInfo
|
||||
err := sm.cdc.UnmarshalBinary(bz, &bi)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bi
|
||||
}
|
||||
|
||||
func (sm StakingMapper) setBondInfo(ctx sdk.Context, addr sdk.Address, bi bondInfo) {
|
||||
store := ctx.KVStore(sm.key)
|
||||
bz, err := sm.cdc.MarshalBinary(bi)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
store.Set(addr, bz)
|
||||
}
|
||||
|
||||
func (sm StakingMapper) deleteBondInfo(ctx sdk.Context, addr sdk.Address) {
|
||||
store := ctx.KVStore(sm.key)
|
||||
store.Delete(addr)
|
||||
}
|
||||
|
||||
func (sm StakingMapper) Bond(ctx sdk.Context, addr sdk.Address, pubKey crypto.PubKey, power int64) (int64, sdk.Error) {
|
||||
|
||||
bi := sm.getBondInfo(ctx, addr)
|
||||
if bi.isEmpty() {
|
||||
bi = bondInfo{
|
||||
PubKey: pubKey,
|
||||
Power: power,
|
||||
}
|
||||
sm.setBondInfo(ctx, addr, bi)
|
||||
return bi.Power, nil
|
||||
}
|
||||
|
||||
newPower := bi.Power + power
|
||||
newBi := bondInfo{
|
||||
PubKey: bi.PubKey,
|
||||
Power: newPower,
|
||||
}
|
||||
sm.setBondInfo(ctx, addr, newBi)
|
||||
|
||||
return newBi.Power, nil
|
||||
}
|
||||
|
||||
func (sm StakingMapper) Unbond(ctx sdk.Context, addr sdk.Address) (crypto.PubKey, int64, sdk.Error) {
|
||||
bi := sm.getBondInfo(ctx, addr)
|
||||
if bi.isEmpty() {
|
||||
return crypto.PubKey{}, 0, ErrInvalidUnbond()
|
||||
}
|
||||
sm.deleteBondInfo(ctx, addr)
|
||||
return bi.PubKey, bi.Power, nil
|
||||
}
|
||||
|
||||
type bondInfo struct {
|
||||
PubKey crypto.PubKey
|
||||
Power int64
|
||||
}
|
||||
|
||||
func (bi bondInfo) isEmpty() bool {
|
||||
if bi == (bondInfo{}) {
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
|
@ -0,0 +1,95 @@
|
|||
package staking
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
|
||||
crypto "github.com/tendermint/go-crypto"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
)
|
||||
|
||||
// -------------------------
|
||||
// BondMsg
|
||||
|
||||
type BondMsg struct {
|
||||
Address sdk.Address `json:"address"`
|
||||
Stake sdk.Coin `json:"coins"`
|
||||
PubKey crypto.PubKey `json:"pub_key"`
|
||||
}
|
||||
|
||||
func NewBondMsg(addr sdk.Address, stake sdk.Coin, pubKey crypto.PubKey) BondMsg {
|
||||
return BondMsg{
|
||||
Address: addr,
|
||||
Stake: stake,
|
||||
PubKey: pubKey,
|
||||
}
|
||||
}
|
||||
|
||||
func (msg BondMsg) Type() string {
|
||||
return "staking"
|
||||
}
|
||||
|
||||
func (msg BondMsg) ValidateBasic() sdk.Error {
|
||||
if msg.Stake.IsZero() {
|
||||
return ErrEmptyStake()
|
||||
}
|
||||
|
||||
if msg.PubKey.Empty() {
|
||||
return sdk.ErrInvalidPubKey("BondMsg.PubKey must not be empty")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg BondMsg) Get(key interface{}) interface{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg BondMsg) GetSignBytes() []byte {
|
||||
bz, err := json.Marshal(msg)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bz
|
||||
}
|
||||
|
||||
func (msg BondMsg) GetSigners() []sdk.Address {
|
||||
return []sdk.Address{msg.Address}
|
||||
}
|
||||
|
||||
// -------------------------
|
||||
// UnbondMsg
|
||||
|
||||
type UnbondMsg struct {
|
||||
Address sdk.Address `json:"address"`
|
||||
}
|
||||
|
||||
func NewUnbondMsg(addr sdk.Address) UnbondMsg {
|
||||
return UnbondMsg{
|
||||
Address: addr,
|
||||
}
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) Type() string {
|
||||
return "staking"
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) ValidateBasic() sdk.Error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) Get(key interface{}) interface{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) GetSignBytes() []byte {
|
||||
bz, err := json.Marshal(msg)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bz
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) GetSigners() []sdk.Address {
|
||||
return []sdk.Address{msg.Address}
|
||||
}
|
|
@ -1,95 +1,15 @@
|
|||
package staking
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
import crypto "github.com/tendermint/go-crypto"
|
||||
|
||||
crypto "github.com/tendermint/go-crypto"
|
||||
|
||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
||||
)
|
||||
|
||||
// -------------------------
|
||||
// BondMsg
|
||||
|
||||
type BondMsg struct {
|
||||
Address sdk.Address `json:"address"`
|
||||
Stake sdk.Coin `json:"coins"`
|
||||
PubKey crypto.PubKey `json:"pub_key"`
|
||||
type bondInfo struct {
|
||||
PubKey crypto.PubKey
|
||||
Power int64
|
||||
}
|
||||
|
||||
func NewBondMsg(addr sdk.Address, stake sdk.Coin, pubKey crypto.PubKey) BondMsg {
|
||||
return BondMsg{
|
||||
Address: addr,
|
||||
Stake: stake,
|
||||
PubKey: pubKey,
|
||||
func (bi bondInfo) isEmpty() bool {
|
||||
if bi == (bondInfo{}) {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
func (msg BondMsg) Type() string {
|
||||
return "staking"
|
||||
}
|
||||
|
||||
func (msg BondMsg) ValidateBasic() sdk.Error {
|
||||
if msg.Stake.IsZero() {
|
||||
return ErrEmptyStake()
|
||||
}
|
||||
|
||||
if msg.PubKey.Empty() {
|
||||
return sdk.ErrInvalidPubKey("BondMsg.PubKey must not be empty")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg BondMsg) Get(key interface{}) interface{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg BondMsg) GetSignBytes() []byte {
|
||||
bz, err := json.Marshal(msg)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bz
|
||||
}
|
||||
|
||||
func (msg BondMsg) GetSigners() []sdk.Address {
|
||||
return []sdk.Address{msg.Address}
|
||||
}
|
||||
|
||||
// -------------------------
|
||||
// UnbondMsg
|
||||
|
||||
type UnbondMsg struct {
|
||||
Address sdk.Address `json:"address"`
|
||||
}
|
||||
|
||||
func NewUnbondMsg(addr sdk.Address) UnbondMsg {
|
||||
return UnbondMsg{
|
||||
Address: addr,
|
||||
}
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) Type() string {
|
||||
return "staking"
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) ValidateBasic() sdk.Error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) Get(key interface{}) interface{} {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) GetSignBytes() []byte {
|
||||
bz, err := json.Marshal(msg)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return bz
|
||||
}
|
||||
|
||||
func (msg UnbondMsg) GetSigners() []sdk.Address {
|
||||
return []sdk.Address{msg.Address}
|
||||
return false
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue