From 9aa10a7cd46de667e85b4ba18eaebf9c3e6f33e1 Mon Sep 17 00:00:00 2001 From: Song Gao Date: Wed, 21 Oct 2020 16:37:26 +0800 Subject: [PATCH 1/2] cherry pick #3082 to release-4.0 Signed-off-by: ti-srebot --- server/api/config.go | 20 ++++++ server/api/config_test.go | 26 +++++++ server/api/store.go | 64 +++++++++++++++++- server/api/store_test.go | 51 ++++++++++++++ server/cluster/cluster.go | 18 +++++ server/config/persist_options.go | 112 ++++++++++++++++++++++++++++++- server/handler.go | 38 +++++++++++ server/server.go | 7 ++ 8 files changed, 333 insertions(+), 3 deletions(-) diff --git a/server/api/config.go b/server/api/config.go index 9d31466de4b..1b752d87e7a 100644 --- a/server/api/config.go +++ b/server/api/config.go @@ -20,7 +20,9 @@ import ( "io/ioutil" "net/http" "reflect" + "strconv" "strings" + "time" "github.com/pingcap/errcode" "github.com/pingcap/errors" @@ -73,6 +75,7 @@ func (h *confHandler) GetDefault(w http.ResponseWriter, r *http.Request) { // @Tags config // @Summary Update a config item. // @Accept json +// @Param ttlSecond query integer false "ttl". ttl param is only for BR and lightning now. Don't use it. // @Param body body object false "json params" // @Produce json // @Success 200 {string} string "The config is updated." @@ -94,6 +97,23 @@ func (h *confHandler) Post(w http.ResponseWriter, r *http.Request) { return } + var ttls int + if ttlSec := r.URL.Query().Get("ttlSecond"); ttlSec != "" { + var err error + ttls, err = strconv.Atoi(ttlSec) + if err != nil { + h.rd.JSON(w, http.StatusBadRequest, err.Error()) + return + } + } + + // if ttlSecond defined, we will apply if to temp configuration. + if ttls > 0 { + h.svr.SaveTTLConfig(conf, time.Duration(ttls)*time.Second) + h.rd.JSON(w, http.StatusOK, "The config is updated.") + return + } + for k, v := range conf { if s := strings.Split(k, "."); len(s) > 1 { if err := h.updateConfig(cfg, k, v); err != nil { diff --git a/server/api/config_test.go b/server/api/config_test.go index d3a3fdd8bfd..162dc7f0130 100644 --- a/server/api/config_test.go +++ b/server/api/config_test.go @@ -269,3 +269,29 @@ func (s *testConfigSuite) TestConfigDefault(c *C) { c.Assert(defaultCfg.Schedule.RegionScheduleLimit, Equals, uint64(2048)) c.Assert(defaultCfg.PDServerCfg.MetricStorage, Equals, "") } + +func (s *testConfigSuite) TestConfigTTL(c *C) { + addr := fmt.Sprintf("%s/config?ttlSecond=3", s.urlPrefix) + r := map[string]interface{}{ + "schedule.max-snapshot-count": 999, + "schedule.enable-location-replacement": false, + "schedule.max-merge-region-size": 999, + "schedule.max-merge-region-keys": 999, + "schedule.scheduler-max-waiting-operator": 999, + } + postData, err := json.Marshal(r) + c.Assert(err, IsNil) + err = postJSON(testDialClient, addr, postData) + c.Assert(err, IsNil) + c.Assert(s.svr.GetPersistOptions().GetMaxSnapshotCount(), Equals, uint64(999)) + c.Assert(s.svr.GetPersistOptions().IsLocationReplacementEnabled(), Equals, false) + c.Assert(s.svr.GetPersistOptions().GetMaxMergeRegionSize(), Equals, uint64(999)) + c.Assert(s.svr.GetPersistOptions().GetMaxMergeRegionKeys(), Equals, uint64(999)) + c.Assert(s.svr.GetPersistOptions().GetSchedulerMaxWaitingOperator(), Equals, uint64(999)) + time.Sleep(5 * time.Second) + c.Assert(s.svr.GetPersistOptions().GetMaxSnapshotCount(), Not(Equals), uint64(999)) + c.Assert(s.svr.GetPersistOptions().IsLocationReplacementEnabled(), Equals, true) + c.Assert(s.svr.GetPersistOptions().GetMaxMergeRegionSize(), Not(Equals), uint64(999)) + c.Assert(s.svr.GetPersistOptions().GetMaxMergeRegionKeys(), Not(Equals), uint64(999)) + c.Assert(s.svr.GetPersistOptions().GetSchedulerMaxWaitingOperator(), Not(Equals), uint64(999)) +} diff --git a/server/api/store.go b/server/api/store.go index 235b9bd9aed..698c235ee2c 100644 --- a/server/api/store.go +++ b/server/api/store.go @@ -14,6 +14,7 @@ package api import ( + "fmt" "net/http" "net/url" "strconv" @@ -341,6 +342,7 @@ func (h *storeHandler) SetWeight(w http.ResponseWriter, r *http.Request) { // FIXME: details of input json body params // @Tags store // @Summary Set the store's limit. +// @Param ttlSecond query integer false "ttl". ttl param is only for BR and lightning now. Don't use it. // @Param id path integer true "Store Id" // @Param body body object true "json params" // @Produce json @@ -384,15 +386,35 @@ func (h *storeHandler) SetLimit(w http.ResponseWriter, r *http.Request) { h.rd.JSON(w, http.StatusBadRequest, err.Error()) return } - + var ttl int + if ttlSec := r.URL.Query().Get("ttlSecond"); ttlSec != "" { + var err error + ttl, err = strconv.Atoi(ttlSec) + if err != nil { + h.rd.JSON(w, http.StatusBadRequest, err.Error()) + return + } + } for _, typ := range typeValues { + if ttl > 0 { + key := fmt.Sprintf("add-peer-%v", storeID) + if typ == storelimit.RemovePeer { + key = fmt.Sprintf("remove-peer-%v", storeID) + } + h.Handler.SetStoreLimitTTL(key, ratePerMin, time.Duration(ttl)*time.Second) + continue + } if err := h.SetStoreLimit(storeID, ratePerMin, typ); err != nil { h.rd.JSON(w, http.StatusInternalServerError, err.Error()) return } } +<<<<<<< HEAD h.rd.JSON(w, http.StatusOK, nil) +======= + h.rd.JSON(w, http.StatusOK, "The store's label is updated.") +>>>>>>> 47e83f78... api: support temporary configuration (#3082) } type storesHandler struct { @@ -428,6 +450,7 @@ func (h *storesHandler) RemoveTombStone(w http.ResponseWriter, r *http.Request) // @Tags store // @Summary Set limit of all stores in the cluster. // @Accept json +// @Param ttlSecond query integer false "ttl". ttl param is only for BR and lightning now. Don't use it. // @Param body body object true "json params" // @Produce json // @Success 200 {string} string "Set store limit success." @@ -457,9 +480,48 @@ func (h *storesHandler) SetAllLimit(w http.ResponseWriter, r *http.Request) { return } +<<<<<<< HEAD for _, typ := range typeValues { if err := h.SetAllStoresLimit(ratePerMin, typ); err != nil { h.rd.JSON(w, http.StatusInternalServerError, err.Error()) +======= + var ttl int + if ttlSec := r.URL.Query().Get("ttlSecond"); ttlSec != "" { + var err error + ttl, err = strconv.Atoi(ttlSec) + if err != nil { + h.rd.JSON(w, http.StatusBadRequest, err.Error()) + return + } + } + + if _, ok := input["labels"]; !ok { + for _, typ := range typeValues { + if ttl > 0 { + if err := h.SetAllStoresLimitTTL(ratePerMin, typ, time.Duration(ttl)*time.Second); err != nil { + h.rd.JSON(w, http.StatusInternalServerError, err.Error()) + return + } + } else { + if err := h.SetAllStoresLimit(ratePerMin, typ); err != nil { + h.rd.JSON(w, http.StatusInternalServerError, err.Error()) + return + } + } + } + } else { + labelMap := input["labels"].(map[string]interface{}) + labels := make([]*metapb.StoreLabel, 0, len(input)) + for k, v := range labelMap { + labels = append(labels, &metapb.StoreLabel{ + Key: k, + Value: v.(string), + }) + } + + if err := config.ValidateLabels(labels); err != nil { + apiutil.ErrorResp(h.rd, w, errcode.NewInvalidInputErr(err)) +>>>>>>> 47e83f78... api: support temporary configuration (#3082) return } } diff --git a/server/api/store_test.go b/server/api/store_test.go index 8932c8c7696..3a19ecbfbbc 100644 --- a/server/api/store_test.go +++ b/server/api/store_test.go @@ -395,3 +395,54 @@ func (s *testStoreSuite) TestGetAllLimit(c *C) { } } } + +func (s *testStoreSuite) TestStoreLimitTTL(c *C) { + // add peer + url := fmt.Sprintf("%s/store/1/limit?ttlSecond=%v", s.urlPrefix, 5) + data := map[string]interface{}{ + "type": "add-peer", + "rate": 999, + } + postData, err := json.Marshal(data) + c.Assert(err, IsNil) + err = postJSON(testDialClient, url, postData) + c.Assert(err, IsNil) + // remove peer + data = map[string]interface{}{ + "type": "remove-peer", + "rate": 998, + } + postData, err = json.Marshal(data) + c.Assert(err, IsNil) + err = postJSON(testDialClient, url, postData) + c.Assert(err, IsNil) + // all store limit add peer + url = fmt.Sprintf("%s/stores/limit?ttlSecond=%v", s.urlPrefix, 3) + data = map[string]interface{}{ + "type": "add-peer", + "rate": 997, + } + postData, err = json.Marshal(data) + c.Assert(err, IsNil) + err = postJSON(testDialClient, url, postData) + c.Assert(err, IsNil) + // all store limit remove peer + data = map[string]interface{}{ + "type": "remove-peer", + "rate": 996, + } + postData, err = json.Marshal(data) + c.Assert(err, IsNil) + err = postJSON(testDialClient, url, postData) + c.Assert(err, IsNil) + + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(1)).AddPeer, Equals, float64(999)) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(1)).RemovePeer, Equals, float64(998)) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(2)).AddPeer, Equals, float64(997)) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(2)).RemovePeer, Equals, float64(996)) + time.Sleep(5 * time.Second) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(1)).AddPeer, Not(Equals), float64(999)) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(1)).RemovePeer, Not(Equals), float64(998)) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(2)).AddPeer, Not(Equals), float64(997)) + c.Assert(s.svr.GetPersistOptions().GetStoreLimit(uint64(2)).RemovePeer, Not(Equals), float64(996)) +} diff --git a/server/cluster/cluster.go b/server/cluster/cluster.go index 879e661244d..bb1b3c032bf 100644 --- a/server/cluster/cluster.go +++ b/server/cluster/cluster.go @@ -1767,6 +1767,24 @@ func (c *RaftCluster) SetAllStoresLimit(typ storelimit.Type, ratePerMin float64) c.opt.SetAllStoresLimit(typ, ratePerMin) } +<<<<<<< HEAD +======= +// SetAllStoresLimitTTL sets all store limit for a given type and rate with ttl. +func (c *RaftCluster) SetAllStoresLimitTTL(typ storelimit.Type, ratePerMin float64, ttl time.Duration) { + c.opt.SetAllStoresLimitTTL(c.ctx, typ, ratePerMin, ttl) +} + +// GetClusterVersion returns the current cluster version. +func (c *RaftCluster) GetClusterVersion() string { + return c.opt.GetClusterVersion().String() +} + +// GetEtcdClient returns the current etcd client +func (c *RaftCluster) GetEtcdClient() *clientv3.Client { + return c.etcdClient +} + +>>>>>>> 47e83f78... api: support temporary configuration (#3082) var healthURL = "/pd/api/v1/ping" // CheckHealth checks if members are healthy. diff --git a/server/config/persist_options.go b/server/config/persist_options.go index 8ac8b11cbe6..6d46307ec9f 100644 --- a/server/config/persist_options.go +++ b/server/config/persist_options.go @@ -15,6 +15,10 @@ package config import ( "context" +<<<<<<< HEAD +======= + "fmt" +>>>>>>> 47e83f78... api: support temporary configuration (#3082) "reflect" "sync/atomic" "time" @@ -22,6 +26,7 @@ import ( "github.com/coreos/go-semver/semver" "github.com/pingcap/kvproto/pkg/metapb" + "github.com/tikv/pd/pkg/cache" "github.com/tikv/pd/pkg/slice" "github.com/tikv/pd/pkg/typeutil" "github.com/tikv/pd/server/core" @@ -33,6 +38,8 @@ import ( // PersistOptions wraps all configurations that need to persist to storage and // allows to access them safely. type PersistOptions struct { + // configuration -> ttl value + ttl map[string]*cache.TTLString schedule atomic.Value replication atomic.Value pdServerConfig atomic.Value @@ -50,6 +57,7 @@ func NewPersistOptions(cfg *Config) *PersistOptions { o.replicationMode.Store(&cfg.ReplicationMode) o.labelProperty.Store(cfg.LabelProperty) o.SetClusterVersion(&cfg.ClusterVersion) + o.ttl = make(map[string]*cache.TTLString, 6) return o } @@ -154,6 +162,12 @@ func (o *PersistOptions) SetMaxReplicas(replicas int) { // GetMaxSnapshotCount returns the number of the max snapshot which is allowed to send. func (o *PersistOptions) GetMaxSnapshotCount() uint64 { + if v, ok := o.getTTLData("schedule.max-snapshot-count"); ok { + r, ok := v.(float64) + if ok { + return uint64(r) + } + } return o.GetScheduleConfig().MaxSnapshotCount } @@ -164,11 +178,23 @@ func (o *PersistOptions) GetMaxPendingPeerCount() uint64 { // GetMaxMergeRegionSize returns the max region size. func (o *PersistOptions) GetMaxMergeRegionSize() uint64 { + if v, ok := o.getTTLData("schedule.max-merge-region-size"); ok { + r, ok := v.(float64) + if ok { + return uint64(r) + } + } return o.GetScheduleConfig().MaxMergeRegionSize } // GetMaxMergeRegionKeys returns the max number of keys. func (o *PersistOptions) GetMaxMergeRegionKeys() uint64 { + if v, ok := o.getTTLData("schedule.max-merge-region-keys"); ok { + r, ok := v.(float64) + if ok { + return uint64(r) + } + } return o.GetScheduleConfig().MaxMergeRegionKeys } @@ -276,22 +302,66 @@ func (o *PersistOptions) GetHotRegionScheduleLimit() uint64 { } // GetStoreLimit returns the limit of a store. -func (o *PersistOptions) GetStoreLimit(storeID uint64) StoreLimitConfig { +func (o *PersistOptions) GetStoreLimit(storeID uint64) (returnSC StoreLimitConfig) { + defer func() { + if v, ok := o.getTTLData(fmt.Sprintf("remove-peer-%v", storeID)); ok { + r, ok := v.(float64) + if ok { + returnSC.RemovePeer = r + } + } + if v, ok := o.getTTLData(fmt.Sprintf("add-peer-%v", storeID)); ok { + r, ok := v.(float64) + if ok { + returnSC.AddPeer = r + } + } + }() if limit, ok := o.GetScheduleConfig().StoreLimit[storeID]; ok { return limit } + v1, ok1 := o.getTTLData("default-add-peer") + v2, ok2 := o.getTTLData("default-remove-peer") cfg := o.GetScheduleConfig().Clone() sc := StoreLimitConfig{ AddPeer: DefaultStoreLimit.GetDefaultStoreLimit(storelimit.AddPeer), RemovePeer: DefaultStoreLimit.GetDefaultStoreLimit(storelimit.RemovePeer), } + if ok1 || ok2 { + r, ok := v1.(float64) + if ok { + returnSC.AddPeer = r + } + r, ok = v2.(float64) + if ok { + returnSC.RemovePeer = r + } + return returnSC + } cfg.StoreLimit[storeID] = sc o.SetScheduleConfig(cfg) return o.GetScheduleConfig().StoreLimit[storeID] } // GetStoreLimitByType returns the limit of a store with a given type. -func (o *PersistOptions) GetStoreLimitByType(storeID uint64, typ storelimit.Type) float64 { +func (o *PersistOptions) GetStoreLimitByType(storeID uint64, typ storelimit.Type) (returned float64) { + defer func() { + if typ == storelimit.RemovePeer { + if v, ok := o.getTTLData(fmt.Sprintf("remove-peer-%v", storeID)); ok { + r, ok := v.(float64) + if ok { + returned = r + } + } + } else if typ == storelimit.AddPeer { + if v, ok := o.getTTLData(fmt.Sprintf("add-peer-%v", storeID)); ok { + r, ok := v.(float64) + if ok { + returned = r + } + } + } + }() limit := o.GetStoreLimit(storeID) switch typ { case storelimit.AddPeer: @@ -330,6 +400,12 @@ func (o *PersistOptions) GetHighSpaceRatio() float64 { // GetSchedulerMaxWaitingOperator returns the number of the max waiting operators. func (o *PersistOptions) GetSchedulerMaxWaitingOperator() uint64 { + if v, ok := o.getTTLData("schedule.scheduler-max-waiting-operator"); ok { + r, ok := v.(float64) + if ok { + return uint64(r) + } + } return o.GetScheduleConfig().SchedulerMaxWaitingOperator } @@ -380,6 +456,12 @@ func (o *PersistOptions) IsRemoveExtraReplicaEnabled() bool { // IsLocationReplacementEnabled returns if location replace is enabled. func (o *PersistOptions) IsLocationReplacementEnabled() bool { + if v, ok := o.getTTLData("schedule.enable-location-replacement"); ok { + r, ok := v.(bool) + if ok { + return r + } + } return o.GetScheduleConfig().EnableLocationReplacement } @@ -532,3 +614,29 @@ func (o *PersistOptions) CheckLabelProperty(typ string, labels []*metapb.StoreLa } return false } + +// SetTTLData set temporary configuration +func (o *PersistOptions) SetTTLData(ctx context.Context, key string, value interface{}, ttl time.Duration) { + if data, ok := o.ttl[key]; ok { + data.Clear() + } + o.ttl[key] = cache.NewStringTTL(ctx, 5*time.Second, ttl) + o.ttl[key].Put(key, value) +} + +func (o *PersistOptions) getTTLData(key string) (interface{}, bool) { + if data, ok := o.ttl[key]; ok { + return data.Get(key) + } + return nil, false +} + +// SetAllStoresLimitTTL sets all store limit for a given type and rate with ttl. +func (o *PersistOptions) SetAllStoresLimitTTL(ctx context.Context, typ storelimit.Type, ratePerMin float64, ttl time.Duration) { + switch typ { + case storelimit.AddPeer: + o.SetTTLData(ctx, "default-add-peer", ratePerMin, ttl) + case storelimit.RemovePeer: + o.SetTTLData(ctx, "default-remove-peer", ratePerMin, ttl) + } +} diff --git a/server/handler.go b/server/handler.go index 8aa01fdffea..fe99067096e 100644 --- a/server/handler.go +++ b/server/handler.go @@ -419,6 +419,37 @@ func (h *Handler) SetAllStoresLimit(ratePerMin float64, limitType storelimit.Typ return nil } +<<<<<<< HEAD +======= +// SetAllStoresLimitTTL is used to set limit of all stores with ttl +func (h *Handler) SetAllStoresLimitTTL(ratePerMin float64, limitType storelimit.Type, ttl time.Duration) error { + c, err := h.GetRaftCluster() + if err != nil { + return err + } + c.SetAllStoresLimitTTL(limitType, ratePerMin, ttl) + return nil +} + +// SetLabelStoresLimit is used to set limit of label stores. +func (h *Handler) SetLabelStoresLimit(ratePerMin float64, limitType storelimit.Type, labels []*metapb.StoreLabel) error { + c, err := h.GetRaftCluster() + if err != nil { + return err + } + for _, store := range c.GetStores() { + for _, label := range labels { + for _, sl := range store.GetLabels() { + if label.Key == sl.Key && label.Value == sl.Value { + c.SetStoreLimit(store.GetID(), limitType, ratePerMin) + } + } + } + } + return nil +} + +>>>>>>> 47e83f78... api: support temporary configuration (#3082) // GetAllStoresLimit is used to get limit of all stores. func (h *Handler) GetAllStoresLimit(limitType storelimit.Type) (map[uint64]config.StoreLimitConfig, error) { c, err := h.GetRaftCluster() @@ -874,3 +905,10 @@ func (h *Handler) PluginUnload(pluginPath string) error { func (h *Handler) GetAddr() string { return h.s.GetAddr() } + +// SetStoreLimitTTL set storeLimit with ttl +func (h *Handler) SetStoreLimitTTL(data string, value float64, ttl time.Duration) { + h.s.SaveTTLConfig(map[string]interface{}{ + data: value, + }, ttl) +} diff --git a/server/server.go b/server/server.go index becc6ee2930..be7f0e08e1e 100644 --- a/server/server.go +++ b/server/server.go @@ -1251,3 +1251,10 @@ func (s *Server) ReplicateFileToAllMembers(ctx context.Context, name string, dat func (s *Server) PersistFile(name string, data []byte) error { return ioutil.WriteFile(filepath.Join(s.GetConfig().DataDir, name), data, 0644) } + +// SaveTTLConfig save ttl config +func (s *Server) SaveTTLConfig(data map[string]interface{}, ttl time.Duration) { + for k, v := range data { + s.persistOptions.SetTTLData(s.ctx, k, v, ttl) + } +} From 5da84843cbe8cc5dd8b92c44f06c8f92a87ab32d Mon Sep 17 00:00:00 2001 From: Song Gao Date: Wed, 21 Oct 2020 20:41:14 +0800 Subject: [PATCH 2/2] fix conflict Signed-off-by: Song Gao --- pkg/cache/ttl.go | 5 +++++ server/api/store.go | 11 ----------- server/cluster/cluster.go | 3 --- server/config/persist_options.go | 3 --- server/handler.go | 3 --- 5 files changed, 5 insertions(+), 20 deletions(-) diff --git a/pkg/cache/ttl.go b/pkg/cache/ttl.go index af6d789e041..cd589abcb94 100644 --- a/pkg/cache/ttl.go +++ b/pkg/cache/ttl.go @@ -246,3 +246,8 @@ func (c *TTLString) Pop() (string, interface{}, bool) { } return key, v, true } + +// Get return the value by key id +func (c *TTLString) Get(id string) (interface{}, bool) { + return c.ttlCache.get(id) +} diff --git a/server/api/store.go b/server/api/store.go index 698c235ee2c..50f30e25b01 100644 --- a/server/api/store.go +++ b/server/api/store.go @@ -409,12 +409,7 @@ func (h *storeHandler) SetLimit(w http.ResponseWriter, r *http.Request) { return } } -<<<<<<< HEAD - h.rd.JSON(w, http.StatusOK, nil) -======= - h.rd.JSON(w, http.StatusOK, "The store's label is updated.") ->>>>>>> 47e83f78... api: support temporary configuration (#3082) } type storesHandler struct { @@ -480,11 +475,6 @@ func (h *storesHandler) SetAllLimit(w http.ResponseWriter, r *http.Request) { return } -<<<<<<< HEAD - for _, typ := range typeValues { - if err := h.SetAllStoresLimit(ratePerMin, typ); err != nil { - h.rd.JSON(w, http.StatusInternalServerError, err.Error()) -======= var ttl int if ttlSec := r.URL.Query().Get("ttlSecond"); ttlSec != "" { var err error @@ -521,7 +511,6 @@ func (h *storesHandler) SetAllLimit(w http.ResponseWriter, r *http.Request) { if err := config.ValidateLabels(labels); err != nil { apiutil.ErrorResp(h.rd, w, errcode.NewInvalidInputErr(err)) ->>>>>>> 47e83f78... api: support temporary configuration (#3082) return } } diff --git a/server/cluster/cluster.go b/server/cluster/cluster.go index bb1b3c032bf..1724bfeb10c 100644 --- a/server/cluster/cluster.go +++ b/server/cluster/cluster.go @@ -1767,8 +1767,6 @@ func (c *RaftCluster) SetAllStoresLimit(typ storelimit.Type, ratePerMin float64) c.opt.SetAllStoresLimit(typ, ratePerMin) } -<<<<<<< HEAD -======= // SetAllStoresLimitTTL sets all store limit for a given type and rate with ttl. func (c *RaftCluster) SetAllStoresLimitTTL(typ storelimit.Type, ratePerMin float64, ttl time.Duration) { c.opt.SetAllStoresLimitTTL(c.ctx, typ, ratePerMin, ttl) @@ -1784,7 +1782,6 @@ func (c *RaftCluster) GetEtcdClient() *clientv3.Client { return c.etcdClient } ->>>>>>> 47e83f78... api: support temporary configuration (#3082) var healthURL = "/pd/api/v1/ping" // CheckHealth checks if members are healthy. diff --git a/server/config/persist_options.go b/server/config/persist_options.go index 6d46307ec9f..9998a7499ce 100644 --- a/server/config/persist_options.go +++ b/server/config/persist_options.go @@ -15,10 +15,7 @@ package config import ( "context" -<<<<<<< HEAD -======= "fmt" ->>>>>>> 47e83f78... api: support temporary configuration (#3082) "reflect" "sync/atomic" "time" diff --git a/server/handler.go b/server/handler.go index fe99067096e..ed17f2deae8 100644 --- a/server/handler.go +++ b/server/handler.go @@ -419,8 +419,6 @@ func (h *Handler) SetAllStoresLimit(ratePerMin float64, limitType storelimit.Typ return nil } -<<<<<<< HEAD -======= // SetAllStoresLimitTTL is used to set limit of all stores with ttl func (h *Handler) SetAllStoresLimitTTL(ratePerMin float64, limitType storelimit.Type, ttl time.Duration) error { c, err := h.GetRaftCluster() @@ -449,7 +447,6 @@ func (h *Handler) SetLabelStoresLimit(ratePerMin float64, limitType storelimit.T return nil } ->>>>>>> 47e83f78... api: support temporary configuration (#3082) // GetAllStoresLimit is used to get limit of all stores. func (h *Handler) GetAllStoresLimit(limitType storelimit.Type) (map[uint64]config.StoreLimitConfig, error) { c, err := h.GetRaftCluster()