1 /* 2 * Copyright 2016-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license. 3 */ 4 package kotlinx.coroutines.debug 5 6 import kotlinx.coroutines.* 7 import org.junit.Test 8 import java.util.concurrent.* 9 import kotlin.test.* 10 11 class DebugProbesTest : TestBase() { 12 createDeferrednull13 private fun CoroutineScope.createDeferred(): Deferred<*> = async(NonCancellable) { 14 throw ExecutionException(null) 15 } 16 17 @Test <lambda>null18 fun testAsync() = runTest { 19 val deferred = createDeferred() 20 val traces = listOf( 21 "java.util.concurrent.ExecutionException\n" + 22 "\tat kotlinx.coroutines.debug.DebugProbesTest\$createDeferred\$1.invokeSuspend(DebugProbesTest.kt:14)\n" + 23 "\t(Coroutine boundary)\n" + 24 "\tat kotlinx.coroutines.DeferredCoroutine.await\$suspendImpl(Builders.common.kt)\n" + 25 "\tat kotlinx.coroutines.debug.DebugProbesTest.oneMoreNestedMethod(DebugProbesTest.kt:49)\n" + 26 "\tat kotlinx.coroutines.debug.DebugProbesTest.nestedMethod(DebugProbesTest.kt:44)\n" + 27 "\tat kotlinx.coroutines.debug.DebugProbesTest\$testAsync\$1.invokeSuspend(DebugProbesTest.kt:17)\n", 28 "Caused by: java.util.concurrent.ExecutionException\n" + 29 "\tat kotlinx.coroutines.debug.DebugProbesTest\$createDeferred\$1.invokeSuspend(DebugProbesTest.kt:14)\n" + 30 "\tat kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:32)" 31 ) 32 nestedMethod(deferred, traces) 33 deferred.join() 34 } 35 36 @Test <lambda>null37 fun testAsyncWithProbes() = DebugProbes.withDebugProbes { 38 DebugProbes.sanitizeStackTraces = false 39 runTest { 40 val deferred = createDeferred() 41 val traces = listOf( 42 "java.util.concurrent.ExecutionException\n" + 43 "\tat kotlinx.coroutines.debug.DebugProbesTest\$createDeferred\$1.invokeSuspend(DebugProbesTest.kt:16)\n" + 44 "\t(Coroutine boundary)\n" + 45 "\tat kotlinx.coroutines.DeferredCoroutine.await\$suspendImpl(Builders.common.kt)\n" + 46 "\tat kotlinx.coroutines.debug.DebugProbesTest.oneMoreNestedMethod(DebugProbesTest.kt:71)\n" + 47 "\tat kotlinx.coroutines.debug.DebugProbesTest.nestedMethod(DebugProbesTest.kt:66)\n" + 48 "\t(Coroutine creation stacktrace)\n" + 49 "\tat kotlin.coroutines.intrinsics.IntrinsicsKt__IntrinsicsJvmKt.createCoroutineUnintercepted(IntrinsicsJvm.kt:116)\n" + 50 "\tat kotlinx.coroutines.intrinsics.CancellableKt.startCoroutineCancellable(Cancellable.kt:23)\n" + 51 "\tat kotlinx.coroutines.CoroutineStart.invoke(CoroutineStart.kt:99)\n" + 52 "\tat kotlinx.coroutines.AbstractCoroutine.start(AbstractCoroutine.kt:148)\n" + 53 "\tat kotlinx.coroutines.BuildersKt__BuildersKt.runBlocking(Builders.kt:45)\n" + 54 "\tat kotlinx.coroutines.BuildersKt.runBlocking(Unknown Source)\n" + 55 "\tat kotlinx.coroutines.TestBase.runTest(TestBase.kt:138)\n" + 56 "\tat kotlinx.coroutines.TestBase.runTest\$default(TestBase.kt:19)\n" + 57 "\tat kotlinx.coroutines.debug.DebugProbesTest.testAsyncWithProbes(DebugProbesTest.kt:38)", 58 "Caused by: java.util.concurrent.ExecutionException\n" + 59 "\tat kotlinx.coroutines.debug.DebugProbesTest\$createDeferred\$1.invokeSuspend(DebugProbesTest.kt:16)\n" + 60 "\tat kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:32)\n") 61 nestedMethod(deferred, traces) 62 deferred.join() 63 } 64 } 65 66 @Test <lambda>null67 fun testAsyncWithSanitizedProbes() = DebugProbes.withDebugProbes { 68 DebugProbes.sanitizeStackTraces = true 69 runTest { 70 val deferred = createDeferred() 71 val traces = listOf( 72 "java.util.concurrent.ExecutionException\n" + 73 "\tat kotlinx.coroutines.debug.DebugProbesTest\$createDeferred\$1.invokeSuspend(DebugProbesTest.kt:16)\n" + 74 "\t(Coroutine boundary)\n" + 75 "\tat kotlinx.coroutines.DeferredCoroutine.await\$suspendImpl(Builders.common.kt)\n" + 76 "\tat kotlinx.coroutines.debug.DebugProbesTest.oneMoreNestedMethod(DebugProbesTest.kt:71)\n" + 77 "\tat kotlinx.coroutines.debug.DebugProbesTest.nestedMethod(DebugProbesTest.kt:66)\n" + 78 "\t(Coroutine creation stacktrace)\n" + 79 "\tat kotlin.coroutines.intrinsics.IntrinsicsKt__IntrinsicsJvmKt.createCoroutineUnintercepted(IntrinsicsJvm.kt:116)\n" + 80 "\tat kotlinx.coroutines.intrinsics.CancellableKt.startCoroutineCancellable(Cancellable.kt:23)\n" + 81 "\tat kotlinx.coroutines.debug.DebugProbesTest.testAsyncWithSanitizedProbes(DebugProbesTest.kt:38)", 82 "Caused by: java.util.concurrent.ExecutionException\n" + 83 "\tat kotlinx.coroutines.debug.DebugProbesTest\$createDeferred\$1.invokeSuspend(DebugProbesTest.kt:16)\n" + 84 "\tat kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:32)\n") 85 nestedMethod(deferred, traces) 86 deferred.join() 87 } 88 } 89 nestedMethodnull90 private suspend fun nestedMethod(deferred: Deferred<*>, traces: List<String>) { 91 oneMoreNestedMethod(deferred, traces) 92 assertTrue(true) // Prevent tail-call optimization 93 } 94 oneMoreNestedMethodnull95 private suspend fun oneMoreNestedMethod(deferred: Deferred<*>, traces: List<String>) { 96 try { 97 deferred.await() 98 expectUnreached() 99 } catch (e: ExecutionException) { 100 verifyStackTrace(e, traces) 101 } 102 } 103 } 104