This is an automated email from the ASF dual-hosted git repository.

dcapwell pushed a commit to branch trunk
in repository https://gitbox.apache.org/repos/asf/cassandra.git


The following commit(s) were added to refs/heads/trunk by this push:
     new bc9773ea0a Fix non-determinism of repair fuzz tests by passing 
randomizer to RetryStrategy
bc9773ea0a is described below

commit bc9773ea0ac96545d15ec81ecfe16ca65ef1d5e5
Author: Nivy Kani <[email protected]>
AuthorDate: Fri Jan 9 11:41:31 2026 -0800

    Fix non-determinism of repair fuzz tests by passing randomizer to 
RetryStrategy
    
    patch by Nivy Kani; reviewed by David Capwell, Jyothsna Konisa for 
CASSANDRA-21087
---
 .../org/apache/cassandra/config/RetrySpec.java     |  8 ++++-
 .../cassandra/service/RetryStrategyTest.java       | 35 +++++++++++++++++++++-
 2 files changed, 41 insertions(+), 2 deletions(-)

diff --git a/src/java/org/apache/cassandra/config/RetrySpec.java 
b/src/java/org/apache/cassandra/config/RetrySpec.java
index ff9b58f827..ffcd9d7bd6 100644
--- a/src/java/org/apache/cassandra/config/RetrySpec.java
+++ b/src/java/org/apache/cassandra/config/RetrySpec.java
@@ -22,12 +22,16 @@ import java.util.Objects;
 
 import javax.annotation.Nullable;
 
+import accord.utils.RandomSource;
+
 import org.apache.cassandra.config.DurationSpec.LongMillisecondsBound;
 import org.apache.cassandra.repair.SharedContext;
 import org.apache.cassandra.service.RetryStrategy;
 import org.apache.cassandra.service.TimeoutStrategy.LatencySourceFactory;
 import org.apache.cassandra.service.WaitStrategy;
 
+import static org.apache.cassandra.service.RetryStrategy.randomizers;
+
 public class RetrySpec
 {
     public static class MaxAttempt
@@ -161,7 +165,9 @@ public class RetrySpec
     {
         if (!spec.isEnabled())
             return WaitStrategy.None.INSTANCE;
-        return RetryStrategy.parse(spec.baseSleepTime.toMilliseconds() + "ms * 
2^attempts <= " + spec.maxSleepTime.toMilliseconds() + "ms,retries=" + 
(spec.maxAttempts.value - 1), LatencySourceFactory.none());
+        RandomSource randomSource = RandomSource.wrap(ctx.random().get());
+        RetryStrategy.WaitRandomizer randomizer = 
randomizers(randomSource).uniform();
+        return RetryStrategy.parse((int) (0.5 * 
spec.baseSleepTime.toMilliseconds())  + "ms * 2^attempts ... " + (int) (1.5 * 
spec.baseSleepTime.toMilliseconds()) + "ms * 2^attempts <= " + 
spec.maxSleepTime.toMilliseconds() + "ms,retries=" + (spec.maxAttempts.value - 
1), LatencySourceFactory.none(), randomizer);
     }
 
     @Override
diff --git a/test/unit/org/apache/cassandra/service/RetryStrategyTest.java 
b/test/unit/org/apache/cassandra/service/RetryStrategyTest.java
index 26c3633a5b..957260172d 100644
--- a/test/unit/org/apache/cassandra/service/RetryStrategyTest.java
+++ b/test/unit/org/apache/cassandra/service/RetryStrategyTest.java
@@ -18,13 +18,21 @@
 
 package org.apache.cassandra.service;
 
+import java.util.Random;
+import java.util.concurrent.TimeUnit;
 import java.util.function.IntFunction;
+import java.util.function.Supplier;
 
+import org.assertj.core.api.Assertions;
 import org.junit.Test;
 
 import accord.utils.Gen;
 import accord.utils.RandomTestRunner;
 
+import org.apache.cassandra.config.DurationSpec;
+import org.apache.cassandra.config.RetrySpec;
+import org.apache.cassandra.repair.SharedContext;
+
 public class RetryStrategyTest
 {
     @Test
@@ -64,6 +72,31 @@ public class RetryStrategyTest
         });
     }
 
+    @Test
+    public void seededWaitRandomizer()
+    {
+        RetrySpec spec = new RetrySpec(new RetrySpec.MaxAttempt(10),
+                                       new 
DurationSpec.LongMillisecondsBound("200ms"),
+                                       new 
DurationSpec.LongMillisecondsBound("1000ms"));
+        long wait1 = RetrySpec.toStrategy(sharedContext(100), 
spec).computeWait(1, TimeUnit.MILLISECONDS);
+        long wait2 = RetrySpec.toStrategy(sharedContext(100), 
spec).computeWait(1, TimeUnit.MILLISECONDS);
+        long wait3 = RetrySpec.toStrategy(sharedContext(200), 
spec).computeWait(1, TimeUnit.MILLISECONDS);
+        Assertions.assertThat(wait1).isEqualTo(wait2);
+        Assertions.assertThat(wait1).isNotEqualTo(wait3);
+    }
+
+    private static SharedContext sharedContext(long seed)
+    {
+        return new 
SharedContext.ForwardingSharedContext(SharedContext.Global.instance)
+        {
+            @Override
+            public Supplier<Random> random()
+            {
+                return () -> new Random(seed);
+            }
+        };
+    }
+
     private static class TestLatencySourceFactory implements 
TimeoutStrategy.LatencySourceFactory
     {
 
@@ -73,4 +106,4 @@ public class RetryStrategyTest
             return percentile -> 10;
         }
     }
-}
\ No newline at end of file
+}


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to