From 33af20776a66e3bc366fafd3d63510b458cd8064 Mon Sep 17 00:00:00 2001 From: daniel-dios Date: Thu, 27 Oct 2022 17:19:15 +0200 Subject: [PATCH 1/4] throwsMany Co-authored-by: antonio-manuel --- .../src/commonMain/kotlin/io/mockk/API.kt | 3 +++ .../io/mockk/it/AdditionalAnswerTest.kt | 24 +++++++++++++++++++ 2 files changed, 27 insertions(+) diff --git a/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt b/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt index c467cd206..bc75f1488 100644 --- a/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt +++ b/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt @@ -2133,6 +2133,9 @@ class MockKStubScope( infix fun throws(ex: Throwable) = answers(ThrowingAnswer(ex)) + infix fun throwsMany(exList: List): MockKAdditionalAnswerScope = + this answers (ManyAnswersAnswer(exList.map { ThrowingAnswer(it) })) + infix fun answers(answer: MockKAnswerScope.(Call) -> T) = answers(FunctionAnswer { MockKAnswerScope(lambda, it).answer(it) }) diff --git a/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt b/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt index 7dbf0b52b..191294293 100644 --- a/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt +++ b/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt @@ -123,6 +123,30 @@ class AdditionalAnswerTest { } } + @Test + fun andThrowsMany() { + val exceptions = listOf( + IllegalArgumentException("error1"), + NullPointerException("error2"), + NoSuchElementException("error3") + ) + + every { mock.op(any()) } throwsMany exceptions + + assertFailsWith(IllegalArgumentException::class) { + mock.op(2) + } + assertFailsWith(NullPointerException::class) { + mock.op(3) + } + assertFailsWith(NoSuchElementException::class) { + mock.op(3) + } + assertFailsWith(NoSuchElementException::class) { + mock.op(4) + } + } + @Test fun arbitraryLengthCheck() { every { From e405665af363724db539d898aa1ed2e6259a3a8e Mon Sep 17 00:00:00 2001 From: daniel-dios Date: Thu, 27 Oct 2022 17:36:31 +0200 Subject: [PATCH 2/4] andThenThrowsMany Co-authored-by: antonio-manuel --- .../src/commonMain/kotlin/io/mockk/API.kt | 3 +++ .../io/mockk/it/AdditionalAnswerTest.kt | 23 +++++++++++++++++++ 2 files changed, 26 insertions(+) diff --git a/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt b/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt index bc75f1488..cf8c484b3 100644 --- a/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt +++ b/modules/mockk-dsl/src/commonMain/kotlin/io/mockk/API.kt @@ -2186,6 +2186,9 @@ class MockKAdditionalAnswerScope( infix fun andThenThrows(ex: Throwable) = andThenAnswer(ThrowingAnswer(ex)) + infix fun andThenThrowsMany(exList: List) = + andThenAnswer(ManyAnswersAnswer(exList.map { ThrowingAnswer(it) })) + @Deprecated("Use andThenAnswer instead of andThen.") infix fun andThen(answer: MockKAnswerScope.(Call) -> T) = andThenAnswer(FunctionAnswer { MockKAnswerScope(lambda, it).answer(it) }) diff --git a/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt b/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt index 191294293..7898706b8 100644 --- a/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt +++ b/modules/mockk/src/commonTest/kotlin/io/mockk/it/AdditionalAnswerTest.kt @@ -147,6 +147,29 @@ class AdditionalAnswerTest { } } + @Test + fun andThenThrowsMany() { + val exceptions = listOf( + IllegalArgumentException("error1"), + NullPointerException("error2"), + NoSuchElementException("error3") + ) + every { mock.op(any()) } returns 3 andThenThrowsMany exceptions andThen 2 + + assertEquals(3, mock.op(1)) + assertFailsWith(IllegalArgumentException::class) { + mock.op(2) + } + assertFailsWith(NullPointerException::class) { + mock.op(3) + } + assertFailsWith(NoSuchElementException::class) { + mock.op(3) + } + assertEquals(2, mock.op(4)) + assertEquals(2, mock.op(5)) + } + @Test fun arbitraryLengthCheck() { every { From 6172acea635235d66927fee2a22b851009ebf8a3 Mon Sep 17 00:00:00 2001 From: Antonio Lopez Date: Fri, 28 Oct 2022 16:04:15 +0200 Subject: [PATCH 3/4] added throwsMany documentation Co-authored-by: daniel-dios --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 63d9a09ac..6fa847839 100644 --- a/README.md +++ b/README.md @@ -1321,6 +1321,7 @@ An Answer can be followed up by one or more additional answers. |`returnsMany list`|specify that the matched call returns a value from the list, with subsequent calls returning the next element| |`returnsArgument(n)`|specify that the matched call returns the nth argument of that call| |`throws ex`|specify that the matched call throws an exception| +|`throwsMany ex`| specify that the matched call throws an exception from the list, with subsequent calls throwing the next exception| |`answers { code }`|specify that the matched call answers with a code block scoped with `answer scope`| |`coAnswers { code }`|specify that the matched call answers with a coroutine code block with `answer scope`| |`answers answerObj`|specify that the matched call answers with an Answer object| @@ -1341,6 +1342,7 @@ So this is similar to the `returnsMany` semantics. |`andThen value`|specify that the matched call returns one specified value| |`andThenMany list`|specify that the matched call returns a value from the list, with subsequent calls returning the next element| |`andThenThrows ex`|specify that the matched call throws an exception| +|`andThenThrowsMany ex`|specify that the matched call throws an exception from the list, with subsequent calls throwing the next exception| |`andThen { code }`|specify that the matched call answers with a code block scoped with `answer scope`| |`coAndThen { code }`|specify that the matched call answers with a coroutine code block with `answer scope`| |`andThenAnswer answerObj`|specify that the matched call answers with an Answer object| From 87219d1f051976dc0945e142c308cb541e38613f Mon Sep 17 00:00:00 2001 From: Antonio Lopez Date: Fri, 28 Oct 2022 16:29:41 +0200 Subject: [PATCH 4/4] mockk-dsl.api fixed Co-authored-by: daniel-dios --- modules/mockk-dsl/api/mockk-dsl.api | 2 ++ 1 file changed, 2 insertions(+) diff --git a/modules/mockk-dsl/api/mockk-dsl.api b/modules/mockk-dsl/api/mockk-dsl.api index e2bcb72a0..1be7af8fc 100644 --- a/modules/mockk-dsl/api/mockk-dsl.api +++ b/modules/mockk-dsl/api/mockk-dsl.api @@ -486,6 +486,7 @@ public final class io/mockk/MockKAdditionalAnswerScope { public final fun andThenMany (Ljava/util/List;)Lio/mockk/MockKAdditionalAnswerScope; public final fun andThenMany ([Ljava/lang/Object;)Lio/mockk/MockKAdditionalAnswerScope; public final fun andThenThrows (Ljava/lang/Throwable;)Lio/mockk/MockKAdditionalAnswerScope; + public final fun andThenThrowsMany (Ljava/util/List;)Lio/mockk/MockKAdditionalAnswerScope; public final fun coAndThen (Lkotlin/jvm/functions/Function3;)Lio/mockk/MockKAdditionalAnswerScope; } @@ -927,6 +928,7 @@ public final class io/mockk/MockKStubScope { public final fun returnsMany (Ljava/util/List;)Lio/mockk/MockKAdditionalAnswerScope; public final fun returnsMany ([Ljava/lang/Object;)Lio/mockk/MockKAdditionalAnswerScope; public final fun throws (Ljava/lang/Throwable;)Lio/mockk/MockKAdditionalAnswerScope; + public final fun throwsMany (Ljava/util/List;)Lio/mockk/MockKAdditionalAnswerScope; } public final class io/mockk/MockKUnmockKCompositeScope : io/mockk/MockKUnmockKScope {