Skip to content

Commit 26425ef

Browse files
committed
Merge commit 'd66fc3a1efa1dfb33dfedf9760528f1ac2b923b6' into HEAD
2 parents 12edd88 + d66fc3a commit 26425ef

File tree

76 files changed

+2426
-368
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

76 files changed

+2426
-368
lines changed

.github/workflows/deps.yml

+43
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
name: Dependency Changes
2+
3+
# Trigger on PRs.
4+
on:
5+
pull_request:
6+
7+
permissions:
8+
contents: read
9+
10+
jobs:
11+
# Compare dependencies before and after this PR.
12+
dependencies:
13+
runs-on: ubuntu-latest
14+
timeout-minutes: 10
15+
strategy:
16+
fail-fast: true
17+
18+
steps:
19+
- name: Checkout repo
20+
uses: actions/checkout@v4
21+
with:
22+
fetch-depth: 0
23+
24+
- name: Setup Go
25+
uses: actions/setup-go@v5
26+
with:
27+
go-version: stable
28+
cache-dependency-path: "**/*go.sum"
29+
30+
# Run the commands to generate dependencies before and after and compare.
31+
- name: Compare dependencies
32+
run: |
33+
BEFORE="$(mktemp -d)"
34+
AFTER="$(mktemp -d)"
35+
36+
scripts/gen-deps.sh "${AFTER}"
37+
git checkout origin/master
38+
scripts/gen-deps.sh "${BEFORE}"
39+
40+
echo "Comparing dependencies..."
41+
# Run grep in a sub-shell since bash does not support ! in the middle of a pipe
42+
diff -u0 -r "${BEFORE}" "${AFTER}" | bash -c '! grep -v "@@"'
43+
echo "No changes detected."

.github/workflows/testing.yml

+8-12
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ jobs:
2727
- name: Setup Go
2828
uses: actions/setup-go@v5
2929
with:
30-
go-version: '1.22'
30+
go-version: '1.23'
3131
cache-dependency-path: "**/go.sum"
3232

3333
# Run the vet-proto checks.
@@ -46,32 +46,28 @@ jobs:
4646
goversion: '1.22'
4747

4848
- type: extras
49-
goversion: '1.22'
49+
goversion: '1.23'
5050

5151
- type: tests
52-
goversion: '1.22'
52+
goversion: '1.23'
5353

5454
- type: tests
55-
goversion: '1.22'
55+
goversion: '1.23'
5656
testflags: -race
5757

5858
- type: tests
59-
goversion: '1.22'
60-
testflags: '-race -tags=buffer_pooling'
61-
62-
- type: tests
63-
goversion: '1.22'
59+
goversion: '1.23'
6460
goarch: 386
6561

6662
- type: tests
67-
goversion: '1.22'
63+
goversion: '1.23'
6864
goarch: arm64
6965

7066
- type: tests
71-
goversion: '1.21'
67+
goversion: '1.22'
7268

7369
- type: tests
74-
goversion: '1.22'
70+
goversion: '1.23'
7571
testflags: -race
7672
grpcenv: 'GRPC_EXPERIMENTAL_ENABLE_NEW_PICK_FIRST=true'
7773

balancer/endpointsharding/endpointsharding.go

+28-15
Original file line numberDiff line numberDiff line change
@@ -28,11 +28,11 @@ package endpointsharding
2828
import (
2929
"encoding/json"
3030
"errors"
31-
"fmt"
32-
"math/rand"
3331
"sync"
3432
"sync/atomic"
3533

34+
rand "math/rand/v2"
35+
3636
"google.golang.org/grpc/balancer"
3737
"google.golang.org/grpc/balancer/base"
3838
"google.golang.org/grpc/connectivity"
@@ -66,7 +66,9 @@ type endpointSharding struct {
6666
cc balancer.ClientConn
6767
bOpts balancer.BuildOptions
6868

69+
childMu sync.Mutex // syncs balancer.Balancer calls into children
6970
children atomic.Pointer[resolver.EndpointMap]
71+
closed bool
7072

7173
// inhibitChildUpdates is set during UpdateClientConnState/ResolverError
7274
// calls (calls to children will each produce an update, only want one
@@ -80,19 +82,11 @@ type endpointSharding struct {
8082
// for endpoints that are no longer present. It also updates all the children,
8183
// and sends a single synchronous update of the childrens' aggregated state at
8284
// the end of the UpdateClientConnState operation. If any endpoint has no
83-
// addresses, returns error without forwarding any updates. Otherwise returns
84-
// first error found from a child, but fully processes the new update.
85+
// addresses it will ignore that endpoint. Otherwise, returns first error found
86+
// from a child, but fully processes the new update.
8587
func (es *endpointSharding) UpdateClientConnState(state balancer.ClientConnState) error {
86-
if len(state.ResolverState.Endpoints) == 0 {
87-
return errors.New("endpoints list is empty")
88-
}
89-
// Check/return early if any endpoints have no addresses.
90-
// TODO: make this configurable if needed.
91-
for i, endpoint := range state.ResolverState.Endpoints {
92-
if len(endpoint.Addresses) == 0 {
93-
return fmt.Errorf("endpoint %d has empty addresses", i)
94-
}
95-
}
88+
es.childMu.Lock()
89+
defer es.childMu.Unlock()
9690

9791
es.inhibitChildUpdates.Store(true)
9892
defer func() {
@@ -106,6 +100,9 @@ func (es *endpointSharding) UpdateClientConnState(state balancer.ClientConnState
106100

107101
// Update/Create new children.
108102
for _, endpoint := range state.ResolverState.Endpoints {
103+
if len(endpoint.Addresses) == 0 {
104+
continue
105+
}
109106
if _, ok := newChildren.Get(endpoint); ok {
110107
// Endpoint child was already created, continue to avoid duplicate
111108
// update.
@@ -153,6 +150,8 @@ func (es *endpointSharding) UpdateClientConnState(state balancer.ClientConnState
153150
// children and sends a single synchronous update of the childStates at the end
154151
// of the ResolverError operation.
155152
func (es *endpointSharding) ResolverError(err error) {
153+
es.childMu.Lock()
154+
defer es.childMu.Unlock()
156155
es.inhibitChildUpdates.Store(true)
157156
defer func() {
158157
es.inhibitChildUpdates.Store(false)
@@ -170,11 +169,14 @@ func (es *endpointSharding) UpdateSubConnState(balancer.SubConn, balancer.SubCon
170169
}
171170

172171
func (es *endpointSharding) Close() {
172+
es.childMu.Lock()
173+
defer es.childMu.Unlock()
173174
children := es.children.Load()
174175
for _, child := range children.Values() {
175176
bal := child.(balancer.Balancer)
176177
bal.Close()
177178
}
179+
es.closed = true
178180
}
179181

180182
// updateState updates this component's state. It sends the aggregated state,
@@ -234,7 +236,7 @@ func (es *endpointSharding) updateState() {
234236
p := &pickerWithChildStates{
235237
pickers: pickers,
236238
childStates: childStates,
237-
next: uint32(rand.Intn(len(pickers))),
239+
next: uint32(rand.IntN(len(pickers))),
238240
}
239241
es.cc.UpdateState(balancer.State{
240242
ConnectivityState: aggState,
@@ -282,6 +284,17 @@ func (bw *balancerWrapper) UpdateState(state balancer.State) {
282284
bw.es.mu.Lock()
283285
bw.childState.State = state
284286
bw.es.mu.Unlock()
287+
// When a child balancer says it's IDLE, ping it to exit idle and reconnect.
288+
// TODO: In the future, perhaps make this a knob in configuration.
289+
if ei, ok := bw.Balancer.(balancer.ExitIdler); state.ConnectivityState == connectivity.Idle && ok {
290+
go func() {
291+
bw.es.childMu.Lock()
292+
if !bw.es.closed {
293+
ei.ExitIdle()
294+
}
295+
bw.es.childMu.Unlock()
296+
}()
297+
}
285298
bw.es.updateState()
286299
}
287300

balancer/grpclb/grpclb_picker.go

+3-3
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@
1919
package grpclb
2020

2121
import (
22-
"math/rand"
22+
rand "math/rand/v2"
2323
"sync"
2424
"sync/atomic"
2525

@@ -112,7 +112,7 @@ type rrPicker struct {
112112
func newRRPicker(readySCs []balancer.SubConn) *rrPicker {
113113
return &rrPicker{
114114
subConns: readySCs,
115-
subConnsNext: rand.Intn(len(readySCs)),
115+
subConnsNext: rand.IntN(len(readySCs)),
116116
}
117117
}
118118

@@ -147,7 +147,7 @@ func newLBPicker(serverList []*lbpb.Server, readySCs []balancer.SubConn, stats *
147147
return &lbPicker{
148148
serverList: serverList,
149149
subConns: readySCs,
150-
subConnsNext: rand.Intn(len(readySCs)),
150+
subConnsNext: rand.IntN(len(readySCs)),
151151
stats: stats,
152152
}
153153
}

balancer/leastrequest/leastrequest.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ package leastrequest
2222
import (
2323
"encoding/json"
2424
"fmt"
25-
"math/rand"
25+
rand "math/rand/v2"
2626
"sync/atomic"
2727

2828
"google.golang.org/grpc/balancer"

balancer/pickfirst/pickfirst.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ import (
2323
"encoding/json"
2424
"errors"
2525
"fmt"
26-
"math/rand"
26+
rand "math/rand/v2"
2727

2828
"google.golang.org/grpc/balancer"
2929
"google.golang.org/grpc/balancer/pickfirst/internal"

balancer/rls/config.go

+4-1
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,10 @@ type lbConfigJSON struct {
143143
// - childPolicyConfigTargetFieldName:
144144
// - must be set and non-empty
145145
func (rlsBB) ParseConfig(c json.RawMessage) (serviceconfig.LoadBalancingConfig, error) {
146-
logger.Infof("Received JSON service config: %v", pretty.ToJSON(c))
146+
if logger.V(2) {
147+
logger.Infof("Received JSON service config: %v", pretty.ToJSON(c))
148+
}
149+
147150
cfgJSON := &lbConfigJSON{}
148151
if err := json.Unmarshal(c, cfgJSON); err != nil {
149152
return nil, fmt.Errorf("rls: json unmarshal failed for service config %+v: %v", string(c), err)

balancer/rls/control_channel.go

+3-1
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,9 @@ func (cc *controlChannel) lookup(reqKeys map[string]string, reason rlspb.RouteLo
209209
Reason: reason,
210210
StaleHeaderData: staleHeaders,
211211
}
212-
cc.logger.Infof("Sending RLS request %+v", pretty.ToJSON(req))
212+
if cc.logger.V(2) {
213+
cc.logger.Infof("Sending RLS request %+v", pretty.ToJSON(req))
214+
}
213215

214216
ctx, cancel := context.WithTimeout(context.Background(), cc.rpcTimeout)
215217
defer cancel()

balancer/rls/internal/adaptive/adaptive.go

+3-3
Original file line numberDiff line numberDiff line change
@@ -20,15 +20,15 @@
2020
package adaptive
2121

2222
import (
23-
"math/rand"
23+
rand "math/rand/v2"
2424
"sync"
2525
"time"
2626
)
2727

2828
// For overriding in unittests.
2929
var (
30-
timeNowFunc = func() time.Time { return time.Now() }
31-
randFunc = func() float64 { return rand.Float64() }
30+
timeNowFunc = time.Now
31+
randFunc = rand.Float64
3232
)
3333

3434
const (

0 commit comments

Comments
 (0)