序
本文次要钻研一下dubbo-go的roundRobinLoadBalance
roundRobinLoadBalance
dubbo-go-v1.4.2/cluster/loadbalance/round_robin.go
const ( // RoundRobin ... RoundRobin = "roundrobin" // COMPLETE ... COMPLETE = 0 // UPDATING ... UPDATING = 1)var ( methodWeightMap sync.Map // [string]invokers state = int32(COMPLETE) // update lock acquired ? recyclePeriod = 60 * time.Second.Nanoseconds())func init() { extension.SetLoadbalance(RoundRobin, NewRoundRobinLoadBalance)}type roundRobinLoadBalance struct{}// NewRoundRobinLoadBalance ...func NewRoundRobinLoadBalance() cluster.LoadBalance { return &roundRobinLoadBalance{}}
- roundRobinLoadBalance的NewRoundRobinLoadBalance办法创立了roundRobinLoadBalance
Select
dubbo-go-v1.4.2/cluster/loadbalance/round_robin.go
func (lb *roundRobinLoadBalance) Select(invokers []protocol.Invoker, invocation protocol.Invocation) protocol.Invoker { count := len(invokers) if count == 0 { return nil } if count == 1 { return invokers[0] } key := invokers[0].GetUrl().Path + "." + invocation.MethodName() cache, _ := methodWeightMap.LoadOrStore(key, &cachedInvokers{}) cachedInvokers := cache.(*cachedInvokers) var ( clean = false totalWeight = int64(0) maxCurrentWeight = int64(math.MinInt64) now = time.Now() selectedInvoker protocol.Invoker selectedWeightRobin *weightedRoundRobin ) for _, invoker := range invokers { var weight = GetWeight(invoker, invocation) if weight < 0 { weight = 0 } identifier := invoker.GetUrl().Key() loaded, found := cachedInvokers.LoadOrStore(identifier, &weightedRoundRobin{weight: weight}) weightRobin := loaded.(*weightedRoundRobin) if !found { clean = true } if weightRobin.Weight() != weight { weightRobin.setWeight(weight) } currentWeight := weightRobin.increaseCurrent() weightRobin.lastUpdate = &now if currentWeight > maxCurrentWeight { maxCurrentWeight = currentWeight selectedInvoker = invoker selectedWeightRobin = weightRobin } totalWeight += weight } cleanIfRequired(clean, cachedInvokers, &now) if selectedWeightRobin != nil { selectedWeightRobin.Current(totalWeight) return selectedInvoker } // should never happen return invokers[0]}
- Select办法遍历invokers,通过weightRobin.increaseCurrent()作为currentWeight,若currentWeight大于maxCurrentWeight则更新maxCurrentWeight,设置selectedInvoker为以后invoker,设置selectedWeightRobin为以后weightRobin;之后对于selectedWeightRobin不为nil的执行selectedWeightRobin.Current(totalWeight),返回selectedInvoker
小结
roundRobinLoadBalance的NewRoundRobinLoadBalance办法创立了roundRobinLoadBalance;其Select办法遍历invokers,通过weightRobin.increaseCurrent()作为currentWeight,若currentWeight大于maxCurrentWeight则更新maxCurrentWeight,设置selectedInvoker为以后invoker,设置selectedWeightRobin为以后weightRobin
doc
- round_robin