[unit-testing] one-node-staked-vote (#1897)

* [unit-testing] Add test for when there are 33 Harmony nodes
	* Add test for Policy
	* Add test for QuorumThreshold

* [quroum] Give diff to last staked voter, make sure sum to one

* [quorum] Fix indent for travis
pull/1929/head
janet-harmony 5 years ago committed by Edgar Aroutiounian
parent e2bbac0089
commit aeb360cb83
  1. 7
      consensus/quorum/one-node-staked-vote.go
  2. 102
      consensus/quorum/one-node-staked-vote_test.go
  3. 19
      consensus/votepower/roster.go

@ -193,13 +193,6 @@ func (v *stakedVoteWeight) SetVoters(
Str("Raw-Staked", roster.RawStakedTotal.String()).
Msg("Total staked")
//switch {
//case roster.totalStakedPercent.Equal(totalShare) == false:
// return nil, errSumOfVotingPowerNotOne
//case roster.ourPercentage.Add(theirPercentage).Equal(totalShare) == false:
// return nil, errSumOfOursAndTheirsNotOne
//}
// Hold onto this calculation
v.roster = *roster
return &TallyResult{

@ -0,0 +1,102 @@
package quorum
import (
"math/big"
"math/rand"
"testing"
"github.com/ethereum/go-ethereum/common"
"github.com/harmony-one/bls/ffi/go/bls"
"github.com/harmony-one/harmony/consensus/votepower"
"github.com/harmony-one/harmony/numeric"
"github.com/harmony-one/harmony/shard"
)
var (
secretKeyMap map[shard.BlsPublicKey]bls.SecretKey
slotList shard.SlotList
roster *votepower.Roster
stakedVote Decider
result *TallyResult
harmonyNodes = 33
stakedNodes = 33
maxAccountGen = int64(98765654323123134)
accountGen = rand.New(rand.NewSource(1337))
maxKeyGen = int64(98765654323123134)
keyGen = rand.New(rand.NewSource(42))
maxStakeGen = int64(200)
stakeGen = rand.New(rand.NewSource(541))
)
func init() {
slotList = shard.SlotList{}
secretKeyMap = make(map[shard.BlsPublicKey]bls.SecretKey)
for i := 0; i < harmonyNodes; i++ {
newSlot, sKey := generateRandomSlot()
newSlot.TotalStake = nil
slotList = append(slotList, newSlot)
secretKeyMap[newSlot.BlsPublicKey] = sKey
}
for j := 0; j < stakedNodes; j++ {
newSlot, sKey := generateRandomSlot()
slotList = append(slotList, newSlot)
secretKeyMap[newSlot.BlsPublicKey] = sKey
}
stakedVote = NewDecider(SuperMajorityStake)
stakedVote.SetShardIDProvider(func() (uint32, error) { return 0, nil })
r, err := stakedVote.SetVoters(slotList)
if err != nil {
panic("Unable to SetVoters")
}
result = r
}
func generateRandomSlot() (shard.Slot, bls.SecretKey) {
addr := common.Address{}
addr.SetBytes(big.NewInt(int64(accountGen.Int63n(maxAccountGen))).Bytes())
secretKey := bls.SecretKey{}
secretKey.Deserialize(big.NewInt(int64(keyGen.Int63n(maxKeyGen))).Bytes())
key := shard.BlsPublicKey{}
key.FromLibBLSPublicKey(secretKey.GetPublicKey())
stake := numeric.NewDecFromBigInt(big.NewInt(int64(stakeGen.Int63n(maxStakeGen))))
return shard.Slot{addr, key, &stake}, secretKey
}
func Test33(t *testing.T) {
sum := result.ourPercent.Add(result.theirPercent)
if !sum.Equal(numeric.OneDec()) {
t.Errorf("Total voting power does not equal 1. Harmony voting power: %s, Staked voting power: %s, Sum: %s",
result.ourPercent, result.theirPercent, sum)
}
}
func TestPolicy(t *testing.T) {
expectedPolicy := SuperMajorityStake
policy := stakedVote.Policy()
if expectedPolicy != policy {
t.Errorf("Expected: %s, Got: %s", expectedPolicy.String(), policy.String())
}
}
func TestIsQuorumAchieved(t *testing.T) {
//
}
func TestQuorumThreshold(t *testing.T) {
expectedThreshold := numeric.NewDec(2).Quo(numeric.NewDec(3))
quorumThreshold := stakedVote.QuorumThreshold()
if !expectedThreshold.Equal(quorumThreshold) {
t.Errorf("Expected: %s, Got: %s", expectedThreshold.String(), quorumThreshold.String())
}
}
func TestIsRewardThresholdAchieved(t *testing.T) {
//
}
// ????
func TestShouldSlash(t *testing.T) {
//
}

@ -2,6 +2,7 @@ package votepower
import (
"github.com/ethereum/go-ethereum/common"
"github.com/harmony-one/harmony/internal/utils"
"github.com/harmony-one/harmony/numeric"
"github.com/harmony-one/harmony/shard"
)
@ -16,6 +17,7 @@ var (
type stakedVoter struct {
IsActive, IsHarmonyNode bool
EarningAccount common.Address
Identity shard.BlsPublicKey
EffectivePercent numeric.Dec
RawStake numeric.Dec
}
@ -29,7 +31,7 @@ type Roster struct {
HmySlotCount int64
}
// Compute ..
// Compute creates a new roster based off the shard.SlotList
func Compute(staked shard.SlotList) *Roster {
roster := NewRoster()
for i := range staked {
@ -45,12 +47,14 @@ func Compute(staked shard.SlotList) *Roster {
ourCount := numeric.NewDec(roster.HmySlotCount)
ourPercentage := numeric.ZeroDec()
theirPercentage := numeric.ZeroDec()
var lastStakedVoter *stakedVoter = nil
for i := range staked {
member := stakedVoter{
IsActive: true,
IsHarmonyNode: true,
EarningAccount: staked[i].EcdsaAddress,
Identity: staked[i].BlsPublicKey,
EffectivePercent: numeric.ZeroDec(),
RawStake: numeric.ZeroDec(),
}
@ -63,6 +67,7 @@ func Compute(staked shard.SlotList) *Roster {
Quo(roster.RawStakedTotal).
Mul(StakersShare)
theirPercentage = theirPercentage.Add(member.EffectivePercent)
lastStakedVoter = &member
} else { // Our node
// TODO See the todo on where this called in one-node-staked-vote,
// need to have these two values of our
@ -74,6 +79,18 @@ func Compute(staked shard.SlotList) *Roster {
roster.Voters[staked[i].BlsPublicKey] = member
}
// NOTE Enforce voting power sums to one, give diff (expect tiny amt) to last staked voter
if diff := numeric.OneDec().Sub(
ourPercentage.Add(theirPercentage),
); diff.GT(numeric.ZeroDec()) && lastStakedVoter != nil {
lastStakedVoter.EffectivePercent = lastStakedVoter.EffectivePercent.Add(diff)
theirPercentage = theirPercentage.Add(diff)
utils.Logger().Info().
Str("diff", diff.String()).
Str("bls-public-key-of-receipent", lastStakedVoter.Identity.Hex()).
Msg("sum of voting power of hmy & staked slots not equal to 1, gave diff to staked slot")
}
roster.OurVotingPowerTotalPercentage = ourPercentage
roster.TheirVotingPowerTotalPercentage = theirPercentage

Loading…
Cancel
Save