Search code examples
javaspringunit-testingtestingjunit

Argument(s) are different! When testing create method JUnit 5. Why?


Currently, I'm writing unit tests for my personal project. Unfortunately, I faced a specific logic that I can't figure out how to test.

I have a create method, which maps DTOs into entities and saves it using repository. Here is the implementation:

public AruCall create(AruCallDtoRequest dtoRequest) {
    log.info("creating aru call with dto: {}", dtoRequest);
    AruCall aruCall = AruCall.builder()
            .aruRequestsId(dtoRequest.getAruRequestsId())
            .customerMsisdn(dtoRequest.getCustomerMsisdn())
            .callParam(dtoRequest.getCallParam())
            .dopFlag(dtoRequest.getDopFlag())
            .waitCalls(dtoRequest.getWaitCalls())
            .build();
    log.info("built aru call with dto: {}", dtoRequest);
    return aruCallsRepository.save(aruCall);
}

In the test, I'm trying to verify repository.save() method call, but unfortunately, the test returns me "Argument(s) are different!" exception. Here is my TestClass:

@ExtendWith(MockitoExtension.class)
class AruCallServiceImplTest {

    @InjectMocks
    private AruCallsServiceImpl aruCallsService;

    @Mock
    private AruCallsRepository aruCallsRepository;

    @Test
    @DisplayName("Test for creating and saving new AruCall")
    public void test_createdObjectsFieldsAreEqualToDtoFields() {
        aruCallsService.create(AruCallDtoRequest.builder()
                .customerMsisdn("test")
                .callParam("test")
                .aruRequestsId(1L)
                .dopFlag(1)
                .waitCalls(0)
                .build());
        verify(aruCallsRepository).save(AruCall.builder()
                .aruRequestsId(1L)
                .customerMsisdn("test")
                .callParam("test")
                .dopFlag(1)
                .waitCalls(0)
                .build());
    }
}

Any suggestions how to fix or optimize this test?


Solution

  • It is not working because the AruCall object on verify is not the same object as the one that is created inside your service.

    To verify that the object contains the correct values u should use an argument captor:

    var dto = AruCallDtoRequest.builder()
                .customerMsisdn("test")
                .callParam("test")
                .aruRequestsId(1L)
                .dopFlag(1)
                .waitCalls(0)
                .build());
    
    aruCallsService.create(dto);
    
    final ArgumentCaptor<AruCall> captor = ArgumentCaptor.forClass(AruCall.class);
    verify(aruCallsRepository).save(captor.capture());
    
    final AruCall savedAruCall = captor.getValue();
    
    assertThat(savedAruCall.getWaitCalls()).isEqualTo(dto.getWaitCalls())
    // further assertions