I am trying to understand Mockito and Junit 4. I hava an interface named UserService which has a method named getUserInfo. I have written an implementation class UserServiceImpl to this interface. I am using this getUserInfo method inside another class named UserInfoImpl. Now I am trying to Junit UserInfoImpl by Mocking UserServiceImpl. But instead of going to to the mock method, the call is going to the actual method. I have verified it by adding sysout to the actual method. I am not sure why it is not getting mocked. Can someone please throw some light.
Junit Class
public class Junit4WithMockito {
private UserInfoImpl userInfo;
@Mock
private UserService userService;
@Before
public void setUp() {
System.out.println("Inside Setup");
MockitoAnnotations.initMocks(this);
}
@Test
public void testUserInfoImpl() throws InterruptedException {
String cid="yu444";
userInfo = new UserInfoImpl();
userInfo.setUserService(userService);
when(userService.getUserInfo(cid)).thenReturn(new User("John Doe",33));
Assert.assertEquals("Peter",userInfo.getUserInfo(cid).getUsername());
}
}
UserInfoImpl Class
public class UserInfoImpl implements UserInfo {
private UserService userService;
public UserService getUserService() {
return userService;
}
public void setUserService(UserService userService) {
this.userService = userService;
}
@Override
public User getUserInfo(String username) {
try {
userService = new UserServiceImpl();
return userService.getUserInfo(username);
} catch (InterruptedException e) {
e.printStackTrace();
return null;
}
}
}
****** UserServiceImpl Class which I am trying to mock *********
public class UserServiceImpl implements UserService {
@Override
public User getUserInfo(String username) throws InterruptedException {
System.out.println("Inside the actual Service");
Thread.sleep(5000);
return new User("John Doe",33);
}
}
Error Message Below
CodePudding user response:
You don't usually want to mock an implementation class, especially when there is an interface for it. The point of mocking is that you don't need (or want) the real implementation to be used.
So in your case, your @Mock
should be
@Mock
private UserService userService;
Furthermore, you have this line in UserInfoImpl
:
userService = new UserServiceImpl();
Obviously this replaces whatever instance of UserService
you inject (including the mock). I'm guessing that's a mistake (maybe left around from an earlier attempt) since I can't think of any reason you'd really want to instantiate something that you're injecting.