-
Notifications
You must be signed in to change notification settings - Fork 0
/
sdk_operations.go
132 lines (114 loc) · 4.77 KB
/
sdk_operations.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
package simulation
import (
"errors"
"math/rand"
"github.com/cosmos/cosmos-sdk/baseapp"
"github.com/cosmos/cosmos-sdk/codec"
sdk "github.com/cosmos/cosmos-sdk/types"
simtypes "github.com/cosmos/cosmos-sdk/types/simulation"
"github.com/cosmos/cosmos-sdk/x/simulation"
sdkslashing "github.com/cosmos/cosmos-sdk/x/slashing/types"
"github.com/incubus-network/fanfury-sdk/v2/furyapp/helpers"
furyappparams "github.com/incubus-network/fanfury-sdk/v2/furyapp/params"
"github.com/incubus-network/fanfury-sdk/v2/x/lsnative/slashing/keeper"
"github.com/incubus-network/fanfury-sdk/v2/x/lsnative/slashing/types"
stakingkeeper "github.com/incubus-network/fanfury-sdk/v2/x/lsnative/staking/keeper"
)
// SdkWeightedOperations returns all the operations from the module with their respective weights
func SdkWeightedOperations(
appParams simtypes.AppParams, cdc codec.JSONCodec, ak types.AccountKeeper,
bk types.BankKeeper, k keeper.Keeper, sk types.StakingKeeper,
) simulation.WeightedOperations {
var weightMsgUnjail int
appParams.GetOrGenerate(cdc, OpWeightMsgUnjail, &weightMsgUnjail, nil,
func(_ *rand.Rand) {
weightMsgUnjail = furyappparams.DefaultWeightMsgUnjail
},
)
return simulation.WeightedOperations{
simulation.NewWeightedOperation(
weightMsgUnjail,
SimulateSdkMsgUnjail(ak, bk, k, sk.(stakingkeeper.Keeper)),
),
}
}
// SimulateSdkMsgUnjail generates a MsgUnjail with random values
func SimulateSdkMsgUnjail(ak types.AccountKeeper, bk types.BankKeeper, k keeper.Keeper, sk stakingkeeper.Keeper) simtypes.Operation {
return func(
r *rand.Rand, app *baseapp.BaseApp, ctx sdk.Context,
accs []simtypes.Account, chainID string,
) (simtypes.OperationMsg, []simtypes.FutureOperation, error) {
validator, ok := stakingkeeper.RandomValidator(r, sk, ctx)
if !ok {
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "validator is not ok"), nil, nil // skip
}
simAccount, found := simtypes.FindAccount(accs, sdk.AccAddress(validator.GetOperator()))
if !found {
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "unable to find account"), nil, nil // skip
}
if !validator.IsJailed() {
// TODO: due to this condition this message is almost, if not always, skipped !
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "validator is not jailed"), nil, nil
}
consAddr, err := validator.GetConsAddr()
if err != nil {
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "unable to get validator consensus key"), nil, err
}
info, found := k.GetValidatorSigningInfo(ctx, consAddr)
if !found {
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "unable to find validator signing info"), nil, nil // skip
}
selfDel := sk.Delegation(ctx, simAccount.Address, validator.GetOperator())
if selfDel == nil {
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "self delegation is nil"), nil, nil // skip
}
account := ak.GetAccount(ctx, sdk.AccAddress(validator.GetOperator()))
spendable := bk.SpendableCoins(ctx, account.GetAddress())
fees, err := simtypes.RandomFees(r, ctx, spendable)
if err != nil {
return simtypes.NoOpMsg(sdkslashing.ModuleName, sdkslashing.TypeMsgUnjail, "unable to generate fees"), nil, err
}
msg := sdkslashing.NewMsgUnjail(validator.GetOperator())
txCfg := furyappparams.MakeTestEncodingConfig().TxConfig
tx, err := helpers.GenSignedMockTx(
r,
txCfg,
[]sdk.Msg{msg},
fees,
helpers.DefaultGenTxGas,
chainID,
[]uint64{account.GetAccountNumber()},
[]uint64{account.GetSequence()},
simAccount.PrivKey,
)
if err != nil {
return simtypes.NoOpMsg(sdkslashing.ModuleName, msg.Type(), "unable to generate mock tx"), nil, err
}
_, res, err := app.SimDeliver(txCfg.TxEncoder(), tx)
// result should fail if:
// - validator cannot be unjailed due to tombstone
// - validator is still in jailed period
// - self delegation too low
if info.Tombstoned ||
ctx.BlockHeader().Time.Before(info.JailedUntil) {
if res != nil && err == nil {
if info.Tombstoned {
return simtypes.NewOperationMsg(msg, true, "", nil), nil, errors.New("validator should not have been unjailed if validator tombstoned")
}
if ctx.BlockHeader().Time.Before(info.JailedUntil) {
return simtypes.NewOperationMsg(msg, true, "", nil), nil, errors.New("validator unjailed while validator still in jail period")
}
}
// msg failed as expected
return simtypes.NewOperationMsg(msg, false, "", nil), nil, nil
}
if err != nil {
noop := simtypes.NoOpMsg(sdkslashing.ModuleName, msg.Type(), "unable to deliver tx")
if res != nil {
return noop, nil, errors.New(res.Log)
}
return noop, nil, err
}
return simtypes.NewOperationMsg(msg, true, "", nil), nil, nil
}
}