github.com/fibonacci-chain/fbc@v0.0.0-20231124064014-c7636198c1e9/libs/cosmos-sdk/x/staking/keeper/validator_test.go (about) 1 package keeper 2 3 import ( 4 "fmt" 5 "testing" 6 "time" 7 8 abci "github.com/fibonacci-chain/fbc/libs/tendermint/abci/types" 9 10 sdk "github.com/fibonacci-chain/fbc/libs/cosmos-sdk/types" 11 "github.com/fibonacci-chain/fbc/libs/cosmos-sdk/x/staking/types" 12 13 "github.com/stretchr/testify/assert" 14 "github.com/stretchr/testify/require" 15 ) 16 17 //_______________________________________________________ 18 19 func TestSetValidator(t *testing.T) { 20 ctx, _, keeper, _ := CreateTestInput(t, false, 10) 21 22 valPubKey := PKs[0] 23 valAddr := sdk.ValAddress(valPubKey.Address().Bytes()) 24 valTokens := sdk.TokensFromConsensusPower(10) 25 26 // test how the validator is set from a purely unbonbed pool 27 validator := types.NewValidator(valAddr, valPubKey, types.Description{}) 28 validator, _ = validator.AddTokensFromDel(valTokens) 29 require.Equal(t, sdk.Unbonded, validator.Status) 30 assert.Equal(t, valTokens, validator.Tokens) 31 assert.Equal(t, valTokens, validator.DelegatorShares.RoundInt()) 32 keeper.SetValidator(ctx, validator) 33 keeper.SetValidatorByPowerIndex(ctx, validator) 34 35 // ensure update 36 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 37 validator, found := keeper.GetValidator(ctx, valAddr) 38 require.True(t, found) 39 require.Equal(t, 1, len(updates)) 40 require.Equal(t, validator.ABCIValidatorUpdate(), updates[0]) 41 42 // after the save the validator should be bonded 43 require.Equal(t, sdk.Bonded, validator.Status) 44 assert.Equal(t, valTokens, validator.Tokens) 45 assert.Equal(t, valTokens, validator.DelegatorShares.RoundInt()) 46 47 // Check each store for being saved 48 resVal, found := keeper.GetValidator(ctx, valAddr) 49 assert.True(ValEq(t, validator, resVal)) 50 require.True(t, found) 51 52 resVals := keeper.GetLastValidators(ctx) 53 require.Equal(t, 1, len(resVals)) 54 assert.True(ValEq(t, validator, resVals[0])) 55 56 resVals = keeper.GetBondedValidatorsByPower(ctx) 57 require.Equal(t, 1, len(resVals)) 58 require.True(ValEq(t, validator, resVals[0])) 59 60 resVals = keeper.GetValidators(ctx, 1) 61 require.Equal(t, 1, len(resVals)) 62 require.True(ValEq(t, validator, resVals[0])) 63 64 resVals = keeper.GetValidators(ctx, 10) 65 require.Equal(t, 1, len(resVals)) 66 require.True(ValEq(t, validator, resVals[0])) 67 68 allVals := keeper.GetAllValidators(ctx) 69 require.Equal(t, 1, len(allVals)) 70 } 71 72 func TestUpdateValidatorByPowerIndex(t *testing.T) { 73 ctx, _, keeper, _ := CreateTestInput(t, false, 0) 74 75 bondedPool := keeper.GetBondedPool(ctx) 76 notBondedPool := keeper.GetNotBondedPool(ctx) 77 bondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), sdk.TokensFromConsensusPower(1234)))) 78 notBondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), sdk.TokensFromConsensusPower(10000)))) 79 keeper.supplyKeeper.SetModuleAccount(ctx, bondedPool) 80 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 81 82 // add a validator 83 validator := types.NewValidator(addrVals[0], PKs[0], types.Description{}) 84 validator, delSharesCreated := validator.AddTokensFromDel(sdk.TokensFromConsensusPower(100)) 85 require.Equal(t, sdk.Unbonded, validator.Status) 86 require.Equal(t, sdk.TokensFromConsensusPower(100), validator.Tokens) 87 TestingUpdateValidator(keeper, ctx, validator, true) 88 validator, found := keeper.GetValidator(ctx, addrVals[0]) 89 require.True(t, found) 90 require.Equal(t, sdk.TokensFromConsensusPower(100), validator.Tokens) 91 92 power := types.GetValidatorsByPowerIndexKey(validator) 93 require.True(t, validatorByPowerIndexExists(keeper, ctx, power)) 94 95 // burn half the delegator shares 96 keeper.DeleteValidatorByPowerIndex(ctx, validator) 97 validator, burned := validator.RemoveDelShares(delSharesCreated.Quo(sdk.NewDec(2))) 98 require.Equal(t, sdk.TokensFromConsensusPower(50), burned) 99 TestingUpdateValidator(keeper, ctx, validator, true) // update the validator, possibly kicking it out 100 require.False(t, validatorByPowerIndexExists(keeper, ctx, power)) 101 102 validator, found = keeper.GetValidator(ctx, addrVals[0]) 103 require.True(t, found) 104 105 power = types.GetValidatorsByPowerIndexKey(validator) 106 require.True(t, validatorByPowerIndexExists(keeper, ctx, power)) 107 } 108 109 func TestUpdateBondedValidatorsDecreaseCliff(t *testing.T) { 110 numVals := 10 111 maxVals := 5 112 113 // create context, keeper, and pool for tests 114 ctx, _, keeper, _ := CreateTestInput(t, false, 0) 115 bondedPool := keeper.GetBondedPool(ctx) 116 notBondedPool := keeper.GetNotBondedPool(ctx) 117 118 // create keeper parameters 119 params := keeper.GetParams(ctx) 120 params.MaxValidators = uint16(maxVals) 121 keeper.SetParams(ctx, params) 122 123 // create a random pool 124 bondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), sdk.TokensFromConsensusPower(1234)))) 125 notBondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), sdk.TokensFromConsensusPower(10000)))) 126 keeper.supplyKeeper.SetModuleAccount(ctx, bondedPool) 127 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 128 129 validators := make([]types.Validator, numVals) 130 for i := 0; i < len(validators); i++ { 131 moniker := fmt.Sprintf("val#%d", int64(i)) 132 val := types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{Moniker: moniker}) 133 delTokens := sdk.TokensFromConsensusPower(int64((i + 1) * 10)) 134 val, _ = val.AddTokensFromDel(delTokens) 135 136 val = TestingUpdateValidator(keeper, ctx, val, true) 137 validators[i] = val 138 } 139 140 nextCliffVal := validators[numVals-maxVals+1] 141 142 // remove enough tokens to kick out the validator below the current cliff 143 // validator and next in line cliff validator 144 keeper.DeleteValidatorByPowerIndex(ctx, nextCliffVal) 145 shares := sdk.TokensFromConsensusPower(21) 146 nextCliffVal, _ = nextCliffVal.RemoveDelShares(shares.ToDec()) 147 nextCliffVal = TestingUpdateValidator(keeper, ctx, nextCliffVal, true) 148 149 expectedValStatus := map[int]sdk.BondStatus{ 150 9: sdk.Bonded, 8: sdk.Bonded, 7: sdk.Bonded, 5: sdk.Bonded, 4: sdk.Bonded, 151 0: sdk.Unbonding, 1: sdk.Unbonding, 2: sdk.Unbonding, 3: sdk.Unbonding, 6: sdk.Unbonding, 152 } 153 154 // require all the validators have their respective statuses 155 for valIdx, status := range expectedValStatus { 156 valAddr := validators[valIdx].OperatorAddress 157 val, _ := keeper.GetValidator(ctx, valAddr) 158 159 assert.Equal( 160 t, status, val.GetStatus(), 161 fmt.Sprintf("expected validator at index %v to have status: %s", valIdx, status), 162 ) 163 } 164 } 165 166 func TestSlashToZeroPowerRemoved(t *testing.T) { 167 // initialize setup 168 ctx, _, keeper, _ := CreateTestInput(t, false, 100) 169 170 // add a validator 171 validator := types.NewValidator(addrVals[0], PKs[0], types.Description{}) 172 valTokens := sdk.TokensFromConsensusPower(100) 173 174 bondedPool := keeper.GetBondedPool(ctx) 175 err := bondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), valTokens))) 176 require.NoError(t, err) 177 keeper.supplyKeeper.SetModuleAccount(ctx, bondedPool) 178 179 validator, _ = validator.AddTokensFromDel(valTokens) 180 require.Equal(t, sdk.Unbonded, validator.Status) 181 require.Equal(t, valTokens, validator.Tokens) 182 keeper.SetValidatorByConsAddr(ctx, validator) 183 validator = TestingUpdateValidator(keeper, ctx, validator, true) 184 require.Equal(t, valTokens, validator.Tokens, "\nvalidator %v\npool %v", validator, valTokens) 185 186 // slash the validator by 100% 187 consAddr0 := sdk.ConsAddress(PKs[0].Address()) 188 keeper.Slash(ctx, consAddr0, 0, 100, sdk.OneDec()) 189 // apply TM updates 190 keeper.ApplyAndReturnValidatorSetUpdates(ctx) 191 // validator should be unbonding 192 validator, _ = keeper.GetValidator(ctx, addrVals[0]) 193 require.Equal(t, validator.GetStatus(), sdk.Unbonding) 194 } 195 196 // This function tests UpdateValidator, GetValidator, GetLastValidators, RemoveValidator 197 func TestValidatorBasics(t *testing.T) { 198 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 199 200 //construct the validators 201 var validators [3]types.Validator 202 powers := []int64{9, 8, 7} 203 for i, power := range powers { 204 validators[i] = types.NewValidator(addrVals[i], PKs[i], types.Description{}) 205 validators[i].Status = sdk.Unbonded 206 validators[i].Tokens = sdk.ZeroInt() 207 tokens := sdk.TokensFromConsensusPower(power) 208 209 validators[i], _ = validators[i].AddTokensFromDel(tokens) 210 } 211 assert.Equal(t, sdk.TokensFromConsensusPower(9), validators[0].Tokens) 212 assert.Equal(t, sdk.TokensFromConsensusPower(8), validators[1].Tokens) 213 assert.Equal(t, sdk.TokensFromConsensusPower(7), validators[2].Tokens) 214 215 // check the empty keeper first 216 _, found := keeper.GetValidator(ctx, addrVals[0]) 217 require.False(t, found) 218 resVals := keeper.GetLastValidators(ctx) 219 require.Zero(t, len(resVals)) 220 221 resVals = keeper.GetValidators(ctx, 2) 222 require.Zero(t, len(resVals)) 223 224 // set and retrieve a record 225 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], true) 226 keeper.SetValidatorByConsAddr(ctx, validators[0]) 227 resVal, found := keeper.GetValidator(ctx, addrVals[0]) 228 require.True(t, found) 229 assert.True(ValEq(t, validators[0], resVal)) 230 231 // retrieve from consensus 232 resVal, found = keeper.GetValidatorByConsAddr(ctx, sdk.ConsAddress(PKs[0].Address())) 233 require.True(t, found) 234 assert.True(ValEq(t, validators[0], resVal)) 235 resVal, found = keeper.GetValidatorByConsAddr(ctx, sdk.GetConsAddress(PKs[0])) 236 require.True(t, found) 237 assert.True(ValEq(t, validators[0], resVal)) 238 239 resVals = keeper.GetLastValidators(ctx) 240 require.Equal(t, 1, len(resVals)) 241 assert.True(ValEq(t, validators[0], resVals[0])) 242 assert.Equal(t, sdk.Bonded, validators[0].Status) 243 assert.True(sdk.IntEq(t, sdk.TokensFromConsensusPower(9), validators[0].BondedTokens())) 244 245 // modify a records, save, and retrieve 246 validators[0].Status = sdk.Bonded 247 validators[0].Tokens = sdk.TokensFromConsensusPower(10) 248 validators[0].DelegatorShares = validators[0].Tokens.ToDec() 249 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], true) 250 resVal, found = keeper.GetValidator(ctx, addrVals[0]) 251 require.True(t, found) 252 assert.True(ValEq(t, validators[0], resVal)) 253 254 resVals = keeper.GetLastValidators(ctx) 255 require.Equal(t, 1, len(resVals)) 256 assert.True(ValEq(t, validators[0], resVals[0])) 257 258 // add other validators 259 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], true) 260 validators[2] = TestingUpdateValidator(keeper, ctx, validators[2], true) 261 resVal, found = keeper.GetValidator(ctx, addrVals[1]) 262 require.True(t, found) 263 assert.True(ValEq(t, validators[1], resVal)) 264 resVal, found = keeper.GetValidator(ctx, addrVals[2]) 265 require.True(t, found) 266 assert.True(ValEq(t, validators[2], resVal)) 267 268 resVals = keeper.GetLastValidators(ctx) 269 require.Equal(t, 3, len(resVals)) 270 assert.True(ValEq(t, validators[0], resVals[0])) // order doesn't matter here 271 assert.True(ValEq(t, validators[1], resVals[1])) 272 assert.True(ValEq(t, validators[2], resVals[2])) 273 274 // remove a record 275 276 // shouldn't be able to remove if status is not unbonded 277 assert.PanicsWithValue(t, 278 "cannot call RemoveValidator on bonded or unbonding validators", 279 func() { keeper.RemoveValidator(ctx, validators[1].OperatorAddress) }) 280 281 // shouldn't be able to remove if there are still tokens left 282 validators[1].Status = sdk.Unbonded 283 keeper.SetValidator(ctx, validators[1]) 284 assert.PanicsWithValue(t, 285 "attempting to remove a validator which still contains tokens", 286 func() { keeper.RemoveValidator(ctx, validators[1].OperatorAddress) }) 287 288 validators[1].Tokens = sdk.ZeroInt() // ...remove all tokens 289 keeper.SetValidator(ctx, validators[1]) // ...set the validator 290 keeper.RemoveValidator(ctx, validators[1].OperatorAddress) // Now it can be removed. 291 _, found = keeper.GetValidator(ctx, addrVals[1]) 292 require.False(t, found) 293 } 294 295 // test how the validators are sorted, tests GetBondedValidatorsByPower 296 func TestGetValidatorSortingUnmixed(t *testing.T) { 297 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 298 299 // initialize some validators into the state 300 amts := []int64{ 301 0, 302 100, 303 1, 304 400, 305 200} 306 n := len(amts) 307 var validators [5]types.Validator 308 for i, amt := range amts { 309 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 310 validators[i].Status = sdk.Bonded 311 validators[i].Tokens = sdk.NewIntFromBigInt(sdk.NewDec(amt).Int) 312 validators[i].DelegatorShares = sdk.NewDec(amt) 313 TestingUpdateValidator(keeper, ctx, validators[i], true) 314 } 315 316 // first make sure everything made it in to the gotValidator group 317 resValidators := keeper.GetBondedValidatorsByPower(ctx) 318 assert.Equal(t, n, len(resValidators)) 319 assert.Equal(t, sdk.NewInt(400).Mul(sdk.PowerReduction), resValidators[0].BondedTokens(), "%v", resValidators) 320 assert.Equal(t, sdk.NewInt(200).Mul(sdk.PowerReduction), resValidators[1].BondedTokens(), "%v", resValidators) 321 assert.Equal(t, sdk.NewInt(100).Mul(sdk.PowerReduction), resValidators[2].BondedTokens(), "%v", resValidators) 322 assert.Equal(t, sdk.NewInt(1).Mul(sdk.PowerReduction), resValidators[3].BondedTokens(), "%v", resValidators) 323 assert.Equal(t, sdk.NewInt(0), resValidators[4].BondedTokens(), "%v", resValidators) 324 assert.Equal(t, validators[3].OperatorAddress, resValidators[0].OperatorAddress, "%v", resValidators) 325 assert.Equal(t, validators[4].OperatorAddress, resValidators[1].OperatorAddress, "%v", resValidators) 326 assert.Equal(t, validators[1].OperatorAddress, resValidators[2].OperatorAddress, "%v", resValidators) 327 assert.Equal(t, validators[2].OperatorAddress, resValidators[3].OperatorAddress, "%v", resValidators) 328 assert.Equal(t, validators[0].OperatorAddress, resValidators[4].OperatorAddress, "%v", resValidators) 329 330 // test a basic increase in voting power 331 validators[3].Tokens = sdk.NewInt(500).Mul(sdk.PowerReduction) 332 TestingUpdateValidator(keeper, ctx, validators[3], true) 333 resValidators = keeper.GetBondedValidatorsByPower(ctx) 334 require.Equal(t, len(resValidators), n) 335 assert.True(ValEq(t, validators[3], resValidators[0])) 336 337 // test a decrease in voting power 338 validators[3].Tokens = sdk.NewInt(300).Mul(sdk.PowerReduction) 339 TestingUpdateValidator(keeper, ctx, validators[3], true) 340 resValidators = keeper.GetBondedValidatorsByPower(ctx) 341 require.Equal(t, len(resValidators), n) 342 assert.True(ValEq(t, validators[3], resValidators[0])) 343 assert.True(ValEq(t, validators[4], resValidators[1])) 344 345 // test equal voting power, different age 346 validators[3].Tokens = sdk.NewInt(200).Mul(sdk.PowerReduction) 347 ctx.SetBlockHeight(10) 348 TestingUpdateValidator(keeper, ctx, validators[3], true) 349 resValidators = keeper.GetBondedValidatorsByPower(ctx) 350 require.Equal(t, len(resValidators), n) 351 assert.True(ValEq(t, validators[3], resValidators[0])) 352 assert.True(ValEq(t, validators[4], resValidators[1])) 353 354 // no change in voting power - no change in sort 355 ctx.SetBlockHeight(20) 356 TestingUpdateValidator(keeper, ctx, validators[4], true) 357 resValidators = keeper.GetBondedValidatorsByPower(ctx) 358 require.Equal(t, len(resValidators), n) 359 assert.True(ValEq(t, validators[3], resValidators[0])) 360 assert.True(ValEq(t, validators[4], resValidators[1])) 361 362 // change in voting power of both validators, both still in v-set, no age change 363 validators[3].Tokens = sdk.NewInt(300).Mul(sdk.PowerReduction) 364 validators[4].Tokens = sdk.NewInt(300).Mul(sdk.PowerReduction) 365 TestingUpdateValidator(keeper, ctx, validators[3], true) 366 resValidators = keeper.GetBondedValidatorsByPower(ctx) 367 require.Equal(t, len(resValidators), n) 368 ctx.SetBlockHeight(30) 369 TestingUpdateValidator(keeper, ctx, validators[4], true) 370 resValidators = keeper.GetBondedValidatorsByPower(ctx) 371 require.Equal(t, len(resValidators), n, "%v", resValidators) 372 assert.True(ValEq(t, validators[3], resValidators[0])) 373 assert.True(ValEq(t, validators[4], resValidators[1])) 374 } 375 376 func TestGetValidatorSortingMixed(t *testing.T) { 377 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 378 bondedPool := keeper.GetBondedPool(ctx) 379 notBondedPool := keeper.GetNotBondedPool(ctx) 380 bondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), sdk.TokensFromConsensusPower(501)))) 381 notBondedPool.SetCoins(sdk.NewCoins(sdk.NewCoin(keeper.BondDenom(ctx), sdk.TokensFromConsensusPower(0)))) 382 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 383 keeper.supplyKeeper.SetModuleAccount(ctx, bondedPool) 384 385 // now 2 max resValidators 386 params := keeper.GetParams(ctx) 387 params.MaxValidators = 2 388 keeper.SetParams(ctx, params) 389 390 // initialize some validators into the state 391 amts := []int64{ 392 0, 393 100, 394 1, 395 400, 396 200} 397 398 var validators [5]types.Validator 399 for i, amt := range amts { 400 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 401 validators[i].DelegatorShares = sdk.NewDec(amt) 402 validators[i].Status = sdk.Bonded 403 validators[i].Tokens = sdk.NewIntFromBigInt(sdk.NewDec(amt).Int) 404 TestingUpdateValidator(keeper, ctx, validators[i], true) 405 } 406 407 val0, found := keeper.GetValidator(ctx, sdk.ValAddress(Addrs[0])) 408 require.True(t, found) 409 val1, found := keeper.GetValidator(ctx, sdk.ValAddress(Addrs[1])) 410 require.True(t, found) 411 val2, found := keeper.GetValidator(ctx, sdk.ValAddress(Addrs[2])) 412 require.True(t, found) 413 val3, found := keeper.GetValidator(ctx, sdk.ValAddress(Addrs[3])) 414 require.True(t, found) 415 val4, found := keeper.GetValidator(ctx, sdk.ValAddress(Addrs[4])) 416 require.True(t, found) 417 require.Equal(t, sdk.Bonded, val0.Status) 418 require.Equal(t, sdk.Unbonding, val1.Status) 419 require.Equal(t, sdk.Unbonding, val2.Status) 420 require.Equal(t, sdk.Bonded, val3.Status) 421 require.Equal(t, sdk.Bonded, val4.Status) 422 423 // first make sure everything made it in to the gotValidator group 424 resValidators := keeper.GetBondedValidatorsByPower(ctx) 425 // The validators returned should match the max validators 426 assert.Equal(t, 2, len(resValidators)) 427 assert.Equal(t, sdk.NewInt(400).Mul(sdk.PowerReduction), resValidators[0].BondedTokens(), "%v", resValidators) 428 assert.Equal(t, sdk.NewInt(200).Mul(sdk.PowerReduction), resValidators[1].BondedTokens(), "%v", resValidators) 429 assert.Equal(t, validators[3].OperatorAddress, resValidators[0].OperatorAddress, "%v", resValidators) 430 assert.Equal(t, validators[4].OperatorAddress, resValidators[1].OperatorAddress, "%v", resValidators) 431 } 432 433 // TODO separate out into multiple tests 434 func TestGetValidatorsEdgeCases(t *testing.T) { 435 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 436 437 // set max validators to 2 438 params := keeper.GetParams(ctx) 439 nMax := uint16(2) 440 params.MaxValidators = nMax 441 keeper.SetParams(ctx, params) 442 443 // initialize some validators into the state 444 powers := []int64{0, 100, 400, 400} 445 var validators [4]types.Validator 446 for i, power := range powers { 447 moniker := fmt.Sprintf("val#%d", int64(i)) 448 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{Moniker: moniker}) 449 tokens := sdk.TokensFromConsensusPower(power) 450 validators[i], _ = validators[i].AddTokensFromDel(tokens) 451 notBondedPool := keeper.GetNotBondedPool(ctx) 452 require.NoError(t, notBondedPool.SetCoins(notBondedPool.GetCoins().Add(sdk.NewCoin(params.BondDenom, tokens)))) 453 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 454 validators[i] = TestingUpdateValidator(keeper, ctx, validators[i], true) 455 } 456 457 // ensure that the first two bonded validators are the largest validators 458 resValidators := keeper.GetBondedValidatorsByPower(ctx) 459 require.Equal(t, nMax, uint16(len(resValidators))) 460 assert.True(ValEq(t, validators[2], resValidators[0])) 461 assert.True(ValEq(t, validators[3], resValidators[1])) 462 463 // delegate 500 tokens to validator 0 464 keeper.DeleteValidatorByPowerIndex(ctx, validators[0]) 465 delTokens := sdk.TokensFromConsensusPower(500) 466 validators[0], _ = validators[0].AddTokensFromDel(delTokens) 467 notBondedPool := keeper.GetNotBondedPool(ctx) 468 newTokens := sdk.NewCoins() 469 require.NoError(t, notBondedPool.SetCoins(notBondedPool.GetCoins().Add(newTokens...))) 470 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 471 472 // test that the two largest validators are 473 // a) validator 0 with 500 tokens 474 // b) validator 2 with 400 tokens (delegated before validator 3) 475 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], true) 476 resValidators = keeper.GetBondedValidatorsByPower(ctx) 477 require.Equal(t, nMax, uint16(len(resValidators))) 478 assert.True(ValEq(t, validators[0], resValidators[0])) 479 assert.True(ValEq(t, validators[2], resValidators[1])) 480 481 // A validator which leaves the bonded validator set due to a decrease in voting power, 482 // then increases to the original voting power, does not get its spot back in the 483 // case of a tie. 484 // 485 // Order of operations for this test: 486 // - validator 3 enter validator set with 1 new token 487 // - validator 3 removed validator set by removing 201 tokens (validator 2 enters) 488 // - validator 3 adds 200 tokens (equal to validator 2 now) and does not get its spot back 489 490 // validator 3 enters bonded validator set 491 ctx.SetBlockHeight(40) 492 493 validators[3] = keeper.mustGetValidator(ctx, validators[3].OperatorAddress) 494 keeper.DeleteValidatorByPowerIndex(ctx, validators[3]) 495 validators[3], _ = validators[3].AddTokensFromDel(sdk.TokensFromConsensusPower(1)) 496 497 notBondedPool = keeper.GetNotBondedPool(ctx) 498 newTokens = sdk.NewCoins(sdk.NewCoin(params.BondDenom, sdk.TokensFromConsensusPower(1))) 499 require.NoError(t, notBondedPool.SetCoins(notBondedPool.GetCoins().Add(newTokens...))) 500 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 501 502 validators[3] = TestingUpdateValidator(keeper, ctx, validators[3], true) 503 resValidators = keeper.GetBondedValidatorsByPower(ctx) 504 require.Equal(t, nMax, uint16(len(resValidators))) 505 assert.True(ValEq(t, validators[0], resValidators[0])) 506 assert.True(ValEq(t, validators[3], resValidators[1])) 507 508 // validator 3 kicked out temporarily 509 keeper.DeleteValidatorByPowerIndex(ctx, validators[3]) 510 rmTokens := validators[3].TokensFromShares(sdk.NewDec(201)).TruncateInt() 511 validators[3], _ = validators[3].RemoveDelShares(sdk.NewDec(201)) 512 513 bondedPool := keeper.GetBondedPool(ctx) 514 require.NoError(t, bondedPool.SetCoins(bondedPool.GetCoins().Add(sdk.NewCoin(params.BondDenom, rmTokens)))) 515 keeper.supplyKeeper.SetModuleAccount(ctx, bondedPool) 516 517 validators[3] = TestingUpdateValidator(keeper, ctx, validators[3], true) 518 resValidators = keeper.GetBondedValidatorsByPower(ctx) 519 require.Equal(t, nMax, uint16(len(resValidators))) 520 assert.True(ValEq(t, validators[0], resValidators[0])) 521 assert.True(ValEq(t, validators[2], resValidators[1])) 522 523 // validator 3 does not get spot back 524 keeper.DeleteValidatorByPowerIndex(ctx, validators[3]) 525 validators[3], _ = validators[3].AddTokensFromDel(sdk.NewInt(200)) 526 527 notBondedPool = keeper.GetNotBondedPool(ctx) 528 require.NoError(t, notBondedPool.SetCoins(notBondedPool.GetCoins().Add(sdk.NewCoin(params.BondDenom, sdk.NewInt(200))))) 529 keeper.supplyKeeper.SetModuleAccount(ctx, notBondedPool) 530 531 validators[3] = TestingUpdateValidator(keeper, ctx, validators[3], true) 532 resValidators = keeper.GetBondedValidatorsByPower(ctx) 533 require.Equal(t, nMax, uint16(len(resValidators))) 534 assert.True(ValEq(t, validators[0], resValidators[0])) 535 assert.True(ValEq(t, validators[2], resValidators[1])) 536 _, exists := keeper.GetValidator(ctx, validators[3].OperatorAddress) 537 require.True(t, exists) 538 } 539 540 func TestValidatorBondHeight(t *testing.T) { 541 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 542 543 // now 2 max resValidators 544 params := keeper.GetParams(ctx) 545 params.MaxValidators = 2 546 keeper.SetParams(ctx, params) 547 548 // initialize some validators into the state 549 var validators [3]types.Validator 550 validators[0] = types.NewValidator(sdk.ValAddress(PKs[0].Address().Bytes()), PKs[0], types.Description{}) 551 validators[1] = types.NewValidator(sdk.ValAddress(Addrs[1]), PKs[1], types.Description{}) 552 validators[2] = types.NewValidator(sdk.ValAddress(Addrs[2]), PKs[2], types.Description{}) 553 554 tokens0 := sdk.TokensFromConsensusPower(200) 555 tokens1 := sdk.TokensFromConsensusPower(100) 556 tokens2 := sdk.TokensFromConsensusPower(100) 557 validators[0], _ = validators[0].AddTokensFromDel(tokens0) 558 validators[1], _ = validators[1].AddTokensFromDel(tokens1) 559 validators[2], _ = validators[2].AddTokensFromDel(tokens2) 560 561 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], true) 562 563 //////////////////////////////////////// 564 // If two validators both increase to the same voting power in the same block, 565 // the one with the first transaction should become bonded 566 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], true) 567 validators[2] = TestingUpdateValidator(keeper, ctx, validators[2], true) 568 569 resValidators := keeper.GetBondedValidatorsByPower(ctx) 570 require.Equal(t, uint16(len(resValidators)), params.MaxValidators) 571 572 assert.True(ValEq(t, validators[0], resValidators[0])) 573 assert.True(ValEq(t, validators[1], resValidators[1])) 574 keeper.DeleteValidatorByPowerIndex(ctx, validators[1]) 575 keeper.DeleteValidatorByPowerIndex(ctx, validators[2]) 576 delTokens := sdk.TokensFromConsensusPower(50) 577 validators[1], _ = validators[1].AddTokensFromDel(delTokens) 578 validators[2], _ = validators[2].AddTokensFromDel(delTokens) 579 validators[2] = TestingUpdateValidator(keeper, ctx, validators[2], true) 580 resValidators = keeper.GetBondedValidatorsByPower(ctx) 581 require.Equal(t, params.MaxValidators, uint16(len(resValidators))) 582 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], true) 583 assert.True(ValEq(t, validators[0], resValidators[0])) 584 assert.True(ValEq(t, validators[2], resValidators[1])) 585 } 586 587 func TestFullValidatorSetPowerChange(t *testing.T) { 588 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 589 params := keeper.GetParams(ctx) 590 max := 2 591 params.MaxValidators = uint16(2) 592 keeper.SetParams(ctx, params) 593 594 // initialize some validators into the state 595 powers := []int64{0, 100, 400, 400, 200} 596 var validators [5]types.Validator 597 for i, power := range powers { 598 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 599 tokens := sdk.TokensFromConsensusPower(power) 600 validators[i], _ = validators[i].AddTokensFromDel(tokens) 601 TestingUpdateValidator(keeper, ctx, validators[i], true) 602 } 603 for i := range powers { 604 var found bool 605 validators[i], found = keeper.GetValidator(ctx, validators[i].OperatorAddress) 606 require.True(t, found) 607 } 608 assert.Equal(t, sdk.Unbonded, validators[0].Status) 609 assert.Equal(t, sdk.Unbonding, validators[1].Status) 610 assert.Equal(t, sdk.Bonded, validators[2].Status) 611 assert.Equal(t, sdk.Bonded, validators[3].Status) 612 assert.Equal(t, sdk.Unbonded, validators[4].Status) 613 resValidators := keeper.GetBondedValidatorsByPower(ctx) 614 assert.Equal(t, max, len(resValidators)) 615 assert.True(ValEq(t, validators[2], resValidators[0])) // in the order of txs 616 assert.True(ValEq(t, validators[3], resValidators[1])) 617 618 // test a swap in voting power 619 620 tokens := sdk.TokensFromConsensusPower(600) 621 validators[0], _ = validators[0].AddTokensFromDel(tokens) 622 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], true) 623 resValidators = keeper.GetBondedValidatorsByPower(ctx) 624 assert.Equal(t, max, len(resValidators)) 625 assert.True(ValEq(t, validators[0], resValidators[0])) 626 assert.True(ValEq(t, validators[2], resValidators[1])) 627 } 628 629 func TestApplyAndReturnValidatorSetUpdatesAllNone(t *testing.T) { 630 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 631 632 powers := []int64{10, 20} 633 var validators [2]types.Validator 634 for i, power := range powers { 635 valPubKey := PKs[i+1] 636 valAddr := sdk.ValAddress(valPubKey.Address().Bytes()) 637 638 validators[i] = types.NewValidator(valAddr, valPubKey, types.Description{}) 639 tokens := sdk.TokensFromConsensusPower(power) 640 validators[i], _ = validators[i].AddTokensFromDel(tokens) 641 } 642 643 // test from nothing to something 644 // tendermintUpdate set: {} -> {c1, c3} 645 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 646 keeper.SetValidator(ctx, validators[0]) 647 keeper.SetValidatorByPowerIndex(ctx, validators[0]) 648 keeper.SetValidator(ctx, validators[1]) 649 keeper.SetValidatorByPowerIndex(ctx, validators[1]) 650 651 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 652 assert.Equal(t, 2, len(updates)) 653 validators[0], _ = keeper.GetValidator(ctx, validators[0].OperatorAddress) 654 validators[1], _ = keeper.GetValidator(ctx, validators[1].OperatorAddress) 655 assert.Equal(t, validators[0].ABCIValidatorUpdate(), updates[1]) 656 assert.Equal(t, validators[1].ABCIValidatorUpdate(), updates[0]) 657 } 658 659 func TestApplyAndReturnValidatorSetUpdatesIdentical(t *testing.T) { 660 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 661 662 powers := []int64{10, 20} 663 var validators [2]types.Validator 664 for i, power := range powers { 665 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 666 667 tokens := sdk.TokensFromConsensusPower(power) 668 validators[i], _ = validators[i].AddTokensFromDel(tokens) 669 670 } 671 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 672 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 673 require.Equal(t, 2, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 674 675 // test identical, 676 // tendermintUpdate set: {} -> {} 677 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 678 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 679 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 680 } 681 682 func TestApplyAndReturnValidatorSetUpdatesSingleValueChange(t *testing.T) { 683 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 684 685 powers := []int64{10, 20} 686 var validators [2]types.Validator 687 for i, power := range powers { 688 689 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 690 691 tokens := sdk.TokensFromConsensusPower(power) 692 validators[i], _ = validators[i].AddTokensFromDel(tokens) 693 694 } 695 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 696 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 697 require.Equal(t, 2, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 698 699 // test single value change 700 // tendermintUpdate set: {} -> {c1'} 701 validators[0].Status = sdk.Bonded 702 validators[0].Tokens = sdk.TokensFromConsensusPower(600) 703 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 704 705 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 706 707 require.Equal(t, 1, len(updates)) 708 require.Equal(t, validators[0].ABCIValidatorUpdate(), updates[0]) 709 } 710 711 func TestApplyAndReturnValidatorSetUpdatesMultipleValueChange(t *testing.T) { 712 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 713 714 powers := []int64{10, 20} 715 var validators [2]types.Validator 716 for i, power := range powers { 717 718 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 719 720 tokens := sdk.TokensFromConsensusPower(power) 721 validators[i], _ = validators[i].AddTokensFromDel(tokens) 722 723 } 724 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 725 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 726 require.Equal(t, 2, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 727 728 // test multiple value change 729 // tendermintUpdate set: {c1, c3} -> {c1', c3'} 730 delTokens1 := sdk.TokensFromConsensusPower(190) 731 delTokens2 := sdk.TokensFromConsensusPower(80) 732 validators[0], _ = validators[0].AddTokensFromDel(delTokens1) 733 validators[1], _ = validators[1].AddTokensFromDel(delTokens2) 734 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 735 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 736 737 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 738 require.Equal(t, 2, len(updates)) 739 require.Equal(t, validators[0].ABCIValidatorUpdate(), updates[0]) 740 require.Equal(t, validators[1].ABCIValidatorUpdate(), updates[1]) 741 } 742 743 func TestApplyAndReturnValidatorSetUpdatesInserted(t *testing.T) { 744 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 745 746 powers := []int64{10, 20, 5, 15, 25} 747 var validators [5]types.Validator 748 for i, power := range powers { 749 750 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 751 752 tokens := sdk.TokensFromConsensusPower(power) 753 validators[i], _ = validators[i].AddTokensFromDel(tokens) 754 755 } 756 757 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 758 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 759 require.Equal(t, 2, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 760 761 // test validtor added at the beginning 762 // tendermintUpdate set: {} -> {c0} 763 keeper.SetValidator(ctx, validators[2]) 764 keeper.SetValidatorByPowerIndex(ctx, validators[2]) 765 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 766 validators[2], _ = keeper.GetValidator(ctx, validators[2].OperatorAddress) 767 require.Equal(t, 1, len(updates)) 768 require.Equal(t, validators[2].ABCIValidatorUpdate(), updates[0]) 769 770 // test validtor added at the beginning 771 // tendermintUpdate set: {} -> {c0} 772 keeper.SetValidator(ctx, validators[3]) 773 keeper.SetValidatorByPowerIndex(ctx, validators[3]) 774 updates = keeper.ApplyAndReturnValidatorSetUpdates(ctx) 775 validators[3], _ = keeper.GetValidator(ctx, validators[3].OperatorAddress) 776 require.Equal(t, 1, len(updates)) 777 require.Equal(t, validators[3].ABCIValidatorUpdate(), updates[0]) 778 779 // test validtor added at the end 780 // tendermintUpdate set: {} -> {c0} 781 keeper.SetValidator(ctx, validators[4]) 782 keeper.SetValidatorByPowerIndex(ctx, validators[4]) 783 updates = keeper.ApplyAndReturnValidatorSetUpdates(ctx) 784 validators[4], _ = keeper.GetValidator(ctx, validators[4].OperatorAddress) 785 require.Equal(t, 1, len(updates)) 786 require.Equal(t, validators[4].ABCIValidatorUpdate(), updates[0]) 787 } 788 789 func TestApplyAndReturnValidatorSetUpdatesWithCliffValidator(t *testing.T) { 790 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 791 params := types.DefaultParams() 792 params.MaxValidators = 2 793 keeper.SetParams(ctx, params) 794 795 powers := []int64{10, 20, 5} 796 var validators [5]types.Validator 797 for i, power := range powers { 798 799 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 800 801 tokens := sdk.TokensFromConsensusPower(power) 802 validators[i], _ = validators[i].AddTokensFromDel(tokens) 803 804 } 805 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 806 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 807 require.Equal(t, 2, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 808 809 // test validator added at the end but not inserted in the valset 810 // tendermintUpdate set: {} -> {} 811 TestingUpdateValidator(keeper, ctx, validators[2], false) 812 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 813 require.Equal(t, 0, len(updates)) 814 815 // test validator change its power and become a gotValidator (pushing out an existing) 816 // tendermintUpdate set: {} -> {c0, c4} 817 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 818 819 tokens := sdk.TokensFromConsensusPower(10) 820 validators[2], _ = validators[2].AddTokensFromDel(tokens) 821 keeper.SetValidator(ctx, validators[2]) 822 keeper.SetValidatorByPowerIndex(ctx, validators[2]) 823 updates = keeper.ApplyAndReturnValidatorSetUpdates(ctx) 824 validators[2], _ = keeper.GetValidator(ctx, validators[2].OperatorAddress) 825 require.Equal(t, 2, len(updates), "%v", updates) 826 require.Equal(t, validators[0].ABCIValidatorUpdateZero(), updates[1]) 827 require.Equal(t, validators[2].ABCIValidatorUpdate(), updates[0]) 828 } 829 830 func TestApplyAndReturnValidatorSetUpdatesPowerDecrease(t *testing.T) { 831 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 832 833 powers := []int64{100, 100} 834 var validators [2]types.Validator 835 for i, power := range powers { 836 837 validators[i] = types.NewValidator(sdk.ValAddress(Addrs[i]), PKs[i], types.Description{}) 838 839 tokens := sdk.TokensFromConsensusPower(power) 840 validators[i], _ = validators[i].AddTokensFromDel(tokens) 841 842 } 843 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 844 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 845 require.Equal(t, 2, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 846 847 // check initial power 848 require.Equal(t, int64(100), validators[0].GetConsensusPower()) 849 require.Equal(t, int64(100), validators[1].GetConsensusPower()) 850 851 // test multiple value change 852 // tendermintUpdate set: {c1, c3} -> {c1', c3'} 853 delTokens1 := sdk.TokensFromConsensusPower(20) 854 delTokens2 := sdk.TokensFromConsensusPower(30) 855 validators[0], _ = validators[0].RemoveDelShares(delTokens1.ToDec()) 856 validators[1], _ = validators[1].RemoveDelShares(delTokens2.ToDec()) 857 validators[0] = TestingUpdateValidator(keeper, ctx, validators[0], false) 858 validators[1] = TestingUpdateValidator(keeper, ctx, validators[1], false) 859 860 // power has changed 861 require.Equal(t, int64(80), validators[0].GetConsensusPower()) 862 require.Equal(t, int64(70), validators[1].GetConsensusPower()) 863 864 // Tendermint updates should reflect power change 865 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 866 require.Equal(t, 2, len(updates)) 867 require.Equal(t, validators[0].ABCIValidatorUpdate(), updates[0]) 868 require.Equal(t, validators[1].ABCIValidatorUpdate(), updates[1]) 869 } 870 871 func TestApplyAndReturnValidatorSetUpdatesNewValidator(t *testing.T) { 872 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 873 params := keeper.GetParams(ctx) 874 params.MaxValidators = uint16(3) 875 876 keeper.SetParams(ctx, params) 877 878 powers := []int64{100, 100} 879 var validators [2]types.Validator 880 881 // initialize some validators into the state 882 for i, power := range powers { 883 884 valPubKey := PKs[i+1] 885 valAddr := sdk.ValAddress(valPubKey.Address().Bytes()) 886 887 validators[i] = types.NewValidator(valAddr, valPubKey, types.Description{}) 888 tokens := sdk.TokensFromConsensusPower(power) 889 validators[i], _ = validators[i].AddTokensFromDel(tokens) 890 891 keeper.SetValidator(ctx, validators[i]) 892 keeper.SetValidatorByPowerIndex(ctx, validators[i]) 893 } 894 895 // verify initial Tendermint updates are correct 896 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 897 require.Equal(t, len(validators), len(updates)) 898 validators[0], _ = keeper.GetValidator(ctx, validators[0].OperatorAddress) 899 validators[1], _ = keeper.GetValidator(ctx, validators[1].OperatorAddress) 900 require.Equal(t, validators[0].ABCIValidatorUpdate(), updates[0]) 901 require.Equal(t, validators[1].ABCIValidatorUpdate(), updates[1]) 902 903 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 904 905 // update initial validator set 906 for i, power := range powers { 907 908 keeper.DeleteValidatorByPowerIndex(ctx, validators[i]) 909 tokens := sdk.TokensFromConsensusPower(power) 910 validators[i], _ = validators[i].AddTokensFromDel(tokens) 911 912 keeper.SetValidator(ctx, validators[i]) 913 keeper.SetValidatorByPowerIndex(ctx, validators[i]) 914 } 915 916 // add a new validator that goes from zero power, to non-zero power, back to 917 // zero power 918 valPubKey := PKs[len(validators)+1] 919 valAddr := sdk.ValAddress(valPubKey.Address().Bytes()) 920 amt := sdk.NewInt(100) 921 922 validator := types.NewValidator(valAddr, valPubKey, types.Description{}) 923 validator, _ = validator.AddTokensFromDel(amt) 924 925 keeper.SetValidator(ctx, validator) 926 927 validator, _ = validator.RemoveDelShares(amt.ToDec()) 928 keeper.SetValidator(ctx, validator) 929 keeper.SetValidatorByPowerIndex(ctx, validator) 930 931 // add a new validator that increases in power 932 valPubKey = PKs[len(validators)+2] 933 valAddr = sdk.ValAddress(valPubKey.Address().Bytes()) 934 935 validator = types.NewValidator(valAddr, valPubKey, types.Description{}) 936 tokens := sdk.TokensFromConsensusPower(500) 937 validator, _ = validator.AddTokensFromDel(tokens) 938 keeper.SetValidator(ctx, validator) 939 keeper.SetValidatorByPowerIndex(ctx, validator) 940 941 // verify initial Tendermint updates are correct 942 updates = keeper.ApplyAndReturnValidatorSetUpdates(ctx) 943 validator, _ = keeper.GetValidator(ctx, validator.OperatorAddress) 944 validators[0], _ = keeper.GetValidator(ctx, validators[0].OperatorAddress) 945 validators[1], _ = keeper.GetValidator(ctx, validators[1].OperatorAddress) 946 require.Equal(t, len(validators)+1, len(updates)) 947 require.Equal(t, validator.ABCIValidatorUpdate(), updates[0]) 948 require.Equal(t, validators[0].ABCIValidatorUpdate(), updates[1]) 949 require.Equal(t, validators[1].ABCIValidatorUpdate(), updates[2]) 950 } 951 952 func TestApplyAndReturnValidatorSetUpdatesBondTransition(t *testing.T) { 953 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 954 params := keeper.GetParams(ctx) 955 params.MaxValidators = uint16(2) 956 957 keeper.SetParams(ctx, params) 958 959 powers := []int64{100, 200, 300} 960 var validators [3]types.Validator 961 962 // initialize some validators into the state 963 for i, power := range powers { 964 moniker := fmt.Sprintf("%d", i) 965 valPubKey := PKs[i+1] 966 valAddr := sdk.ValAddress(valPubKey.Address().Bytes()) 967 968 validators[i] = types.NewValidator(valAddr, valPubKey, types.Description{Moniker: moniker}) 969 tokens := sdk.TokensFromConsensusPower(power) 970 validators[i], _ = validators[i].AddTokensFromDel(tokens) 971 keeper.SetValidator(ctx, validators[i]) 972 keeper.SetValidatorByPowerIndex(ctx, validators[i]) 973 } 974 975 // verify initial Tendermint updates are correct 976 updates := keeper.ApplyAndReturnValidatorSetUpdates(ctx) 977 require.Equal(t, 2, len(updates)) 978 validators[2], _ = keeper.GetValidator(ctx, validators[2].OperatorAddress) 979 validators[1], _ = keeper.GetValidator(ctx, validators[1].OperatorAddress) 980 require.Equal(t, validators[2].ABCIValidatorUpdate(), updates[0]) 981 require.Equal(t, validators[1].ABCIValidatorUpdate(), updates[1]) 982 983 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 984 985 // delegate to validator with lowest power but not enough to bond 986 ctx.SetBlockHeight(1) 987 988 var found bool 989 validators[0], found = keeper.GetValidator(ctx, validators[0].OperatorAddress) 990 require.True(t, found) 991 992 keeper.DeleteValidatorByPowerIndex(ctx, validators[0]) 993 tokens := sdk.TokensFromConsensusPower(1) 994 validators[0], _ = validators[0].AddTokensFromDel(tokens) 995 keeper.SetValidator(ctx, validators[0]) 996 keeper.SetValidatorByPowerIndex(ctx, validators[0]) 997 998 // verify initial Tendermint updates are correct 999 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 1000 1001 // create a series of events that will bond and unbond the validator with 1002 // lowest power in a single block context (height) 1003 ctx.SetBlockHeight(2) 1004 1005 validators[1], found = keeper.GetValidator(ctx, validators[1].OperatorAddress) 1006 require.True(t, found) 1007 1008 keeper.DeleteValidatorByPowerIndex(ctx, validators[0]) 1009 validators[0], _ = validators[0].RemoveDelShares(validators[0].DelegatorShares) 1010 keeper.SetValidator(ctx, validators[0]) 1011 keeper.SetValidatorByPowerIndex(ctx, validators[0]) 1012 updates = keeper.ApplyAndReturnValidatorSetUpdates(ctx) 1013 require.Equal(t, 0, len(updates)) 1014 1015 keeper.DeleteValidatorByPowerIndex(ctx, validators[1]) 1016 tokens = sdk.TokensFromConsensusPower(250) 1017 validators[1], _ = validators[1].AddTokensFromDel(tokens) 1018 keeper.SetValidator(ctx, validators[1]) 1019 keeper.SetValidatorByPowerIndex(ctx, validators[1]) 1020 1021 // verify initial Tendermint updates are correct 1022 updates = keeper.ApplyAndReturnValidatorSetUpdates(ctx) 1023 require.Equal(t, 1, len(updates)) 1024 require.Equal(t, validators[1].ABCIValidatorUpdate(), updates[0]) 1025 1026 require.Equal(t, 0, len(keeper.ApplyAndReturnValidatorSetUpdates(ctx))) 1027 } 1028 1029 func TestUpdateValidatorCommission(t *testing.T) { 1030 ctx, _, keeper, _ := CreateTestInput(t, false, 1000) 1031 ctx.SetBlockHeader(abci.Header{Time: time.Now().UTC()}) 1032 1033 commission1 := types.NewCommissionWithTime( 1034 sdk.NewDecWithPrec(1, 1), sdk.NewDecWithPrec(3, 1), 1035 sdk.NewDecWithPrec(1, 1), time.Now().UTC().Add(time.Duration(-1)*time.Hour), 1036 ) 1037 commission2 := types.NewCommission(sdk.NewDecWithPrec(1, 1), sdk.NewDecWithPrec(3, 1), sdk.NewDecWithPrec(1, 1)) 1038 1039 val1 := types.NewValidator(addrVals[0], PKs[0], types.Description{}) 1040 val2 := types.NewValidator(addrVals[1], PKs[1], types.Description{}) 1041 1042 val1, _ = val1.SetInitialCommission(commission1) 1043 val2, _ = val2.SetInitialCommission(commission2) 1044 1045 keeper.SetValidator(ctx, val1) 1046 keeper.SetValidator(ctx, val2) 1047 1048 testCases := []struct { 1049 validator types.Validator 1050 newRate sdk.Dec 1051 expectedErr bool 1052 }{ 1053 {val1, sdk.ZeroDec(), true}, 1054 {val2, sdk.NewDecWithPrec(-1, 1), true}, 1055 {val2, sdk.NewDecWithPrec(4, 1), true}, 1056 {val2, sdk.NewDecWithPrec(3, 1), true}, 1057 {val2, sdk.NewDecWithPrec(2, 1), false}, 1058 } 1059 1060 for i, tc := range testCases { 1061 commission, err := keeper.UpdateValidatorCommission(ctx, tc.validator, tc.newRate) 1062 1063 if tc.expectedErr { 1064 require.Error(t, err, "expected error for test case #%d with rate: %s", i, tc.newRate) 1065 } else { 1066 tc.validator.Commission = commission 1067 keeper.SetValidator(ctx, tc.validator) 1068 val, found := keeper.GetValidator(ctx, tc.validator.OperatorAddress) 1069 1070 require.True(t, found, 1071 "expected to find validator for test case #%d with rate: %s", i, tc.newRate, 1072 ) 1073 require.NoError(t, err, 1074 "unexpected error for test case #%d with rate: %s", i, tc.newRate, 1075 ) 1076 require.Equal(t, tc.newRate, val.Commission.Rate, 1077 "expected new validator commission rate for test case #%d with rate: %s", i, tc.newRate, 1078 ) 1079 require.Equal(t, ctx.BlockHeader().Time, val.Commission.UpdateTime, 1080 "expected new validator commission update time for test case #%d with rate: %s", i, tc.newRate, 1081 ) 1082 } 1083 } 1084 }