|
|
|
@ -14,7 +14,10 @@ |
|
|
|
|
*/ |
|
|
|
|
package org.hyperledger.besu.ethereum.api.jsonrpc.internal; |
|
|
|
|
|
|
|
|
|
import java.util.concurrent.atomic.AtomicInteger; |
|
|
|
|
import static org.assertj.core.api.Assertions.assertThatThrownBy; |
|
|
|
|
import static org.assertj.core.api.AssertionsForClassTypes.assertThat; |
|
|
|
|
|
|
|
|
|
import java.util.concurrent.TimeoutException; |
|
|
|
|
|
|
|
|
|
import io.vertx.core.Vertx; |
|
|
|
|
import io.vertx.ext.unit.Async; |
|
|
|
@ -32,63 +35,46 @@ public class QosTimerTest { |
|
|
|
|
@Test |
|
|
|
|
public void shouldExecuteConsecutivelyAtTimeout(final TestContext ctx) { |
|
|
|
|
final long TEST_QOS_TIMEOUT = 100L; |
|
|
|
|
final Async async = ctx.async(); |
|
|
|
|
final AtomicInteger execCount = new AtomicInteger(0); |
|
|
|
|
new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> execCount.incrementAndGet()); |
|
|
|
|
|
|
|
|
|
vertx.setTimer( |
|
|
|
|
250L, |
|
|
|
|
z -> { |
|
|
|
|
ctx.assertEquals(2, execCount.get()); |
|
|
|
|
async.complete(); |
|
|
|
|
}); |
|
|
|
|
final int INVOCATIONS_COUNT = 2; |
|
|
|
|
final Async async = ctx.async(INVOCATIONS_COUNT); |
|
|
|
|
final long startTime = System.currentTimeMillis(); |
|
|
|
|
new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> async.countDown()); |
|
|
|
|
async.awaitSuccess(); |
|
|
|
|
final long executionTime = System.currentTimeMillis() - startTime; |
|
|
|
|
assertThat(executionTime) |
|
|
|
|
.as("Execution ended ahead of time") |
|
|
|
|
.isGreaterThanOrEqualTo(TEST_QOS_TIMEOUT * INVOCATIONS_COUNT); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
public void shouldExecuteOnceAtTimeout(final TestContext ctx) { |
|
|
|
|
final long TEST_QOS_TIMEOUT = 75L; |
|
|
|
|
final Async async = ctx.async(); |
|
|
|
|
final AtomicInteger execCount = new AtomicInteger(0); |
|
|
|
|
new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> execCount.incrementAndGet()); |
|
|
|
|
|
|
|
|
|
vertx.setTimer( |
|
|
|
|
100L, |
|
|
|
|
z -> { |
|
|
|
|
ctx.assertEquals(1, execCount.get()); |
|
|
|
|
async.complete(); |
|
|
|
|
}); |
|
|
|
|
final long startTime = System.currentTimeMillis(); |
|
|
|
|
new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> async.countDown()); |
|
|
|
|
async.awaitSuccess(); |
|
|
|
|
final long executionTime = System.currentTimeMillis() - startTime; |
|
|
|
|
assertThat(executionTime) |
|
|
|
|
.as("Execution ended ahead of time") |
|
|
|
|
.isGreaterThanOrEqualTo(TEST_QOS_TIMEOUT); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
public void shouldNotExecuteBeforeTimeout(final TestContext ctx) { |
|
|
|
|
final long TEST_QOS_TIMEOUT = 200L; |
|
|
|
|
final Async async = ctx.async(); |
|
|
|
|
final AtomicInteger execCount = new AtomicInteger(0); |
|
|
|
|
new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> execCount.incrementAndGet()); |
|
|
|
|
|
|
|
|
|
vertx.setTimer( |
|
|
|
|
50L, |
|
|
|
|
z -> { |
|
|
|
|
ctx.assertEquals(0, execCount.get()); |
|
|
|
|
async.complete(); |
|
|
|
|
}); |
|
|
|
|
new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> async.countDown()); |
|
|
|
|
assertThatThrownBy(() -> async.awaitSuccess(50L)).isInstanceOf(TimeoutException.class); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@Test |
|
|
|
|
public void shouldNotExecuteWhenReset(final TestContext ctx) { |
|
|
|
|
final long TEST_QOS_TIMEOUT = 50L; |
|
|
|
|
final Async async = ctx.async(); |
|
|
|
|
final AtomicInteger execCount = new AtomicInteger(0); |
|
|
|
|
final var timer = new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> execCount.incrementAndGet()); |
|
|
|
|
|
|
|
|
|
final var timer = new QosTimer(vertx, TEST_QOS_TIMEOUT, z -> async.countDown()); |
|
|
|
|
// reset QoS timer every 25 millis
|
|
|
|
|
vertx.setPeriodic(25L, z -> timer.resetTimer()); |
|
|
|
|
|
|
|
|
|
vertx.setTimer( |
|
|
|
|
200L, |
|
|
|
|
z -> { |
|
|
|
|
ctx.assertEquals(0, execCount.get()); |
|
|
|
|
assertThatThrownBy(() -> async.awaitSuccess(200L)).isInstanceOf(TimeoutException.class); |
|
|
|
|
async.complete(); |
|
|
|
|
}); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|