### Mocking a BookRepository in Kotlin Source: https://github.com/lupuuss/mokkery/blob/master/README.md Demonstrates how to mock a BookRepository using Mokkery, define behavior for suspend functions with `everySuspend`, and provide custom call logic. This setup is useful for testing services that depend on repository interactions. ```kotlin class BookServiceTest { val repository = mock { everySuspend { findById(any()) } calls { (id: String) -> Book(id) } } val service = BookService(repository) @Test fun `rent should call repository for each book`() = runTest { service.rentAll(listOf("1", "2")) verifySuspend(exhaustiveOrder) { repository.findById("1") repository.findById("2") } } } ``` -------------------------------- ### Soft Mode Verification Example Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx In soft mode, `verify` checks if each call pattern occurred at least once. Duplicated patterns within a single `verify` block do not change the outcome as each check is independent. ```kotlin foo.getAt(1) verify { foo.getAt(1) } // ✅ verify { foo.getAt(1) } // ❌ - no matching calls ``` ```kotlin foo.getAll() foo.getAll() verify { foo.getAll() // ✅ - `getAll` was called at least once } ``` ```kotlin foo.getAll() foo.getAll() verify { foo.getAll() foo.getAll() // ✅ - `getAll` was called at least once // the only difference is that `getAll` check is duplicated } ``` -------------------------------- ### MokkerySuiteScope Mock and Verify Overloads Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Strict_exhaustiveness.mdx This example highlights how mocks and verification functions become extensions of `MokkerySuiteScope` when the interface is implemented, enabling stricter checks. ```kotlin class ClassTest : MokkerySuiteScope { private val a = mock() // <-- This calls `fun MokkerySuiteScope.mock(...)`, not `fun mock(...)` private val b = mock() // <-- Same as above @Test fun test() { a.call(1) b.call(2) // Verification fails - b.call(2) was not verified verify(exhaustive) { // <-- This calls `fun MokkerySuiteScope.verify(...)`, not `fun verify(...)` a.call(1) } } } ``` -------------------------------- ### Basic Mocking Without Strict Exhaustiveness Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Strict_exhaustiveness.mdx This example demonstrates a typical test setup where not all mock calls are verified, and Mokkery's default behavior allows this. ```kotlin class ClassTest { private val a = mock() private val b = mock() @Test fun test() { a.call(1) b.call(2) // Verification passes verify(exhaustive) { a.call(1) } } } ``` -------------------------------- ### Shorthand Behavior Definition with Function References Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Both `every` and `everySuspend` support function references for a more concise way to define behavior. This example demonstrates defining getters, setters, and suspending functions using this shorthand. ```kotlin every(foo::getAll) returns listOf(1, 2) every(foo::values::get) returns listOf(2, 3) every(foo::values::set) returns Unit everySuspend(foo::fetchAt) returns 10 foo.getAll() // returns listOf(1, 2) foo.values // returns listOf(2, 3) foo.values = emptyList() // returns Unit foo.fetchAt(0) // returns 10 foo.fetchAt(1) // returns 10 foo.fetchAt(2) // returns 10 ``` -------------------------------- ### Non-synchronized Side Effect Example Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Thread_safety.mdx This example demonstrates a non-synchronized side effect that can cause issues in multithreaded environments. ```kotlin var x: Int = 0 every { mock.getAndIncrement() } calls { x++ } ``` -------------------------------- ### Suspend-Only Answer with Delay Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Implement a custom answer for suspend functions that introduces a delay before returning a value. This example demonstrates how to create a suspend-only answer and its usage. ```kotlin infix fun SuspendAnsweringScope.returnsDelayed(value: T) { answers(ReturnsDelayedAnswer(value)) } // you can optionally mark this class as private private class ReturnsDelayedAnswer(private val value: T) : Answer { public fun call(scope: MokkeryBlockingCallScope): T = error("Not supported") public suspend fun call(scope: MokkerySuspendCallScope): T { delay(1_000) return value } } ``` ```kotlin // Usage: everySuspend { mock.fetchAt(any()) } returnsDelayed 10 // ✅ compiles - suspend context every { mock.getAt(any()) } returnsDelayed 10 // ❌ does NOT compile - regular context ``` -------------------------------- ### Mocking Suspendable Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Use `everySuspend` to mock suspendable functions. This example uses `calls` to define a custom suspending answer with a delay. ```kotlin everySuspend { mock.fetchAt(any()) } calls { (index: Int) -> delay(1_000) index + 1 } ``` -------------------------------- ### Handle Overlapping Answers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx When multiple answers match a call, the most recently defined answer takes precedence. This example shows how a general `any()` matcher overrides a specific parameter match. ```kotlin // this answer is unreachable as the later defined matches all possible calls every { foo.getAt(0) } returns 1 every { foo.getAt(any()) } returns 2 foo.getAt(0) // returns 2 ``` -------------------------------- ### Manual MokkerySuiteScope Creation Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Strict_exhaustiveness.mdx Demonstrates how to manually create and use a `MokkerySuiteScope` instance when you cannot implement the interface directly in your test class. ```kotlin with(MokkerySuiteScope()) { val a = mock() val b = mock() a.call(1) b.call(2) // Verification fails // Unverified call: b.call(2) verify(exhaustive) { a.call(1) } } ``` -------------------------------- ### Implement `description()` for Debugging Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Add a `description()` function to your custom `Answer` implementation to provide a human-readable explanation for debugging purposes, especially with `printMokkeryDebug`. ```kotlin infix fun SuspendAnsweringScope.returnsDelayed(value: T) { answers(ReturnsDelayedAnswer(value)) } // ... private class ReturnsDelayedAnswer(private val value: T) : Answer { // ... override fun description() = "returnsDelayed $value" } ``` -------------------------------- ### Enable Concrete Class Instantiation and Class Inheritance Stubs Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx Configure Mokkery to allow instantiation of concrete classes and generation of stub implementations for classes by setting flags in the `build.gradle.kts` file. This is necessary for mocking classes with parameterized constructors or when generating stubs for classes. ```kotlin mokkery { stubs { allowConcreteClassInstantiation = true allowClassInheritance = true } } ``` -------------------------------- ### Configure Dependency Resolution Management Repositories Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Configure repositories for dependency resolution management. Includes `mavenCentral()` and `gradlePluginPortal()` for older Mokkery versions. ```kotlin dependencyResolutionManagement { repositories { mavenCentral() // required to download Mokkery Gradle plugin before version 2.3.0 gradlePluginPortal() } } ``` -------------------------------- ### Apply All-Open Plugin for Final Classes Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Apply the `all-open` plugin and define a custom annotation to make final classes open for mocking. ```kotlin plugins { // ... kotlin("plugin.allopen") } ``` ```kotlin package your.package annotation class OpenForMokkery() ``` ```kotlin @OpenForMokkery class Foo { fun foo() = Unit } ``` ```kotlin allOpen { annotation("your.package.OpenForMokkery") } ``` -------------------------------- ### Mocking Member Functions with Extension Parameters Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx For member functions that include extension parameters, use the special `ext` function within `every` to define their behavior. Ensure `dev.mokkery.templating.ext` is imported. ```kotlin import dev.mokkery.templating.ext // ... every { foo.ext { any().toNumber() } } returns 10 foo.run { "10".toNumber() } // returns 10 ``` -------------------------------- ### Configure Plugin Management Repository Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Configure repositories for plugin dependencies. `gradlePluginPortal()` is required for Mokkery versions before 2.3.0. ```kotlin pluginManagement { repositories { gradlePluginPortal() // required only before Mokkery 2.3.0 mavenCentral() } } ``` -------------------------------- ### Configure Runtime Dependencies Repository Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Configure the Maven Central repository for runtime dependencies. This is a standard Gradle configuration. ```kotlin repositories { mavenCentral() } ``` -------------------------------- ### Create Custom Answer Using Existing Answers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Simplify custom answer creation by declaring an extension using existing built-in answers. This avoids implementing a new `Answer` class and reduces boilerplate. ```kotlin fun SuspendAnsweringScope.returnsDelayed(value: T) { calls { delay(1_000) value } } ``` -------------------------------- ### Apply Mokkery to Listed Source Sets Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Manually specify source sets for Mokkery application using `ApplicationRule.Listed`. Ensure all source sets within a subtree are included. ```kotlin ApplicationRule.Listed("fooMain", "barMain") ``` -------------------------------- ### Use Matchers for Broad Parameter Acceptance Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Employ matchers like `any()` to define behavior that accepts a wider range of parameter values, ensuring a default response for any input. ```kotlin every { foo.getAt(any()) } returns 0 foo.getAt(0) // returns 0 foo.getAt(1) // returns 0 foo.getAt(2) // returns 0 ``` -------------------------------- ### Order Verification Mode Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx `VerifyMode.order` verifies that each call from the verification block happened exactly once and in the specified sequence. ```kotlin mock.getAt(1) mock.getAt(2) mock.getAll() verify(order) { mock.getAt(any()) mock.getAll() // ✅ - only `getAt(1)` and `getAll()` are marked as verified } ``` ```kotlin mock.getAt(1) mock.getAt(2) mock.getAll() verify(order) { mock.getAll() mock.getAt(any()) // ❌ - `getAt(any())` does not occur after `getAll()` } ``` -------------------------------- ### Conditionally Apply All-Open Plugin Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Conditionally apply the `allOpen` configuration based on whether a testing task is being executed to avoid opening production code. ```kotlin // this check might require adjustment depending on your project type and the tasks that you use // `endsWith("Test")` works with "*Test" tasks from Multiplafrom projects, but it does not include tasks like `check` fun isTestingTask(name: String) = name.endsWith("Test") val isTesting = gradle .startParameter .taskNames .any(::isTestingTask) if (isTesting) allOpen { /* ... */ } ``` -------------------------------- ### Create a Mock Object Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Use the `mock` function to create a mock instance of a given type. If a member function without defined behavior is called, it will result in a runtime error by default. ```kotlin val foo = mock() ``` -------------------------------- ### Configure Default Verify Mode Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx Set the default `VerifyMode` globally in your `build.gradle` file to apply it to all verifications unless overridden. ```kotlin import dev.mokkery.verify.VerifyMode.exhaustiveOrder mokkery { defaultVerifyMode.set(exhaustiveOrder) } ``` -------------------------------- ### Mock Mode: Autofill Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Returns default empty values for missing answers (e.g., 0 for numbers, "" for strings, null for complex types). ```kotlin import dev.mokkery.MockMode.autofill val foo = mock(autofill) ``` -------------------------------- ### Mocking Member Functions with Context Parameters Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx To mock member functions with context parameters, use the `ctx` function within `every`, specifying the context type and a lambda for the function call. Ensure `dev.mokkery.templating.ctx` is imported. ```kotlin import dev.mokkery.templating.ctx // ... every { ctx(any()) { foo.getAllWithContext() } } returns listOf(1, 2, 3) context(FooContext()) { foo.getAllWithContext() // returns listOf(1, 2, 3) } ``` -------------------------------- ### Apply Mokkery to All Source Sets Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Configure Mokkery to apply to all source sets within the current subproject using `ApplicationRule.All`. Useful when mocks need to be extracted to a separate subproject. ```kotlin mokkery { rule.set(ApplicationRule.All) } ``` -------------------------------- ### Define Answers for Specific Parameters Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Configure behavior for specific parameter values of a member function. Calls with parameters not explicitly defined will result in an error. ```kotlin every { foo.getAt(0) } returns 1 every { foo.getAt(1) } returns 2 foo.getAt(0) // returns 1 foo.getAt(1) // returns 2 foo.getAt(2) // error - answer not defined ``` -------------------------------- ### Create a Spy from an Object Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Spying.mdx Use the `spy` function with the real object as a parameter. It's crucial to specify the type for the spy to avoid issues with final classes. ```kotlin val foo = FooImpl() val spiedFoo = spy(foo) ``` -------------------------------- ### Define Behavior for Member Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Use the `every` function to define the return value for regular member functions. For properties, call the getter or setter within `every`. ```kotlin every { foo.getAll() } returns listOf(1, 2, 3) ``` ```kotlin // getter every { foo.values } returns listOf(1, 2, 3) // setter every { foo.values = any() } returns Unit ``` -------------------------------- ### Nest `sequentially` Calls Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx You can nest `sequentially` blocks to create more complex sequences of answers, allowing for hierarchical control over mock responses. ```kotlin every { mock.getAt(any()) } sequentially { returns(0) sequentially { returns(1) returns(2) } returns(3) } ``` -------------------------------- ### Registering AutofillProvider for Value Classes in WASM Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx For WASM, custom value classes require registering an AutofillProvider that supplies an empty value. This is necessary when the value class is not from the standard library. ```kotlin AutofillProvider.forInternals.types.register { ValueClass(null) } ``` -------------------------------- ### Capture Multiple Arguments with Container Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Employ `Capture.container` to store all values of an argument that match the definition, even across multiple calls. ```kotlin val container = Capture.container() // stores multiple values every { mock.getAtOrDefault(index = any(), default = any()) } returns 0 every { mock.getAtOrDefault(index = capture(container), default = 10) } returns 0 every { mock.getAtOrDefault(index = 3, default = any()) } returns 0 mock.getAtOrDefault(index = 1, default = 10) // `index` arg is captured mock.getAtOrDefault(index = 2, default = 20) // `default` parameter does not match - argument is not captured mock.getAtOrDefault(index = 3, default = 10) // answer defined later is selected here - argument is not captured println(container.values) // prints [1] ``` -------------------------------- ### Await Sending to a Channel for Unit Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx For `Unit`-returning suspendable functions, use `Awaitable.send` to mock sending an element to a `Channel`. This is useful for testing functions that produce data. ```kotlin import dev.mokkery.coroutines.answering.Awaitable.Companion.send val channel = Channel() everySuspend { mock.insert(any()) } awaits send(to = channel) { it.arg(0) } ``` -------------------------------- ### Create a Mock of Multiple Types Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking_multiple_types.mdx Use `mockMany` to instantiate a mock object that implements multiple specified types. This function accepts up to five types. ```kotlin val mock = mockMany() ``` -------------------------------- ### Log Mock Calls with MokkeryCallLogger (Global Scope) Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Debugging.mdx For quick debugging, you can register `MokkeryCallLogger` globally with `MokkeryCallInterceptor.beforeAnswering`. Be mindful that this affects all subsequent tests. ```kotlin MokkeryCallInterceptor.beforeAnswering.register(MokkeryCallLogger()) ``` -------------------------------- ### Match Varargs with Any Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Use the `any()` matcher with the spread operator to match any arguments within a vararg. ```kotlin everySuspend { mock.insertAll(1, *any(), 3) } returns 0 ``` -------------------------------- ### Call Original Implementation Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `calls original` to invoke the original function implementation. This is the most straightforward method. ```kotlin every { mock.getAt(any()) } calls original mock.getAt(2) // this calls original function implementation with 2 ``` -------------------------------- ### Shorthand for Repeating Sequences with `sequentiallyRepeat` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `sequentiallyRepeat` as a concise way to define a sequence of answers that should repeat indefinitely. ```kotlin every { mock.getAt(any()) } sequentiallyRepeat { returns(0) returns(1) } ``` -------------------------------- ### Call Original Implementation with Arguments Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `calls originalWith(args)` to invoke the original function implementation with specific arguments. The arguments provided to `originalWith` will be used instead of the arguments passed to the mocked function. ```kotlin every { mock.getAt(any()) } calls originalWith(3) mock.getAt(2) // this calls original function implementation with 3 ``` -------------------------------- ### Define a Constant Answer with `returns` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `returns` to specify a constant value that the mock should return. ```kotlin every { mock.getAt(index = any()) } returns 100 ``` -------------------------------- ### Combine Logical Matchers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Use logical matchers like `or` and `not` to create complex argument matching conditions. ```kotlin every { mock.getAt(or(1, not(2))) } returns 10 ``` -------------------------------- ### Apply Mokkery to Source Sets Matching Regex Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Apply Mokkery to source sets whose names match a given regular expression using `ApplicationRule.MatchesName`. Ensure all source sets within a subtree are included. ```kotlin ApplicationRule.MatchesName(Regex(".+Main")) ``` -------------------------------- ### Await Multiple Deferreds with `all` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Use `Awaitable.all` to mock a suspendable function that should return results from multiple `Deferred` instances. The results are collected as a list. ```kotlin import dev.mokkery.coroutines.answering.Awaitable.Companion.all val deferred1 = CompletableDeferred() val deferred2 = CompletableDeferred() val deferred3 = CompletableDeferred() everySuspend { mock.fetchAll() } awaits all(deferred1, deferred2, deferred3) ``` -------------------------------- ### Define Answer for Member Function Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Use the `every` function to define the return value for a regular member function call. ```kotlin every { foo.getAll() } returns listOf(1, 2, 3) ``` -------------------------------- ### Mock Mode: Strict Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx The default mode that throws a runtime exception when a missing answer is encountered. Ensure all behaviors are defined. ```kotlin import dev.mokkery.MockMode.strict val foo = mock(strict) ``` -------------------------------- ### Define Custom String Regex Matcher Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Create a custom matcher for strings that checks if the string matches a given regex. ```kotlin fun MokkeryMatcherScope.regex( regex: Regex ): String = matches(toString = { "regex(\"$regex\")" }, predicate = regex::matches) ``` -------------------------------- ### Unified Answer for Blocking and Suspend Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Define a convenience extension for answers applicable to both regular and suspend functions. This ensures consistency by using `AnsweringScope` as the receiver. ```kotlin infix fun AnsweringScope.returns(value: T) { answers(ReturnsAnswer(value)) } private class ReturnsAnswer(private val value: T) : Answer { public fun call(scope: MokkeryBlockingCallScope): T = value public suspend fun call(scope: MokkerySuspendCallScope): T = value } ``` ```kotlin // Usage: everySuspend { mock.fetchAt(any()) } returns 10 // suspend every { mock.getAt(any()) } returns 10 // regular // ✅ both compile ``` -------------------------------- ### Using verifyNoMoreCalls with MokkerySuiteScope Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Strict_exhaustiveness.mdx Utilize the `verifyNoMoreCalls` extension provided by `MokkerySuiteScope` to automatically check for unverified calls after test execution. ```kotlin class ClassTest : MokkerySuiteScope { private val a = mock() private val b = mock() @Test fun test() { a.call(1) b.call(2) } @AfterTest fun after() { // fails after `test` - 2 unverified calls verifyNoMoreCalls() } } ``` -------------------------------- ### Define Answer for Property Setter Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Define the behavior for a property's setter using `every`. It typically returns `Unit`. ```kotlin // setter every { foo.values = any() } returns Unit ``` -------------------------------- ### Exhaustive Order Verification Mode Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx `VerifyMode.exhaustiveOrder` verifies that all calls occurred in the exact same sequence as specified in the verification block. No extra calls are allowed. ```kotlin mock.getAt(1) mock.getAt(2) mock.getAll() verify(exhaustiveOrder) { mock.getAt(any()) mock.getAt(any()) mock.getAll() // ✅ - each call matches } ``` -------------------------------- ### Return `Result.success` with `returnsSuccess` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `returnsSuccess` to explicitly return a `Result.success` value for functions that return `Result`. ```kotlin every { mock.getAtCatching(index = 0) } returnsSuccess 1 ``` -------------------------------- ### Correct: Using `eq` with Composite Matchers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx To correctly use composite matchers with literal values, wrap each literal with an explicit matcher like `eq`. ```kotlin every { foo.getAt(or(eq(1), eq(2))) } returns 10 ``` -------------------------------- ### Synchronize Side Effects with atomic-fu Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Thread_safety.mdx Use atomic-fu to synchronize non-thread-safe side effects in mock configurations, especially in older Mokkery versions. ```kotlin var x = atomic(0) every { mock.getAndIncrement() } calls { x.getAndIncrement() } ``` -------------------------------- ### Shorthand for Sequential Returns with `sequentiallyReturns` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `sequentiallyReturns` to provide a list of values that will be returned in sequence. The mock fails if the list is exhausted. ```kotlin every { mock.getAt(any()) } sequentiallyReturns listOf(0, 1) ``` -------------------------------- ### Call Spied Implementation with Arguments Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `callSpiedWith(args)` to invoke the spied function with specific arguments. This allows you to override the arguments passed to the original spied method. ```kotlin every { spy.getAt(any()) } calls { // ... callSpiedWith(3) } ``` -------------------------------- ### Restrictions in Every and Verify Blocks Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx Code within `every` and `verify` blocks cannot be extracted into separate functions due to compiler plugin transformations. Block parameters must be lambda expressions. ```kotlin private val foo = mock() @Test fun test() { // ... verify { extracted() } } private fun MokkeryMatcherScope.extracted() { foo.getAll() } ``` ```kotlin private val foo = mock() @Test fun test() { // ... extracted() } private fun extracted() { verify { foo.getAll() } } ``` -------------------------------- ### Soft Verification with Call Count Restrictions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx Use `atMost`, `atLeast`, `exactly`, or `inRange` with soft modes to restrict the number of expected calls. ```kotlin mock.getAt(1) mock.getAt(2) mock.getAll() verify(atMost(1)) { mock.getAt(any()) // ❌ - 2 matching calls, but expected 1 at most } ``` -------------------------------- ### Await Receiving from a Channel Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Use `Awaitable.receive` to mock a suspendable function that should wait for and return an element from a `Channel`. Specify the channel to receive from. ```kotlin import dev.mokkery.coroutines.answering.Awaitable.Companion.receive val channel = Channel>() everySuspend { mock.fetchAll() } awaits receive(from = channel) ``` -------------------------------- ### Verify Function Calls Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Use the `verify` function to assert that specific member functions have been called. This is performed on unverified calls, meaning repeated verifications might yield different results. ```kotlin verify { foo.getAll() } ``` -------------------------------- ### Define Answer for Property Getter Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Define the return value for a property's getter using `every`. ```kotlin // getter every { foo.values } returns listOf(1, 2, 3) ``` -------------------------------- ### Apply Mokkery Gradle Plugin (Kotlin 2.3.20) Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Apply the Mokkery Gradle plugin for Kotlin version 2.3.20. Ensure your Kotlin plugin version is compatible. ```kotlin plugins { kotlin("multiplatform") version "2.3.20" // ...or any other Kotlin plugin id("dev.mokkery") version "3.3.0" } ``` -------------------------------- ### Call Superclass Implementation with Arguments Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `superWith(args)` to call a specific superclass implementation with modified arguments. This allows you to control which superclass's method is invoked and with what parameters. ```kotlin val mock = mockMany { every { t1.sharedFunction(any()) } calls superWith(3) } mock.t1.sharedFunction(2) // this calls function implementation from A with 3 ``` -------------------------------- ### Print Mock State with printMokkeryDebug Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Debugging.mdx Use `printMokkeryDebug` to output the internal state of a mock. This is useful for understanding how a mock is configured and what calls it has received. ```kotlin val mock = mock() // ... printMokkeryDebug(mock) ``` -------------------------------- ### Configure Mock Behavior within a Mock Block Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx You can group behavior configurations for a mock object within a `mock` block, applying settings like `autoUnit` and defining multiple `every` and `everySuspend` calls. ```kotlin val mock = mock(autoUnit) { every { getAll() } returns listOf(1, 2, 3) everySuspend { fetchAll() } returns listOf(1, 2, 3) } ``` -------------------------------- ### Throw an Exception with `throws` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `throws` to make the mock throw a specified exception. ```kotlin every { mock.getAt(index = any()) } throws IllegalArgumentException() ``` -------------------------------- ### Provide Complex Answer with `calls` for Regular Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `calls` with a lambda to define a custom answer for regular functions. The lambda receives the function's arguments and returns the desired value. ```kotlin every { mock.getAt(index = any()) } calls { (index: Int) -> index + 1 } ``` -------------------------------- ### Capture Varargs with Spread Operator Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Capture all elements of a vararg parameter using `capture` with the spread operator. ```kotlin val slot = Capture.slot>() everySuspend { mock.insertAll(*capture(slot)) } returns 1 mock.insertAll(1, 2, 3) // slot contains intArrayOf(1, 2, 3) ``` -------------------------------- ### Independent Soft Verifications Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx Each verification in soft mode is independent. Duplicating patterns within a single `verify` block in soft mode has no additional effect. ```kotlin mock.getAll() mock.getAll() verify { mock.getAll() // ✅ - `getAll` was called at least once } verify { mock.getAll() mock.getAll() // ✅ - `getAll` was called at least once // the only difference is that `getAll` check is duplicated } ``` -------------------------------- ### Repeat Answers in a Sequence with `repeat` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Within a `sequentially` block, use `repeat` to define a sub-sequence of answers that will be repeated after the initial sequence is exhausted. ```kotlin every { mock.getAt(any()) } sequentially { returns(0) repeat { returns(1) } } ``` -------------------------------- ### Apply Mokkery Gradle Plugin (Kotlin 1.9.25) Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Apply the Mokkery Gradle plugin for Kotlin version 1.9.25. Ensure your Kotlin plugin version is compatible. ```kotlin plugins { kotlin("multiplatform") version "1.9.25" // ...or any other Kotlin plugin id("dev.mokkery") version "1.9.25-1.7.0" } ``` -------------------------------- ### Throw Exception Provided by a Function with `throwsBy` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `throwsBy` to throw an exception that is dynamically provided by a function reference. A new exception instance is created on each invocation. ```kotlin every { mock.getAt(any()) } throwsBy ::IllegalStateException ``` -------------------------------- ### Define a Sequence of Answers with `sequentially` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `sequentially` to define a series of answers that will be returned in order for successive calls to the mock. The sequence repeats or fails if exhausted. ```kotlin every { mock.getAt(any()) } sequentially { returns(0) calls { 1 } throws(IllegalStateException()) } ``` -------------------------------- ### Return a Specific Argument with `returnsArgAt` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `returnsArgAt` to return an argument passed to the mocked function. The argument's index is specified. ```kotlin every { mock.getAt(index = any()) } returnsArgAt 0 ``` -------------------------------- ### Mock Mode: Original Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Calls the super implementation if available (default implementation for interfaces). Otherwise, it fails. This is useful for mocking types that rely heavily on default behavior. ```kotlin import dev.mokkery.MockMode.original val foo = mock(original) ``` -------------------------------- ### Define Suspend and Blocking Answer Scopes Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx These marker interfaces differentiate between regular and suspend function contexts for compile-time safety. ```kotlin public interface SuspendAnsweringScope : AnsweringScope public interface BlockingAnsweringScope : AnsweringScope ``` -------------------------------- ### Match Varargs with Composite Matchers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Combine spread operator usage with logical matchers for flexible vararg matching. ```kotlin everySuspend { mock.insertAll(*any()) } returns 1 ``` ```kotlin everySuspend { mock.insertAll(*not(containsAllElements { it == "2" })) } returns 2 ``` -------------------------------- ### Add Mokkery Gradle Plugin Dependency Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Setup.mdx Add the Mokkery Gradle plugin as an implementation dependency. Replace `$mokkeryVersion` with the actual version. ```kotlin dependencies { implementation("dev.mokkery:mokkery-gradle:$mokkeryVersion") } ``` -------------------------------- ### Set Default Mock Mode Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Configure the default `MockMode` for all subsequent mocks using the `defaultMockMode` option within the `mokkery` block. ```kotlin import dev.mokkery.MockMode mokkery { defaultMockMode.set(MockMode.autoUnit) } ``` -------------------------------- ### Return Value Provided by a Function with `returnsBy` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `returnsBy` to return a value that is dynamically provided by a function reference. The mock will call this function each time it's invoked. ```kotlin every { mock.getAt(any()) } returnsBy ::number ``` -------------------------------- ### Repeated Verifications Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx Each verification is performed on unverified calls. Repeated verifications of the same call may fail if the call has already been marked as verified. ```kotlin mock.getAt(1) verify { mock.getAt(1) } // ✅ verify { mock.getAt(1) } // ❌ - no matching calls ``` -------------------------------- ### Return `Result.failure` with `returnsFailure` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `returnsFailure` to explicitly return a `Result.failure` with a specified exception for functions that return `Result`. ```kotlin every { mock.getAtCatching(index = 30) } returnsFailure IndexOutOfBoundsException() ``` -------------------------------- ### Await a Deferred Created by a Lambda Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Mock a suspendable function by providing a lambda that creates and returns a `Deferred` value. This is useful when the `Deferred` needs to be constructed based on arguments. ```kotlin everySuspend { mock.fetchAt(any()) } awaits { (index: Int) -> createDeferred(index) } ``` -------------------------------- ### Mock Mode: AutoUnit Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Similar to strict mode, but it does not throw an exception for functions that return Unit. Useful for ignoring side effects. ```kotlin import dev.mokkery.MockMode.autoUnit val foo = mock(autoUnit) ``` -------------------------------- ### Call Spied Implementation Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `callSpied()` within the `calls` scope to invoke the real implementation of a spied object. This is useful when you want to add behavior around the original spied method. ```kotlin every { spy.getAt(any()) } calls { // ... callSpied() } ``` -------------------------------- ### Generate Mock Debug String Manually Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Debugging.mdx Create a debug string representation of a mock using `mokkeryDebugString` for custom processing or logging. ```kotlin val debugString = mokkeryDebugString(mock) ``` -------------------------------- ### Mocking with Type Casting and Member Access Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking_multiple_types.mdx When mocking multiple types, you need to use `tN` extensions for explicit casting to access members of specific types within the mock. This is useful for setting up behavior for functions defined in each individual type. ```kotlin val mock = mockMany { // t1 extension casts to A every { t1.functionFromA() } returns Unit // t2 extension casts to B every { t2.functionFromB() } returns Unit // t3 extension casts to C every { t3.functionFromC() } returns Unit } val foo = Foo(a = mock.t1) ``` -------------------------------- ### Define Custom AnyOf Matcher Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Implement a generic custom matcher to check if an argument is present in a vararg of values. ```kotlin fun MokkeryMatcherScope.eqAnyOf( vararg values: T ): T = matches( toString = { "eqAnyOf(\"${values.contentToString()}\")" }, predicate = { values.contains(it) } ) ``` -------------------------------- ### Allowed: Varargs with Explicit Matchers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx When passing varargs as an array, ensure that literals are explicitly matched using functions like `eq` to avoid ambiguity. ```kotlin everySuspend { foo.insertAll(numbers = intArrayOf(eq(1), *anyVarargsInt(), eq(3))) } returns 0 ``` ```kotlin everySuspend { foo.insertAll(numbers = intArrayOf(eq(1), any())) } returns 0 ``` -------------------------------- ### Illegal: Assigning Matchers to Variables Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx In Mokkery 1 and 2, matchers cannot be assigned to variables before being used in an `every` block. This is a common pitfall to avoid. ```kotlin every { val matcher = any() foo.getAt(matcher) } returns 1 ``` -------------------------------- ### Await with a Custom Delay and Lambda Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Use `Awaitable.delayed` with a custom delay duration and a lambda to compute the return value. The lambda receives arguments passed to the mocked function. ```kotlin import dev.mokkery.coroutines.answering.Awaitable.Companion.delayed everySuspend { mock.fetchAt(any()) } awaits delayed(by = 2.seconds) { (index: Int) -> index + 1 } ``` -------------------------------- ### Type Specification for Mock and Spy Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx When using `spy` and `mock`, the type must be directly specified. Generic type inference is not supported in this context. ```kotlin inline fun myMock() = mock() ``` ```kotlin fun myListMock() = mock>() ``` -------------------------------- ### Provide Complex Answer with `calls` for Suspend Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `calls` with a lambda for suspend functions. Suspension is allowed within the lambda, enabling asynchronous operations like `delay`. ```kotlin everySuspend { mock.fetchAt(index = any()) } calls { delay(1_000) // suspension is allowed here! index + 1 } ``` -------------------------------- ### Custom Answer Interface Definition Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Defines the `Answer` interface, which represents custom behavior for mocked calls. It includes methods for both blocking and suspend functions. ```kotlin @DelicateMokkeryApi public interface Answer { public fun call(scope: MokkeryBlockingCallScope): T public suspend fun call(scope: MokkerySuspendCallScope): T } ``` -------------------------------- ### Manual Exhaustiveness Check Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx Use `verifyNoMoreCalls` to manually check if all calls made to a mock have been verified. This is useful after using soft verification modes. ```kotlin mock.getAt(1) mock.getAll() verify(soft) { mock.getAt(1) // ✅ } verifyNoMoreCalls(mock) // ❌ - `getAll` was not verified! ``` -------------------------------- ### Add mokkery-coroutines Dependency Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Include the `mokkery-coroutines` module in your project dependencies to use coroutine-specific features. This can be done via Gradle or the Mokkery Gradle plugin. ```kotlin dependencies { implementation("dev.mokkery:mokkery-coroutines:$version") } ``` ```kotlin import dev.mokkery.gradle.mokkery dependencies { implementation(mokkery("coroutines")) // defaults to the current Mokkery version } ``` -------------------------------- ### Answering Scope Interface Definition Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Defines the `AnsweringScope` interface, which provides the `answers` function to register a custom `Answer` for a mocked call. Both `answers` and the `Answer` interface are marked as delicate due to potential misuse. ```kotlin // ... public interface AnsweringScope { @DelicateMokkeryApi public infix fun answers(answer: Answer) } ``` -------------------------------- ### Call Superclass Implementation with Ambiguity Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx When mocking multiple types and facing ambiguity with `original`, use `superOf()` to specify which supertype's implementation to call. This is necessary when a function exists in multiple supertypes. ```kotlin val mock = mockMany { every { t1.sharedFunction(any()) } calls superOf() } mock.t1.sharedFunction(2) // this calls function implementation from A with 2 ``` -------------------------------- ### Configure Annotation Copying Behavior Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Control which annotations are copied from the original type to the mock using `copyToMock` with various selectors. ```kotlin import dev.mokkery.options.AnnotationSelector.Companion.all import dev.mokkery.options.AnnotationSelector.Companion.none import dev.mokkery.options.AnnotationSelector.Companion.named import dev.mokkery.options.AnnotationSelector.Companion.matches mokkery { annotations { // No annotations copyToMock = none // All annotations except "example.A" copyToMock = all - named("example.A") // Only "example.A" copyToMock = named("example.A") // All annotations matching the regex "internal.*" copyToMock = matches(Regex("internal.*\"")) // Combine rules: all except "example.A" and all annotations starting with "internal" copyToMock = all - named("example.A") - matches(Regex("internal.*\"")) } } ``` -------------------------------- ### Match Varargs with Custom Predicate Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Define a custom predicate for the spread operator to match varargs based on array size. ```kotlin everySuspend { mock.insertAll(1, *matches { it.size == 2 }, 3) } returns 0 ``` -------------------------------- ### Define Behavior for Suspending Functions Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Use `everySuspend` to define the return value for suspending member functions. This function itself is not suspending, allowing configuration in non-suspending contexts. ```kotlin everySuspend { foo.fetchAll() } returns listOf(1, 2, 3) ``` -------------------------------- ### Resetting Registered Calls Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx Use `resetCalls` to clear all recorded calls for a mock. Subsequent verifications will not find any previously recorded calls. ```kotlin mock.getAt(1) resetCalls(mock) verify(soft) { mock.getAt(1) // ❌ - registered calls were removed with `resetCalls` } ``` -------------------------------- ### Await with a Fixed Delay Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Use `Awaitable.delayed` to mock a suspendable function that should return a value after a default delay of 1 second. The `value` parameter specifies the return value. ```kotlin import dev.mokkery.coroutines.answering.Awaitable.Companion.delayed everySuspend { mock.fetchAt(any()) } awaits delayed(value = 10) // by default, the delay takes 1 second. ``` -------------------------------- ### Capture Argument with Conditional Matcher Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Capture an argument only if it satisfies a specific matcher, like `not(1)`. ```kotlin val slot = Capture.slot() every { mock.getAt(capture(slot, not(1))) } returns 0 mock.getAt(2) println(slot.get()) // prints 2 mock.getAt(1) // fails - no answer provided for arg 1 ``` -------------------------------- ### Log Mock Calls with MokkeryCallLogger (Test Class Scope) Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Debugging.mdx Register `MokkeryCallLogger` using `MokkeryCallInterceptor.beforeAnswering` within `@BeforeTest` and `@AfterTest` to log calls only for the duration of a specific test class. ```kotlin private val logger = MokkeryCallLogger() @BeforeTest fun before() { MokkeryCallInterceptor.beforeAnswering.register(logger) } @AfterTest fun after() { MokkeryCallInterceptor.beforeAnswering.unregister(logger) } ``` -------------------------------- ### Match Varargs with Array Matchers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Utilize array-specific matchers like `containsAllInts` with the spread operator for vararg matching. ```kotlin everySuspend { mock.insertAll(1, *containsAllInts { it != 2 }, 3) } returns 0 ``` -------------------------------- ### Soft Verification Mode Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx The default `VerifyMode.soft` checks if calls in the verification block happened and marks matching calls as verified. It does not check for unverified calls. ```kotlin mock.getAt(1) mock.getAt(2) mock.getAll() verify { mock.getAt(any()) // ✅ `getAt(1)` and `getAt(2)` are marked as verified. } ``` -------------------------------- ### Await a Deferred Value Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Coroutines.mdx Use the `awaits` overload to mock a suspendable function that returns a `Deferred`. The provided `Deferred` will be returned directly. ```kotlin val deferred = CompletableDeferred() everySuspend { mock.fetchAt(any()) } awaits deferred ``` -------------------------------- ### Verify Suspending Function Calls Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Quick_start.mdx Employ `verifySuspend` to verify that suspending member functions have been invoked. Similar to `verify`, it operates on unverified calls. ```kotlin verifySuspend { foo.fetchAll() } ``` -------------------------------- ### Illegal: Using Literals with Composite Matchers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx When using composite matchers like `or` that accept other matchers, literals are not permitted. Use explicit matchers such as `eq` instead. ```kotlin every { foo.getAt(or(1, 2)) } returns 10 ``` -------------------------------- ### Handling Shared Functions in Multiple Type Mocks Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking_multiple_types.mdx If different types share functions with identical signatures, they are treated as a single function within the mock. Mocking the shared function via one type's `tN` extension will affect all types that share that function. ```kotlin val mock = mockMany { every { t1.sharedFunction(any()) } returns "Hello world!" } // ... mock.t2.sharedFunction(1) // returns "Hello world!" ``` -------------------------------- ### Capture Single Argument with Slot Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Matchers.mdx Use `Capture.slot` to capture the latest value of a specific argument passed to a mocked method. ```kotlin val slot = Capture.slot() // stores only the latest value every { mock.getAt(capture(slot)) } returns 1 mock.getAt(1) println(slot.get()) // prints 1 ``` -------------------------------- ### Exhaustive Verification Mode Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Verifying.mdx `VerifyMode.exhaustive` acts like soft mode but also checks if all calls made within the verification block have been verified. It does not check calls outside the block. ```kotlin mock.getAt(1) mock.getAt(2) mock.getAll() verify(exhaustive) { mock.getAt(any()) // ❌ - `getAll` not verified } ``` -------------------------------- ### Enforcing Strict Exhaustiveness with MokkerySuiteScope Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Strict_exhaustiveness.mdx Implement `MokkerySuiteScope` in your test class to enable stricter exhaustiveness checks. This will cause verification to fail if unverified calls exist. ```kotlin class ClassTest : MokkerySuiteScope { private val a = mock() private val b = mock() @Test fun test() { a.call(1) b.call(2) // Verification fails - b.call(2) was not verified verify(exhaustive) { a.call(1) } } } ``` -------------------------------- ### Reset Mock Answers Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Mocking.mdx Use `resetAnswers` to clear all defined behaviors for a specific mock object. After resetting, calls to its members will result in errors if no new answers are defined. ```kotlin every { foo.getAt(0) } returns 1 resetAnswers(mock) foo.getAt(0) // error - answer not defined ``` -------------------------------- ### Handle Complex `Result` Answers with `callsCatching` Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Guides/Answers.mdx Use `callsCatching` for functions returning `Result`. The lambda defines the logic to produce either a success or failure `Result` based on input. ```kotlin every { mock.getAtCatching(any()) } callsCatching { if (index < 0) error("Negative index not allowed!") index + 1 } ``` -------------------------------- ### Illegal: Varargs Ambiguity with Matchers and Literals Source: https://github.com/lupuuss/mokkery/blob/master/website/docs/Limitations.mdx Passing varargs as an array can lead to ambiguity if matchers are mixed directly with literals. These specific call patterns are prohibited. ```kotlin everySuspend { foo.insertAll(numbers = intArrayOf(1, *anyVarargsInt(), 3)) } returns 0 ``` ```kotlin everySuspend { foo.insertAll(numbers = intArrayOf(1, any())) } returns 0 ```