Skip to content

Commit

Permalink
Feature/update metrics gathering (#1084)
Browse files Browse the repository at this point in the history
# Related Github tickets

- VolumeFi#421

# Background

Some of our metrics were calculated incorrectly. This fix should address
the issue.

# Testing completed

- [x] test coverage exists or has been added/updated
- [ ] tested in a private testnet

# Breaking changes

- [x] I have checked my code for breaking changes
- [x] If there are breaking changes, there is a supporting migration.
  • Loading branch information
byte-bandit committed Feb 8, 2024
1 parent 65a0320 commit dd5d9a3
Show file tree
Hide file tree
Showing 3 changed files with 91 additions and 47 deletions.
39 changes: 24 additions & 15 deletions x/metrix/keeper/keeper.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import (
sdk "github.com/cosmos/cosmos-sdk/types"
paramtypes "github.com/cosmos/cosmos-sdk/x/params/types"
slashingtypes "github.com/cosmos/cosmos-sdk/x/slashing/types"
stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types"
keeperutil "github.com/palomachain/paloma/util/keeper"
"github.com/palomachain/paloma/util/liblog"
"github.com/palomachain/paloma/util/palomath"
Expand Down Expand Up @@ -178,14 +179,13 @@ func (k Keeper) OnSnapshotBuilt(ctx sdk.Context, snapshot *valsettypes.Snapshot)
logger.Debug("Updating snapshot metrics...")

// Building the feature set is currently only taking MEV support into consideration.
max := int64(len(snapshot.Chains))
if max < 1 {
logger.Info("Skip updating metrics, no chains found.")
return
}

for _, v := range snapshot.Validators {
logger := logger.WithValidator(v.GetAddress().String())
scoreMax := int64(len(v.ExternalChainInfos))
if scoreMax < 1 {
logger.Info("Skip updating metrics, no chains found.")
return
}

matches := func() int64 {
if v.State != valsettypes.ValidatorState_ACTIVE {
Expand All @@ -200,15 +200,10 @@ func (k Keeper) OnSnapshotBuilt(ctx sdk.Context, snapshot *valsettypes.Snapshot)
}
}

if matches > max {
logger.WithFields("max-matches", max, "found-matches", matches).Error("Found too many matches.")
return 0
}

return matches
}()

score := palomath.BigIntDiv(big.NewInt(matches), big.NewInt(max))
score := palomath.BigIntDiv(big.NewInt(matches), big.NewInt(scoreMax))
k.updateRecord(ctx, v.GetAddress(), recordPatch{featureSet: &score})
}
}
Expand Down Expand Up @@ -339,6 +334,14 @@ func (k *Keeper) UpdateUptime(ctx sdk.Context) {
logger := liblog.FromSDKLogger(k.Logger(ctx)).WithComponent("metrix.UpdateUptime").WithFields("signed-blocks-window", window)
logger.Debug("Running uptime update loop.")

jailed := make(map[string]struct{})
k.staking.IterateValidators(ctx, func(_ int64, val stakingtypes.ValidatorI) bool {
if val.IsJailed() {
jailed[val.GetOperator().String()] = struct{}{}
}
return false
})

k.slashing.IterateValidatorSigningInfos(ctx, func(consAddr sdk.ConsAddress, info slashingtypes.ValidatorSigningInfo) (stop bool) {
logger := logger.WithFields("validator-conspub", info.GetAddress())
val, found := k.staking.GetValidatorByConsAddr(ctx, consAddr)
Expand All @@ -348,11 +351,17 @@ func (k *Keeper) UpdateUptime(ctx sdk.Context) {
return false
}

uptime := calculateUptime(window, info.MissedBlocksCounter)
logger.WithValidator(val.GetOperator().String()).
valAddr := val.GetOperator().String()
uptime := math.LegacyNewDec(0)
_, isJailed := jailed[valAddr]
if !isJailed {
uptime = calculateUptime(window, info.MissedBlocksCounter)
}
logger.WithValidator(valAddr).
WithFields(
"missed-blocks-counter", info.MissedBlocksCounter,
"uptime", uptime).
"uptime", uptime,
"is-jailed", isJailed).
Debug("Calculated uptime, updating record.")
k.updateRecord(ctx, val.GetOperator(), recordPatch{uptime: &uptime})
return false
Expand Down
98 changes: 66 additions & 32 deletions x/metrix/keeper/keeper_integration_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (
tmproto "github.com/cometbft/cometbft/proto/tendermint/types"
sdk "github.com/cosmos/cosmos-sdk/types"
slashingtypes "github.com/cosmos/cosmos-sdk/x/slashing/types"
stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types"
. "github.com/onsi/ginkgo/v2"
. "github.com/onsi/gomega"
"github.com/palomachain/paloma/app"
Expand All @@ -25,44 +26,62 @@ func TestGenesisGinkgo(t *testing.T) {
var _ = Describe("updating uptime", func() {
var a app.TestApp
var ctx sdk.Context
var validators []stakingtypes.Validator
var cons []sdk.ConsAddress
var uptimes []math.LegacyDec

BeforeEach(func() {
a = app.NewTestApp(GinkgoT(), false)
ctx = a.NewContext(false, tmproto.Header{
Height: 5,
})
validators := testutil.GenValidators(3, 1000)
for _, v := range validators {
r, err := a.MetrixKeeper.GetValidatorMetrics(ctx, v.GetOperator())
Expect(r).To(BeNil())
Expect(err).To(BeNil())

a.StakingKeeper.SetValidator(ctx, v)
a.StakingKeeper.SetValidatorByConsAddr(ctx, v)
}

cons = make([]sdk.ConsAddress, len(validators))
for i, v := range validators {
var err error
cons[i], err = v.GetConsAddr()
Expect(err).To(BeNil())
}

a.SlashingKeeper.SetValidatorSigningInfo(ctx, cons[0], slashingtypes.NewValidatorSigningInfo(cons[0], 0, 0, time.Time{}, false, 1))
a.SlashingKeeper.SetValidatorSigningInfo(ctx, cons[1], slashingtypes.NewValidatorSigningInfo(cons[1], 0, 0, time.Time{}, false, 10))
a.SlashingKeeper.SetValidatorSigningInfo(ctx, cons[2], slashingtypes.NewValidatorSigningInfo(cons[2], 0, 0, time.Time{}, false, 42))

uptimes = []math.LegacyDec{
math.LegacyMustNewDecFromStr("0.99"),
math.LegacyMustNewDecFromStr("0.9"),
math.LegacyMustNewDecFromStr("0.58"),
}
a.MetrixKeeper.UpdateUptime(ctx)
})

Context("with nonexisting validator", func() {
It("creates new validator metrics", func() {
validators := testutil.GenValidators(3, 1000)
for _, v := range validators {
r, err := a.MetrixKeeper.GetValidatorMetrics(ctx, v.GetOperator())
Expect(r).To(BeNil())
Expect(err).To(BeNil())

a.StakingKeeper.SetValidator(ctx, v)
a.StakingKeeper.SetValidatorByConsAddr(ctx, v)
}

cons := make([]sdk.ConsAddress, len(validators))
for i, v := range validators {
var err error
cons[i], err = v.GetConsAddr()
r, err := a.MetrixKeeper.GetValidatorMetrics(ctx, v.GetOperator())
Expect(r).To(Not(BeNil()))
Expect(err).To(BeNil())
Expect(r.Uptime).To(Equal(uptimes[i]))
}
})
})

a.SlashingKeeper.SetValidatorSigningInfo(ctx, cons[0], slashingtypes.NewValidatorSigningInfo(cons[0], 0, 0, time.Time{}, false, 1))
a.SlashingKeeper.SetValidatorSigningInfo(ctx, cons[1], slashingtypes.NewValidatorSigningInfo(cons[1], 0, 0, time.Time{}, false, 10))
a.SlashingKeeper.SetValidatorSigningInfo(ctx, cons[2], slashingtypes.NewValidatorSigningInfo(cons[2], 0, 0, time.Time{}, false, 42))

a.MetrixKeeper.UpdateUptime(ctx)
Context("with jailed validator", func() {
BeforeEach(func() {
a.StakingKeeper.Jail(ctx, cons[2])
uptimes[2] = math.LegacyNewDec(0)
})

uptimes := []math.LegacyDec{
math.LegacyMustNewDecFromStr("0.99"),
math.LegacyMustNewDecFromStr("0.9"),
math.LegacyMustNewDecFromStr("0.58"),
}
It("sets uptime to 0", func() {
for i, v := range validators {
r, err := a.MetrixKeeper.GetValidatorMetrics(ctx, v.GetOperator())
Expect(r).To(Not(BeNil()))
Expand Down Expand Up @@ -91,13 +110,16 @@ var _ = Describe("updating feature set", func() {
State: valsettypes.ValidatorState_ACTIVE,
ExternalChainInfos: []*valsettypes.ExternalChainInfo{
{
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
ChainReferenceID: "1",
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
},
{
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
ChainReferenceID: "2",
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
},
{
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
ChainReferenceID: "3",
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
},
},
Address: validators[0].GetOperator(),
Expand All @@ -106,10 +128,15 @@ var _ = Describe("updating feature set", func() {
State: valsettypes.ValidatorState_ACTIVE,
ExternalChainInfos: []*valsettypes.ExternalChainInfo{
{
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
ChainReferenceID: "1",
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
},
{
ChainReferenceID: "2",
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
},
{
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
ChainReferenceID: "3",
},
},
Address: validators[1].GetOperator(),
Expand All @@ -118,13 +145,19 @@ var _ = Describe("updating feature set", func() {
State: valsettypes.ValidatorState_ACTIVE,
ExternalChainInfos: []*valsettypes.ExternalChainInfo{
{
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
ChainReferenceID: "1",
Traits: []string{valsettypes.PIGEON_TRAIT_MEV},
},
{
ChainReferenceID: "2",
},
{
ChainReferenceID: "3",
},
},
Address: validators[2].GetOperator(),
},
},
Chains: []string{"chain-1", "chain-2", "chain-3"},
}
})

Expand Down Expand Up @@ -188,8 +221,9 @@ var _ = Describe("updating feature set", func() {

a.MetrixKeeper.OnSnapshotBuilt(ctx, snapshot)
snapshot.Validators[0].ExternalChainInfos[0].Traits = []string{}
snapshot.Validators[1].ExternalChainInfos = snapshot.Validators[1].ExternalChainInfos[:1]
snapshot.Validators[2].ExternalChainInfos = append(snapshot.Validators[2].ExternalChainInfos, &valsettypes.ExternalChainInfo{Traits: []string{valsettypes.PIGEON_TRAIT_MEV}})
snapshot.Validators[1].ExternalChainInfos[1].Traits = []string{}
snapshot.Validators[2].ExternalChainInfos[0].Traits = []string{valsettypes.PIGEON_TRAIT_MEV}
snapshot.Validators[2].ExternalChainInfos[1].Traits = []string{valsettypes.PIGEON_TRAIT_MEV}
a.MetrixKeeper.OnSnapshotBuilt(ctx, snapshot)

featureSets := []math.LegacyDec{
Expand Down
1 change: 1 addition & 0 deletions x/metrix/types/expected_keepers.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,4 +16,5 @@ type SlashingKeeper interface {
type StakingKeeper interface {
GetValidator(sdk.Context, sdk.ValAddress) (stakingtypes.Validator, bool)
GetValidatorByConsAddr(sdk.Context, sdk.ConsAddress) (stakingtypes.Validator, bool)
IterateValidators(sdk.Context, func(int64, stakingtypes.ValidatorI) bool)
}

0 comments on commit dd5d9a3

Please sign in to comment.