UpdateState intercepts child balancer state updates. It updates the per-endpoint state stored in the ring, and also the aggregated state based on the child picker. It also reconciles the endpoint list. It sets `b.shouldRegenerateRing` to true if the new endpoint list is different from the previous,
(state balancer.State)
| 128 | // - an endpoint's weight was updated |
| 129 | // - the first addresses of the endpoint has changed |
| 130 | func (b *ringhashBalancer) UpdateState(state balancer.State) { |
| 131 | b.mu.Lock() |
| 132 | defer b.mu.Unlock() |
| 133 | childStates := endpointsharding.ChildStatesFromPicker(state.Picker) |
| 134 | // endpointsSet is the set converted from endpoints, used for quick lookup. |
| 135 | endpointsSet := resolver.NewEndpointMap[bool]() |
| 136 | |
| 137 | for _, childState := range childStates { |
| 138 | endpoint := childState.Endpoint |
| 139 | endpointsSet.Set(endpoint, true) |
| 140 | newWeight := getWeightAttribute(endpoint) |
| 141 | hk := hashKey(endpoint) |
| 142 | es, ok := b.endpointStates.Get(endpoint) |
| 143 | if !ok { |
| 144 | es := &endpointState{ |
| 145 | balancer: childState.Balancer, |
| 146 | hashKey: hk, |
| 147 | weight: newWeight, |
| 148 | state: childState.State, |
| 149 | } |
| 150 | b.endpointStates.Set(endpoint, es) |
| 151 | b.shouldRegenerateRing = true |
| 152 | } else { |
| 153 | // We have seen this endpoint before and created a `endpointState` |
| 154 | // object for it. If the weight or the hash key of the endpoint has |
| 155 | // changed, update the endpoint state map with the new weight or |
| 156 | // hash key. This will be used when a new ring is created. |
| 157 | if oldWeight := es.weight; oldWeight != newWeight { |
| 158 | b.shouldRegenerateRing = true |
| 159 | es.weight = newWeight |
| 160 | } |
| 161 | if es.hashKey != hk { |
| 162 | b.shouldRegenerateRing = true |
| 163 | es.hashKey = hk |
| 164 | } |
| 165 | es.state = childState.State |
| 166 | } |
| 167 | } |
| 168 | |
| 169 | for endpoint := range b.endpointStates.All() { |
| 170 | if _, ok := endpointsSet.Get(endpoint); ok { |
| 171 | continue |
| 172 | } |
| 173 | // endpoint was removed by resolver. |
| 174 | b.endpointStates.Delete(endpoint) |
| 175 | b.shouldRegenerateRing = true |
| 176 | } |
| 177 | |
| 178 | b.updatePickerLocked() |
| 179 | } |
| 180 | |
| 181 | func (b *ringhashBalancer) UpdateClientConnState(ccs balancer.ClientConnState) error { |
| 182 | if b.logger.V(2) { |
nothing calls this directly
no test coverage detected