[英]Code running fine in debug mode, but stops when run normally (eclipse)
[英]Unit test succeeds in debug mode but fails when running it normally
為什么我的單元測試在調試模式下成功,但是在正常運行時失敗?
public class ExecutorServiceTest extends MockitoTestCase{
private int numThreads;
private ExecutorService pool;
private volatile boolean interruptedBitSet;
@Override
public void setUp() {
numThreads = 5;
pool = Executors.newFixedThreadPool(numThreads);
}
class TaskChecksForInterruptedBit implements Callable<String> {
@Override
public String call() throws Exception {
interruptedBitSet = false;
while (!Thread.currentThread().isInterrupted()) {
}
interruptedBitSet = Thread.currentThread().isInterrupted();
return "blah";
}
}
public void testCancelSetsInterruptedBitInCallable() throws Exception {
interruptedBitSet = false;
final Future<String> future =
pool.submit(new TaskChecksForInterruptedBit());
final boolean wasJustCancelled = future.cancel(true);
assertTrue(wasJustCancelled);
// Give time for the thread to notice the interrupted bit and set the flag
Thread.sleep(5000);
// This succeeds when stepping through w/ a debugger, but fails when running
// the test straight. WHY?
assertTrue(interruptedBitSet);
assertTrue(future.isDone());
assertTrue(future.isCancelled());
}
}
原因幾乎可以肯定是,調試器中的斷點將暫停主線程,但不暫停任何后台線程-ExecutorService中的那些后台線程。 在Eclipse中調試時,您可以更改斷點以暫停所有線程,而不僅僅是主要線程。
當不調試任務提交和立即取消時,是如此之快,以至於您在任務運行一次之前就將其取消。 嘗試在這些行之間添加睡眠延遲:
final Future<String> future = pool.submit(new TaskChecksForInterruptedBit());
Thread.sleep(1000);
final boolean wasJustCancelled = future.cancel(true);
我知道這很舊,但是我遇到了同樣的問題。 我的問題是我有一個IEnumerable ,我正在枚舉並檢查輸出。
運行單元測試時, IEnumerable返回的調試順序與其他順序不同。 這就是IEnumerable的本質,只需添加一個OrderBy子句即可解決我的問題。
我希望這對外面的人有所幫助,因為這可能會令人沮喪。
您必須確保任務實際開始運行。 它甚至有可能被取消。
public class ExecutorServiceTest {
private int numThreads;
private ExecutorService pool;
private volatile boolean interruptedBitSet;
private static final CountDownLatch latch = new CountDownLatch(1);
@Before
public void setUp() {
numThreads = 5;
pool = Executors.newFixedThreadPool(numThreads);
}
class TaskChecksForInterruptedBit implements Callable<String> {
@Override
public String call() throws Exception {
interruptedBitSet = false;
latch.countDown();
while (!Thread.currentThread().isInterrupted()) {
System.out.println(System.currentTimeMillis());
}
System.out.println("haha");
interruptedBitSet = Thread.currentThread().isInterrupted();
return "blah";
}
}
@Test
public void testCancelSetsInterruptedBitInCallable() throws Exception {
final Future<String> future =
pool.submit(new TaskChecksForInterruptedBit());
interruptedBitSet = false;
latch.await();
final boolean wasJustCancelled = future.cancel(true);
Assert.assertTrue(wasJustCancelled);
// Give time for the thread to notice the interrupted bit and set the flag
Thread.sleep(5000);
// This succeeds when stepping through w/ a debugger, but fails when running
// the test straight. WHY?
Assert.assertTrue(interruptedBitSet);
Assert.assertTrue(future.isDone());
Assert.assertTrue(future.isCancelled());
}
}
您應該在終止主線程之前檢查所有線程是否都死了
private void shutdownExecutionService(ExecutorService executorService) {
if (executorService != null) {
try {
executorService.shutdown();
while (!executorService.awaitTermination(10, TimeUnit.HOURS)) {
logger.info("Awaiting completion of threads.");
}
} catch (final InterruptedException e) {
logger.error("Error while shutting down threadpool", e);
}
}
}
通過在線課程進行家庭作業時,我遇到了類似的問題。 我添加到構建路徑的課程中的評分器程序使用了JUnit4,我的Eclipse版本將JUnit5添加到了任何新的測試用例中。 我創建了一個新的Java項目,並在沒有評分器的情況下為測試用例添加了JUnit5,並將其修復了。 希望這可以幫助。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.