0

I have a class to test named ClassToTest. It calls a CloudService to upload file.

public class ClassToTest {
    public String moveFilesToCloud(String path, String documentclass, String objStore) {
        log.info("Moving files to cloud.");
        String docId = StringUtils.EMPTY;
        CloudService service = new CloudService();
        try {
            docId = service.uploadDocument(path,documentclass,objStore,"");
        } catch (CloudException e) {
            log.info("* Error uploading reports to cloud *" + e.getMessage());
        }
        return docId;
    }
}

Below is the test class. The test class has a mocked object for CloudService. When I run the test instead of getting the mocked object, the actual CloudService is executed and fails.

@Mock
CloudService cloudService;

@InjectMocks
ClassToTest classToTest;

@Test
public void testMoveFilesToCloud() throws Exception {
    String pass = "pass";
    when(cloudService.uploadDocument("abc","def","ghi","")).thenReturn(pass);

    String result = classToTest.moveFilesToCloud("abc","def","ghi");

    assertEquals(result,pass);
}

I am expecting the mocked object for CloudService to be used when executing this line -

CloudService service = new CloudService();

Instead, it is actually trying to create a new instance of CloudService.

Where am I going wrong here?

Andulos
  • 433
  • 6
  • 20
  • Try to use dependency injection. Make CloudService a field of ClassToTest. Change the constructor of ClassToTest to accept a CloudService. Then Mockito is able to inject the mock into ClassToTest in your unit test. – Willem Jan 31 '20 at 22:02

2 Answers2

2

Try to use dependency injection. Make CloudService a field of ClassToTest. Change the constructor of ClassToTest to accept a CloudService. Then Mockito is able to inject the mock into ClassToTest in your unit test.

public class ClassToTest {

    private CloudService service;

    public ClassToTest(CloudService service) {
        this.service = service;
    }

    public String moveFilesToCloud(String path, String documentclass, String objStore) {
        log.info("Moving files to cloud.");
        String docId = StringUtils.EMPTY;
        try {
            docId = service.uploadDocument(path,documentclass,objStore,"");
        } catch (CloudException e) {
            log.info("* Error uploading reports to cloud *" + e.getMessage());
        }
        return docId;
    }
}
Willem
  • 992
  • 6
  • 13
1

This will not work.

If you had used injection, then adding @RunWith(MockitoJUnitRunner.class) would have been useful, but it is not.

If you can use Injection, then do it, otherwise you have to use PowerMockito in order to modify bytecode and produce a mock when invoking a constructor. This can help you

Renato
  • 2,077
  • 1
  • 11
  • 22
  • The relevant part from the link is PowerMockito's `whenNew` functionality combined witht the correct usage of the `PrepareForTest` annotation. – second Jan 31 '20 at 22:35