Search code examples
javaunit-testingmockito

Mockito: InvalidUseOfMatchersException


I have a command line tool that performs a DNS check. If the DNS check succeeds, the command proceeds with further tasks. I am trying to write unit tests for this using Mockito. Here's my code:

public class Command() {
    // ....
    void runCommand() {
        // ..
        dnsCheck(hostname, new InetAddressFactory());
        // ..
        // do other stuff after dnsCheck
    }

    void dnsCheck(String hostname, InetAddressFactory factory) {
        // calls to verify hostname
    }
}

I am using InetAddressFactory to mock a static implementation of the InetAddress class. Here's the code for the factory:

public class InetAddressFactory {
    public InetAddress getByName(String host) throws UnknownHostException {
        return InetAddress.getByName(host);
    }
}

Here's my unit test case:

@RunWith(MockitoJUnitRunner.class)
public class CmdTest {

    // many functional tests for dnsCheck

    // here's the piece of code that is failing
    // in this test I want to test the rest of the code (i.e. after dnsCheck)
    @Test
    void testPostDnsCheck() {
        final Cmd cmd = spy(new Cmd());

        // this line does not work, and it throws the exception below:
        // tried using (InetAddressFactory) anyObject()
        doNothing().when(cmd).dnsCheck(HOST, any(InetAddressFactory.class));
        cmd.runCommand();
    }
}

Exception on running testPostDnsCheck() test:

org.mockito.exceptions.misusing.InvalidUseOfMatchersException: 
Invalid use of argument matchers!
2 matchers expected, 1 recorded.
This exception may occur if matchers are combined with raw values:
    //incorrect:
    someMethod(anyObject(), "raw String");
When using matchers, all arguments have to be provided by matchers.
For example:
    //correct:
    someMethod(anyObject(), eq("String by matcher"));

Any input on how to solve this?


Solution

  • The error message outlines the solution. The line

    doNothing().when(cmd).dnsCheck(HOST, any(InetAddressFactory.class))
    

    uses one raw value and one matcher, when it's required to use either all raw values or all matchers. A correct version might read

    doNothing().when(cmd).dnsCheck(eq(HOST), any(InetAddressFactory.class))