MCPcopy
hub / github.com/grpc/grpc-go / TestThreeBackendsAffinityMultiple

Method TestThreeBackendsAffinityMultiple

balancer/ringhash/ringhash_test.go:334–425  ·  view source on GitHub ↗

TestThreeBackendsAffinity covers that there are 3 SubConns, RPCs with the same hash always pick the same SubConn. Then try different hash to pick another backend, and verify the first hash still picks the first backend.

(t *testing.T)

Source from the content-addressed store, hash-verified

332// same hash always pick the same SubConn. Then try different hash to pick
333// another backend, and verify the first hash still picks the first backend.
334func (s) TestThreeBackendsAffinityMultiple(t *testing.T) {
335 wantEndpoints := []resolver.Endpoint{
336 {Addresses: []resolver.Address{{Addr: testBackendAddrStrs[0]}}},
337 {Addresses: []resolver.Address{{Addr: testBackendAddrStrs[1]}}},
338 {Addresses: []resolver.Address{{Addr: testBackendAddrStrs[2]}}},
339 }
340 cc, _, p0 := setupTest(t, wantEndpoints)
341 // This test doesn't update addresses, so this ring will be used by all the
342 // pickers.
343 ring0 := p0.(*picker).ring
344
345 firstHash := ring0.items[0].hash
346 // firstHash+1 will pick the second SubConn from the ring.
347 testHash := firstHash + 1
348 // The first pick should be queued, and should trigger Connect() on the only
349 // SubConn.
350 ctx, cancel := context.WithTimeout(context.Background(), defaultTestTimeout)
351 defer cancel()
352 if _, err := p0.Pick(balancer.PickInfo{Ctx: iringhash.SetXDSRequestHash(ctx, testHash)}); err != balancer.ErrNoSubConnAvailable {
353 t.Fatalf("first pick returned err %v, want %v", err, balancer.ErrNoSubConnAvailable)
354 }
355 // The picked SubConn should be the second in the ring.
356 var sc0 *testutils.TestSubConn
357 select {
358 case <-ctx.Done():
359 t.Fatalf("Timed out waiting for SubConn creation.")
360 case sc0 = <-cc.NewSubConnCh:
361 }
362 if got, want := sc0.Addresses[0].Addr, ring0.items[1].hashKey; got != want {
363 t.Fatalf("SubConn.Address = %v, want = %v", got, want)
364 }
365 select {
366 case <-sc0.ConnectCh:
367 case <-time.After(defaultTestTimeout):
368 t.Errorf("timeout waiting for Connect() from SubConn %v", sc0)
369 }
370
371 // Send state updates to Ready.
372 sc0.UpdateState(balancer.SubConnState{ConnectivityState: connectivity.Connecting})
373 sc0.UpdateState(balancer.SubConnState{ConnectivityState: connectivity.Ready})
374 if err := cc.WaitForConnectivityState(ctx, connectivity.Ready); err != nil {
375 t.Fatal(err)
376 }
377
378 // First hash should always pick sc0.
379 p1 := <-cc.NewPickerCh
380 for i := 0; i < 5; i++ {
381 gotSCSt, _ := p1.Pick(balancer.PickInfo{Ctx: iringhash.SetXDSRequestHash(ctx, testHash)})
382 if gotSCSt.SubConn != sc0 {
383 t.Fatalf("picker.Pick, got %v, want SubConn=%v", gotSCSt, sc0)
384 }
385 }
386
387 secondHash := ring0.items[1].hash
388 // secondHash+1 will pick the third SubConn from the ring.
389 testHash2 := secondHash + 1
390 if _, err := p0.Pick(balancer.PickInfo{Ctx: iringhash.SetXDSRequestHash(ctx, testHash2)}); err != balancer.ErrNoSubConnAvailable {
391 t.Fatalf("first pick returned err %v, want %v", err, balancer.ErrNoSubConnAvailable)

Callers

nothing calls this directly

Calls 8

UpdateStateMethod · 0.95
setupTestFunction · 0.85
PickMethod · 0.65
FatalfMethod · 0.65
ErrorfMethod · 0.65
FatalMethod · 0.65
DoneMethod · 0.45

Tested by

no test coverage detected