jeudi 25 juin 2015

PowerMock mock object with generic constructor

I have been banging my head against the wall for a few hours now and can't seem to mock an object correctly to then mock a method call. My code is below:

@RunWith(PowerMockRunner.class)
@PrepareForTest({Dao.class, DeviceEnrollmentService.class})
public class DeviceEnrollmentServiceTest {

    private Dao dao;
    private DeviceEnrollmentService deviceEnrollmentService;

    @Before
    @SuppressWarnings("unchecked")
    public void setup() throws Exception {
        dao = createMockAndExpectNew(Dao.class, new Class[] {Class.class}, DeviceEnrollment.class);

        replay(dao, Dao.class);

        deviceEnrollmentService = spy(new DeviceEnrollmentService(dao));
    }

    @Test
    public void testGetDeviceEnrollmentById() throws Exception {

        expect(dao.get(anyString())).andReturn(new DeviceEnrollment()); //ERROR HERE

        deviceEnrollmentService.getDeviceEnrollmentById("test");
    }
}

And here is the important parts of my Dao class:

public class Dao<T> {

    private Class<T> clazz;

    public Dao(Class<T> clazz){
        this.clazz = clazz;
    }

    public T get(String id) {
        Key<T> key = Key.create(clazz, id);
        return get(key);
    }
}

And finally the important piece of my DeviceEnrollmentService class:

public DeviceEnrollmentService(Dao<DeviceEnrollment> dao){
    this.dao = dao;
}

public DeviceEnrollment getDeviceEnrollmentById(String enrollmentCode) {

    return dao.get(enrollmentCode.toUpperCase());
}

The problem is that I am getting a 'java.lang.AssertionError: Unexpected method call Dao.get(null)' error on the line where my 'expect' is. I have tried other ways to mock my Dao object but it either runs into the same unexpected method call error or calls the .get method of my Dao instead of mocking it. I have tried using a 'replay' and I have also used the exact string of "TEST" instead of anyString but with no luck.

If I don't do the 'expect' line then I get an unexpected method call error on the line where I actually call my .getDeviceEnrollmentById method.

Any help would be greatly appreciated. I am not a testing expert so I don't mind too much if you blast my horrible test.

Aucun commentaire:

Enregistrer un commentaire