CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/maven-org-powermock--powermock-api-mockito

PowerMock API extension for Mockito that enables mocking of static methods, constructors, final classes and methods, private methods, and advanced testing capabilities through bytecode manipulation and custom classloading

Pending
Overview
Eval results
Files

advanced-stubbing.mddocs/

Advanced Stubbing

PowerMock provides enhanced stubbing capabilities that extend beyond standard Mockito when() syntax. These methods are essential for stubbing void methods, private methods, static methods, and scenarios where the standard approach cannot be used due to Java language limitations.

Capabilities

Custom Answer Stubbing

Stub methods with custom Answer implementations for complex return logic or side effects.

static PowerMockitoStubber doAnswer(Answer<?> answer);

Parameters:

  • answer - Custom Answer implementation defining the method behavior

Returns: PowerMockitoStubber for chaining with method selection

Usage Example:

@Test
@PrepareForTest(DatabaseService.class)
public void testCustomAnswer() throws Exception {
    DatabaseService service = spy(new DatabaseService());
    
    doAnswer(new Answer<String>() {
        @Override
        public String answer(InvocationOnMock invocation) throws Throwable {
            Object[] args = invocation.getArguments();
            String query = (String) args[0];
            return "Result for: " + query.toUpperCase();
        }
    }).when(service, "executeQuery", anyString());
    
    String result = service.performSearch("select * from users");
    assertEquals("Result for: SELECT * FROM USERS", result);
}

Exception Stubbing

Stub methods to throw specific exceptions, particularly useful for void methods and error scenario testing.

static PowerMockitoStubber doThrow(Throwable toBeThrown);

Parameters:

  • toBeThrown - The exception to throw when the stubbed method is called

Returns: PowerMockitoStubber for chaining with method selection

Usage Example:

@Test
@PrepareForTest(FileManager.class)
public void testExceptionStubbing() throws Exception {
    FileManager manager = spy(new FileManager());
    
    // Stub private method to throw exception
    doThrow(new IOException("Disk full")).when(manager, "writeToFile", anyString(), anyString());
    
    // Test that exception is properly handled
    assertThrows(FileOperationException.class, () -> {
        manager.saveDocument("document.txt", "content");
    });
}

Real Method Call Stubbing

Stub methods to call their real implementation, useful for partial mocking scenarios.

static PowerMockitoStubber doCallRealMethod();

Returns: PowerMockitoStubber for chaining with method selection

Usage Example:

@Test
@PrepareForTest(MathUtils.class)
public void testCallRealMethod() {
    mockStatic(MathUtils.class);
    
    // Mock one method but call real implementation for others
    when(MathUtils.complexCalculation(anyDouble())).thenReturn(100.0);
    doCallRealMethod().when(MathUtils.class);
    MathUtils.simpleAddition(5, 3);
    
    assertEquals(100.0, MathUtils.complexCalculation(50.0), 0.001);
    assertEquals(8, MathUtils.simpleAddition(5, 3)); // Real implementation
}

Do Nothing Stubbing

Stub void methods to do nothing, overriding default behavior or consecutive call stubbing.

static PowerMockitoStubber doNothing();

Returns: PowerMockitoStubber for chaining with method selection

Usage Example:

@Test
@PrepareForTest(Logger.class)
public void testDoNothing() throws Exception {
    Logger logger = spy(new Logger());
    
    // Stub private void method to do nothing
    doNothing().when(logger, "writeToFile", anyString());
    
    // First call does nothing, second call throws exception
    doNothing().doThrow(new IOException("File locked")).when(logger, "writeToFile", anyString());
    
    logger.log("First message"); // Does nothing
    
    assertThrows(IOException.class, () -> {
        logger.log("Second message"); // Throws exception
    });
}

Return Value Stubbing

Stub methods to return specific values, particularly useful when when() syntax cannot be used.

static PowerMockitoStubber doReturn(Object toBeReturned);
static PowerMockitoStubber doReturn(Object toBeReturned, Object... othersToBeReturned);

Parameters:

  • toBeReturned - The value to return when the stubbed method is called
  • othersToBeReturned - Additional values for consecutive calls

Returns: PowerMockitoStubber for chaining with method selection

Usage Example:

@Test
@PrepareForTest(ConfigurationManager.class)
public void testDoReturn() throws Exception {
    ConfigurationManager manager = spy(new ConfigurationManager());
    
    // Use doReturn when when() would call the real method
    doReturn("mocked-value").when(manager, "getConfigValue", "key");
    
    // Multiple return values for consecutive calls
    doReturn("first", "second", "third").when(manager, "getNextValue");
    
    assertEquals("mocked-value", manager.getProperty("key"));
    assertEquals("first", manager.getNext());
    assertEquals("second", manager.getNext());
    assertEquals("third", manager.getNext());
}

PowerMockitoStubber Interface Methods

The PowerMockitoStubber interface extends Mockito's Stubber with additional capabilities for static and private methods:

interface PowerMockitoStubber extends Stubber {
    void when(Class<?> classMock);
    <T> PrivatelyExpectedArguments when(T mock, Method method) throws Exception;
    <T> void when(T mock, Object... arguments) throws Exception;
    <T> void when(T mock, String methodToExpected, Object... arguments) throws Exception;
    <T> PrivatelyExpectedArguments when(Class<T> classMock, Method method) throws Exception;
    <T> void when(Class<T> classMock, Object... arguments) throws Exception;
    <T> void when(Class<T> classMock, String methodToExpected, Object... parameters) throws Exception;
}

Common Patterns

Stubbing Static Void Methods

@Test
@PrepareForTest(SystemLogger.class)
public void testStaticVoidMethodStubbing() {
    mockStatic(SystemLogger.class);
    
    // Stub static void method to throw exception
    doThrow(new RuntimeException("Logging failed")).when(SystemLogger.class);
    SystemLogger.log(eq("ERROR"), anyString());
    
    ServiceManager manager = new ServiceManager();
    
    assertThrows(ServiceException.class, () -> {
        manager.handleError("Critical error occurred");
    });
}

Consecutive Behavior Stubbing

@Test
@PrepareForTest(NetworkService.class)
public void testConsecutiveBehavior() throws Exception {
    NetworkService service = spy(new NetworkService());
    
    // First call succeeds, second fails, third succeeds again
    doReturn("success")
        .doThrow(new NetworkException("Connection timeout"))
        .doReturn("retry success")
        .when(service, "attemptConnection", anyString());
    
    assertEquals("success", service.connect("server1"));
    assertThrows(NetworkException.class, () -> service.connect("server1"));
    assertEquals("retry success", service.connect("server1"));
}

Stubbing Private Methods with Complex Logic

@Test
@PrepareForTest(DataProcessor.class)
public void testComplexPrivateMethodStubbing() throws Exception {
    DataProcessor processor = spy(new DataProcessor());
    
    doAnswer(invocation -> {
        String data = (String) invocation.getArguments()[0];
        if (data.startsWith("PRIORITY")) {
            return data.toUpperCase();
        } else {
            return data.toLowerCase();
        }
    }).when(processor, "transformData", anyString());
    
    String priorityResult = processor.processData("PRIORITY: urgent message");
    String normalResult = processor.processData("Normal message");
    
    assertEquals("PRIORITY: URGENT MESSAGE", priorityResult);
    assertEquals("normal message", normalResult);
}

Stubbing with Side Effects

@Test
@PrepareForTest(CacheManager.class)
public void testSideEffects() throws Exception {
    CacheManager manager = spy(new CacheManager());
    AtomicInteger callCount = new AtomicInteger(0);
    
    doAnswer(invocation -> {
        callCount.incrementAndGet();
        String key = (String) invocation.getArguments()[0];
        return "cached-" + key + "-" + callCount.get();
    }).when(manager, "getCachedValue", anyString());
    
    String first = manager.getValue("key1");
    String second = manager.getValue("key2");
    
    assertEquals("cached-key1-1", first);
    assertEquals("cached-key2-2", second);
    assertEquals(2, callCount.get());
}

Mixed Stubbing Approaches

@Test
@PrepareForTest(SecurityService.class)
public void testMixedStubbing() throws Exception {
    SecurityService service = spy(new SecurityService());
    
    // Use when() for return values
    when(service.validateUser("admin")).thenReturn(true);
    
    // Use doThrow for exceptions
    doThrow(new SecurityException("Access denied")).when(service, "checkPermissions", "guest");
    
    // Use doNothing for void methods
    doNothing().when(service, "logSecurityEvent", anyString());
    
    // Use doAnswer for complex logic
    doAnswer(invocation -> {
        String action = (String) invocation.getArguments()[0];
        return "audit-" + action + "-" + System.currentTimeMillis();
    }).when(service, "generateAuditId", anyString());
    
    assertTrue(service.validateUser("admin"));
    assertThrows(SecurityException.class, () -> service.authorize("guest", "read"));
    String auditId = service.performAction("login");
    assertTrue(auditId.startsWith("audit-login-"));
}

When to Use Advanced Stubbing

Use doAnswer() when:

  • Complex return logic based on input parameters
  • Side effects need to be performed during method execution
  • Method behavior depends on object state or external conditions

Use doThrow() when:

  • Stubbing void methods to throw exceptions
  • Testing error handling and exception propagation
  • Simulating failure scenarios in dependencies

Use doCallRealMethod() when:

  • Partial mocking where most methods should use real implementation
  • Testing method interactions while stubbing only specific behaviors
  • Gradual refactoring where some methods are mocked temporarily

Use doNothing() when:

  • Overriding default behavior of void methods
  • Consecutive stubbing where some calls should be ignored
  • Disabling side effects like logging or notifications in tests

Use doReturn() when:

  • Standard when() syntax would call the real method (spies)
  • Overriding previous exception stubbing
  • Type safety issues with generic return types

Requirements

  • Enhanced stubbing works with both static and instance methods
  • Classes with stubbed methods must be specified in @PrepareForTest annotation
  • Test must use @RunWith(PowerMockRunner.class) or equivalent
  • Stubbing must be configured before the code under test executes
  • PowerMockitoStubber chaining must be completed with appropriate when() method call

Install with Tessl CLI

npx tessl i tessl/maven-org-powermock--powermock-api-mockito

docs

advanced-stubbing.md

constructor-mocking.md

index.md

object-mocking.md

private-methods.md

static-mocking.md

static-verification.md

verification-extensions.md

tile.json