Mocking static objects under completable future supply async

521 Views Asked by At

Consider below code snippet:

class XYZ {
  public static getFieldABC(){
    return new ABC();
  }
}

...
CompletableFuture.supplyAsync(() -> XYZ.getFieldABC())
...

I need to unit test this piece of code.

I have a static method getFieldABC which returns an object of a particular class ABC. I want to mock this static method call using Mockito.mockStatic and then return mockObject using when().

The catch here is that this method call is under CompletableFuture.supplyAsync. Since, its running in a different thread, the call to the static method, instead of calling the mock, its invoking the actual method call.

1

There are 1 best solutions below

0
On

Assuming the class you want to test looks like this

class ABCSupplier {

    void supply() {

        CompletableFuture.supplyAsync(XYZ::getFieldABC);
    }
}

You can mock statics with Mockito like this:

@ExtendWith(MockitoExtension.class)
class ABCSupplierTest {

    @InjectMocks
    ABCSupplier abcSupplier;

    @Captor
    private ArgumentCaptor<Supplier<ABC>> supplierArgumentCaptor;

    @Test
    void it_should_supply_ABC_field() {

        final ABC abc = new ABC();

        try (var completableFutureMockedStatic = Mockito.mockStatic(CompletableFuture.class);
            var xyzMockedStatic = Mockito.mockStatic(XYZ.class)) {

            xyzMockedStatic.when(XYZ::getFieldABC)
                .thenReturn(abc);

            this.abcSupplier.supply();

            completableFutureMockedStatic.verify(() -> CompletableFuture.supplyAsync(this.supplierArgumentCaptor.capture()));

            Assertions.assertThat(this.supplierArgumentCaptor.getValue().get())
                .isEqualTo(abc);
        }
    }
}