@@ -1058,3 +1058,85 @@ func TestServerSendsHighStampsDiff(t *testing.T) {
10581058 return nil
10591059 })
10601060}
1061+
1062+ // TestGossipBatching verifies that both server and client gossip updates are
1063+ // batched.
1064+ func TestGossipBatching (t * testing.T ) {
1065+ defer leaktest .AfterTest (t )()
1066+ skip .UnderDeadlock (t , "might be flaky since it relies on some upper-bound timing" )
1067+ skip .UnderRace (t , "might be flaky since it relies on some upper-bound timing" )
1068+
1069+ stopper := stop .NewStopper ()
1070+ defer stopper .Stop (context .Background ())
1071+
1072+ // Shared cluster ID by all gossipers
1073+ clusterID := uuid .MakeV4 ()
1074+
1075+ local , localCtx := startGossip (clusterID , 1 , stopper , t , metric .NewRegistry ())
1076+ remote , remoteCtx := startGossip (clusterID , 2 , stopper , t , metric .NewRegistry ())
1077+ remote .mu .Lock ()
1078+ rAddr := remote .mu .is .NodeAddr
1079+ remote .mu .Unlock ()
1080+ local .manage (localCtx )
1081+ remote .manage (remoteCtx )
1082+
1083+ // Start a client connection to the remote node
1084+ local .mu .Lock ()
1085+ local .startClientLocked (rAddr , roachpb.Locality {}, localCtx )
1086+ local .mu .Unlock ()
1087+
1088+ // Wait for connection to be established
1089+ var c * client
1090+ testutils .SucceedsSoon (t , func () error {
1091+ c = local .findClient (func (c * client ) bool { return c .addr .String () == rAddr .String () })
1092+ if c == nil {
1093+ return fmt .Errorf ("client not found" )
1094+ }
1095+ return nil
1096+ })
1097+
1098+ // Prepare 10,000 keys to gossip. This is a large enough number to allow
1099+ // batching to kick in.
1100+ numKeys := 10_000
1101+ localKeys := make ([]string , numKeys )
1102+ remoteKeys := make ([]string , numKeys )
1103+ for i := 0 ; i < numKeys ; i ++ {
1104+ localKeys [i ] = fmt .Sprintf ("local-key-%d" , i )
1105+ remoteKeys [i ] = fmt .Sprintf ("remote-key-%d" , i )
1106+ }
1107+
1108+ // Gossip the keys to both local and remote nodes.
1109+ for i := range numKeys {
1110+ require .NoError (t , local .AddInfo (localKeys [i ], []byte ("value" ), time .Hour ))
1111+ require .NoError (t , remote .AddInfo (remoteKeys [i ], []byte ("value" ), time .Hour ))
1112+ }
1113+
1114+ // Wait for updates to propagate
1115+ testutils .SucceedsSoon (t , func () error {
1116+ for i := range numKeys {
1117+ if _ , err := local .GetInfo (remoteKeys [i ]); err != nil {
1118+ return err
1119+ }
1120+ if _ , err := remote .GetInfo (localKeys [i ]); err != nil {
1121+ return err
1122+ }
1123+ }
1124+ return nil
1125+ })
1126+
1127+ // Record the number of messages both the client and the server sent, and
1128+ // assert that it's within the expected bounds.
1129+ serverMessagesSentCount := remote .serverMetrics .MessagesSent .Count ()
1130+ clientMessagesSentCount := local .serverMetrics .MessagesSent .Count ()
1131+
1132+ fmt .Printf ("client msgs sent: %+v\n " , clientMessagesSentCount )
1133+ fmt .Printf ("server msgs sent: %+v\n " , serverMessagesSentCount )
1134+
1135+ // upperBoundMessages is the maximum number of sent messages we expect to see.
1136+ // Note that in reality with batching, we see 3-10 messages sent in this test,
1137+ // However, in order to avoid flakiness, we set a very high number here. The
1138+ // test would fail even with this high number if we don't have batching.
1139+ upperBoundMessages := int64 (500 )
1140+ require .LessOrEqual (t , serverMessagesSentCount , upperBoundMessages )
1141+ require .LessOrEqual (t , clientMessagesSentCount , upperBoundMessages )
1142+ }
0 commit comments