add rpc api for support monitor the signing power (#3848)

* add rpc api for https://github.com/harmony-one/watchdog/issues/11

* fix bug: last power will be cleaned up

* fix goimports
pull/3866/head
LuttyYang 3 years ago committed by GitHub
parent 6d8ba75248
commit 6bd1c152dd
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 25
      consensus/quorum/one-node-one-vote.go
  2. 14
      consensus/quorum/one-node-staked-vote.go
  3. 17
      consensus/quorum/quorum.go
  4. 1
      hmy/hmy.go
  5. 12
      node/api.go
  6. 7
      rpc/private_debug.go

@ -4,6 +4,8 @@ import (
"encoding/json" "encoding/json"
"math/big" "math/big"
"github.com/pkg/errors"
bls_core "github.com/harmony-one/bls/ffi/go/bls" bls_core "github.com/harmony-one/bls/ffi/go/bls"
"github.com/harmony-one/harmony/crypto/bls" "github.com/harmony-one/harmony/crypto/bls"
@ -20,6 +22,9 @@ type uniformVoteWeight struct {
DependencyInjectionWriter DependencyInjectionWriter
DependencyInjectionReader DependencyInjectionReader
SignatureReader SignatureReader
lastPowerSignersCountCache map[Phase]int64
lastParticipantsCount int64
} }
// Policy .. // Policy ..
@ -123,9 +128,29 @@ func (v *uniformVoteWeight) AmIMemberOfCommitee() bool {
} }
func (v *uniformVoteWeight) ResetPrepareAndCommitVotes() { func (v *uniformVoteWeight) ResetPrepareAndCommitVotes() {
v.lastPowerSignersCountCache[Prepare] = v.SignersCount(Prepare)
v.lastPowerSignersCountCache[Commit] = v.SignersCount(Commit)
v.lastParticipantsCount = v.ParticipantsCount()
v.reset([]Phase{Prepare, Commit}) v.reset([]Phase{Prepare, Commit})
} }
func (v *uniformVoteWeight) ResetViewChangeVotes() { func (v *uniformVoteWeight) ResetViewChangeVotes() {
v.lastPowerSignersCountCache[ViewChange] = v.SignersCount(ViewChange)
v.lastParticipantsCount = v.ParticipantsCount()
v.reset([]Phase{ViewChange}) v.reset([]Phase{ViewChange})
} }
func (v *uniformVoteWeight) CurrentTotalPower(p Phase) (*numeric.Dec, error) {
if v.lastParticipantsCount == 0 {
return nil, errors.New("uniformVoteWeight not cache last participants count")
}
if lastPowerSignersCount, ok := v.lastPowerSignersCountCache[p]; ok {
power := numeric.NewDec(lastPowerSignersCount).Quo(numeric.NewDec(v.lastParticipantsCount))
return &power, nil
} else {
return nil, errors.New("uniformVoteWeight not cache this phase")
}
}

@ -49,6 +49,7 @@ type stakedVoteWeight struct {
DependencyInjectionReader DependencyInjectionReader
roster votepower.Roster roster votepower.Roster
voteTally VoteTally voteTally VoteTally
lastPower map[Phase]numeric.Dec
} }
// Policy .. // Policy ..
@ -323,12 +324,25 @@ func newVoteTally() VoteTally {
} }
func (v *stakedVoteWeight) ResetPrepareAndCommitVotes() { func (v *stakedVoteWeight) ResetPrepareAndCommitVotes() {
v.lastPower[Prepare] = v.voteTally.Prepare.tally
v.lastPower[Commit] = v.voteTally.Commit.tally
v.reset([]Phase{Prepare, Commit}) v.reset([]Phase{Prepare, Commit})
v.voteTally.Prepare = &tallyAndQuorum{numeric.NewDec(0), false} v.voteTally.Prepare = &tallyAndQuorum{numeric.NewDec(0), false}
v.voteTally.Commit = &tallyAndQuorum{numeric.NewDec(0), false} v.voteTally.Commit = &tallyAndQuorum{numeric.NewDec(0), false}
} }
func (v *stakedVoteWeight) ResetViewChangeVotes() { func (v *stakedVoteWeight) ResetViewChangeVotes() {
v.lastPower[ViewChange] = v.voteTally.ViewChange.tally
v.reset([]Phase{ViewChange}) v.reset([]Phase{ViewChange})
v.voteTally.ViewChange = &tallyAndQuorum{numeric.NewDec(0), false} v.voteTally.ViewChange = &tallyAndQuorum{numeric.NewDec(0), false}
} }
func (v *stakedVoteWeight) CurrentTotalPower(p Phase) (*numeric.Dec, error) {
if power, ok := v.lastPower[p]; ok {
return &power, nil
} else {
return nil, errors.New("stakedVoteWeight not cache this phase")
}
}

@ -132,6 +132,7 @@ type Decider interface {
IsAllSigsCollected() bool IsAllSigsCollected() bool
ResetPrepareAndCommitVotes() ResetPrepareAndCommitVotes()
ResetViewChangeVotes() ResetViewChangeVotes()
CurrentTotalPower(p Phase) (*numeric.Dec, error)
} }
// Registry .. // Registry ..
@ -408,15 +409,19 @@ func NewDecider(p Policy, shardID uint32) Decider {
switch p { switch p {
case SuperMajorityVote: case SuperMajorityVote:
return &uniformVoteWeight{ return &uniformVoteWeight{
c.DependencyInjectionWriter, c.DependencyInjectionReader, c, DependencyInjectionWriter: c.DependencyInjectionWriter,
DependencyInjectionReader: c.DependencyInjectionReader,
SignatureReader: c,
lastPowerSignersCountCache: make(map[Phase]int64),
} }
case SuperMajorityStake: case SuperMajorityStake:
return &stakedVoteWeight{ return &stakedVoteWeight{
c.SignatureReader, SignatureReader: c.SignatureReader,
c.DependencyInjectionWriter, DependencyInjectionWriter: c.DependencyInjectionWriter,
c.DependencyInjectionWriter.(DependencyInjectionReader), DependencyInjectionReader: c.DependencyInjectionWriter.(DependencyInjectionReader),
*votepower.NewRoster(shardID), roster: *votepower.NewRoster(shardID),
newVoteTally(), voteTally: newVoteTally(),
lastPower: make(map[Phase]numeric.Dec),
} }
default: default:
// Should not be possible // Should not be possible

@ -110,6 +110,7 @@ type NodeAPI interface {
GetConsensusCurViewID() uint64 GetConsensusCurViewID() uint64
GetConfig() commonRPC.Config GetConfig() commonRPC.Config
ShutDown() ShutDown()
GetLastSigningPower() (float64, error)
} }
// New creates a new Harmony object (including the // New creates a new Harmony object (including the

@ -2,6 +2,7 @@ package node
import ( import (
"github.com/ethereum/go-ethereum/rpc" "github.com/ethereum/go-ethereum/rpc"
"github.com/harmony-one/harmony/consensus/quorum"
"github.com/harmony-one/harmony/core/types" "github.com/harmony-one/harmony/core/types"
"github.com/harmony-one/harmony/hmy" "github.com/harmony-one/harmony/hmy"
"github.com/harmony-one/harmony/rosetta" "github.com/harmony-one/harmony/rosetta"
@ -166,3 +167,14 @@ func (node *Node) GetConfig() rpc_common.Config {
ChainConfig: node.chainConfig, ChainConfig: node.chainConfig,
} }
} }
// GetLastSigningPower get last signed power
func (node *Node) GetLastSigningPower() (float64, error) {
power, err := node.Consensus.Decider.CurrentTotalPower(quorum.Commit)
if err != nil {
return 0, err
}
round := float64(power.MulInt64(10000).RoundInt64()) / 10000
return round, nil
}

@ -58,3 +58,10 @@ func (s *PrivateDebugService) GetConfig(
) (StructuredResponse, error) { ) (StructuredResponse, error) {
return NewStructuredResponse(s.hmy.NodeAPI.GetConfig()) return NewStructuredResponse(s.hmy.NodeAPI.GetConfig())
} }
// GetLastSigningPower get last signed power
func (s *PrivateDebugService) GetLastSigningPower(
ctx context.Context,
) (float64, error) {
return s.hmy.NodeAPI.GetLastSigningPower()
}

Loading…
Cancel
Save