From 24dcebbac61a31973d992d3395dbc4e0cd8b772b Mon Sep 17 00:00:00 2001 From: Ti Chi Robot Date: Tue, 22 Nov 2022 12:21:58 +0800 Subject: [PATCH] statistics: fix `ToHotPeersStat` result when `HotPeers` is empty (#5597) (#5618) ref tikv/pd#5597, close tikv/pd#5598 Signed-off-by: ti-chi-bot Signed-off-by: lhy1024 Co-authored-by: lhy1024 --- server/statistics/store_load.go | 7 ++- tests/pdctl/hot/hot_test.go | 85 +++++++++++++++++++++++++++++++++ 2 files changed, 90 insertions(+), 2 deletions(-) diff --git a/server/statistics/store_load.go b/server/statistics/store_load.go index e907f725815..b81a0d21d46 100644 --- a/server/statistics/store_load.go +++ b/server/statistics/store_load.go @@ -30,9 +30,14 @@ type StoreLoadDetail struct { // ToHotPeersStat abstracts load information to HotPeersStat. func (li *StoreLoadDetail) ToHotPeersStat() *HotPeersStat { totalLoads := make([]float64, RegionStatCount) + storeByteRate, storeKeyRate, storeQueryRate := li.LoadPred.Current.Loads[ByteDim], + li.LoadPred.Current.Loads[KeyDim], li.LoadPred.Current.Loads[QueryDim] if len(li.HotPeers) == 0 { return &HotPeersStat{ TotalLoads: totalLoads, + StoreByteRate: storeByteRate, + StoreKeyRate: storeKeyRate, + StoreQueryRate: storeQueryRate, TotalBytesRate: 0.0, TotalKeysRate: 0.0, TotalQueryRate: 0.0, @@ -57,8 +62,6 @@ func (li *StoreLoadDetail) ToHotPeersStat() *HotPeersStat { b, k, q := GetRegionStatKind(kind, ByteDim), GetRegionStatKind(kind, KeyDim), GetRegionStatKind(kind, QueryDim) byteRate, keyRate, queryRate := totalLoads[b], totalLoads[k], totalLoads[q] - storeByteRate, storeKeyRate, storeQueryRate := li.LoadPred.Current.Loads[ByteDim], - li.LoadPred.Current.Loads[KeyDim], li.LoadPred.Current.Loads[QueryDim] return &HotPeersStat{ TotalLoads: totalLoads, diff --git a/tests/pdctl/hot/hot_test.go b/tests/pdctl/hot/hot_test.go index de40564c2d9..6254866cd32 100644 --- a/tests/pdctl/hot/hot_test.go +++ b/tests/pdctl/hot/hot_test.go @@ -21,6 +21,7 @@ import ( "testing" "time" + "github.com/docker/go-units" "github.com/gogo/protobuf/proto" . "github.com/pingcap/check" "github.com/pingcap/kvproto/pkg/metapb" @@ -362,3 +363,87 @@ func (s *hotTestSuite) TestHistoryHotRegions(c *C) { c.Assert(e, IsNil) c.Assert(json.Unmarshal(output, &hotRegions), NotNil) } + +func (s *hotTestSuite) TestHotWithoutHotPeer(c *C) { + statistics.Denoising = false + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + cluster, err := tests.NewTestCluster(ctx, 1, func(cfg *config.Config, serverName string) { cfg.Schedule.HotRegionCacheHitsThreshold = 0 }) + c.Assert(err, IsNil) + err = cluster.RunInitialServers() + c.Assert(err, IsNil) + cluster.WaitLeader() + pdAddr := cluster.GetConfig().GetClientURL() + cmd := pdctlCmd.GetRootCmd() + + stores := []*metapb.Store{ + { + Id: 1, + State: metapb.StoreState_Up, + LastHeartbeat: time.Now().UnixNano(), + }, + { + Id: 2, + State: metapb.StoreState_Up, + LastHeartbeat: time.Now().UnixNano(), + }, + } + + leaderServer := cluster.GetServer(cluster.GetLeader()) + err = leaderServer.BootstrapCluster() + c.Assert(err, IsNil) + for _, store := range stores { + pdctl.MustPutStore(c, leaderServer.GetServer(), store) + } + timestamp := uint64(time.Now().UnixNano()) + load := 1024.0 + for _, store := range stores { + for i := 0; i < 5; i++ { + err := leaderServer.GetServer().GetRaftCluster().HandleStoreHeartbeat(&pdpb.StoreStats{ + StoreId: store.Id, + BytesRead: uint64(load * statistics.StoreHeartBeatReportInterval), + KeysRead: uint64(load * statistics.StoreHeartBeatReportInterval), + BytesWritten: uint64(load * statistics.StoreHeartBeatReportInterval), + KeysWritten: uint64(load * statistics.StoreHeartBeatReportInterval), + Capacity: 1000 * units.MiB, + Available: 1000 * units.MiB, + Interval: &pdpb.TimeInterval{ + StartTimestamp: timestamp + uint64(i*statistics.StoreHeartBeatReportInterval), + EndTimestamp: timestamp + uint64((i+1)*statistics.StoreHeartBeatReportInterval)}, + }) + c.Assert(err, IsNil) + } + } + defer cluster.Destroy() + + // wait hot scheduler starts + time.Sleep(5000 * time.Millisecond) + { + args := []string{"-u", pdAddr, "hot", "read"} + output, err := pdctl.ExecuteCommand(cmd, args...) + hotRegion := statistics.StoreHotPeersInfos{} + c.Assert(err, IsNil) + err = json.Unmarshal(output, &hotRegion) + c.Assert(err, IsNil) + c.Assert(hotRegion.AsPeer[1].Count, Equals, 0) + c.Assert(hotRegion.AsPeer[1].TotalBytesRate, Equals, 0.0) + c.Assert(hotRegion.AsPeer[1].StoreByteRate, Equals, load) + c.Assert(hotRegion.AsLeader[1].Count, Equals, 0) + c.Assert(hotRegion.AsLeader[1].TotalBytesRate, Equals, 0.0) + c.Assert(hotRegion.AsLeader[1].StoreByteRate, Equals, load) + } + { + args := []string{"-u", pdAddr, "hot", "write"} + output, err := pdctl.ExecuteCommand(cmd, args...) + hotRegion := statistics.StoreHotPeersInfos{} + c.Assert(err, IsNil) + err = json.Unmarshal(output, &hotRegion) + c.Assert(err, IsNil) + c.Assert(hotRegion.AsPeer[1].Count, Equals, 0) + c.Assert(hotRegion.AsPeer[1].TotalBytesRate, Equals, 0.0) + c.Assert(hotRegion.AsPeer[1].StoreByteRate, Equals, load) + c.Assert(hotRegion.AsLeader[1].Count, Equals, 0) + c.Assert(hotRegion.AsLeader[1].TotalBytesRate, Equals, 0.0) + c.Assert(hotRegion.AsLeader[1].StoreByteRate, Equals, 0.0) // write leader sum + } +}