ExecutionStateSampler { @VisibleForTesting public synchronized void doSampling(long millisSinceLastSample) { for (ExecutionStateTracker tracker : activeTrackers) { tracker.takeSample(millisSinceLastSample); } } private  ExecutionStateSampler(MillisProvider clock); static ExecutionStateSampler instance(); @VisibleForTesting static ExecutionStateSampler newForTest(); @VisibleForTesting static ExecutionStateSampler newForTest(MillisProvider clock); void reset(); void start(); synchronized void stop(); @VisibleForTesting synchronized void doSampling(long millisSinceLastSample);  }
@Test public void testOneThreadSampling() throws Exception { ExecutionStateTracker tracker = createTracker(); try (Closeable c1 = tracker.activate(new Thread())) { try (Closeable c2 = tracker.enterState(step1act1)) { sampler.doSampling(400); assertThat(step1act1.totalMillis, equalTo(400L)); sampler.doSampling(200); assertThat(step1act1.totalMillis, equalTo(400L + 200L)); } sampler.doSampling(300); assertThat(step1act1.totalMillis, equalTo(400L + 200L)); assertThat(step1act1.lullReported, equalTo(false)); } }
@Test public void testMultipleThreads() throws Exception { ExecutionStateTracker tracker1 = createTracker(); ExecutionStateTracker tracker2 = createTracker(); try (Closeable t1 = tracker1.activate(new Thread())) { try (Closeable t2 = tracker2.activate(new Thread())) { Closeable c1 = tracker1.enterState(step1act1); sampler.doSampling(101); Closeable c2 = tracker2.enterState(step2act1); sampler.doSampling(102); Closeable c3 = tracker1.enterState(step1act2); sampler.doSampling(203); c3.close(); sampler.doSampling(104); c1.close(); sampler.doSampling(105); c2.close(); } } assertThat(step1act1.totalMillis, equalTo(101L + 102L + 104L)); assertThat(step1act2.totalMillis, equalTo(203L)); assertThat(step2act1.totalMillis, equalTo(102L + 203L + 104L + 105L)); assertThat(step1act1.lullReported, equalTo(false)); assertThat(step1act2.lullReported, equalTo(false)); assertThat(step2act1.lullReported, equalTo(false)); }
@Test public void testLullDetectionOccurs() throws Exception { ExecutionStateTracker tracker1 = createTracker(); try (Closeable t1 = tracker1.activate(new Thread())) { try (Closeable c = tracker1.enterState(step1act1)) { sampler.doSampling(TimeUnit.MINUTES.toMillis(6)); } } assertThat(step1act1.lullReported, equalTo(true)); }