Junit+SpringBoot+JpaRepository.saveAndFlush()でmockit.doThrow()を指定してもExceptionが発生しない
前提・実現したいこと
JpaRepository.saveAndFlush()でExceptionが発生した場合のテストを行うためmockit.doThrow()を使用しています。
テストを行いたいメソッド内部でsaveAndFlush()の対象entityのインスタンス作成を行っている場合、saveAndFlush()戻り値がnullとなりExceptionが発生しませんでした。
しかし、saveAndFlush()の対象entityをテストを行いたいメソッドの引数に指定しテストクラスからentityを渡した場合、期待通りExceptionが発生しました。
上記違いでなぜmockit.doThrow()のExceptionが発生しないのかわからないため、ご教授いただけないでしょうか。
Exceptionが発生しないソースコード
@Service
@Transactional(readOnly = true)
public class ServiceImpl implements Service
{
@Autowired
private Repository _repository;
@Override
@Transactional(readOnly = false, rollbackFor = Exception.class)
public boolean insert(String user) throws Exception
{
UserMst userMst = this.setUserMst(user);
try
{
_repository.saveAndFlush(userMst);
}catch(Exception e)
{
return false;
}
return true;
}
private UserMst setUserMst(String user)
{
UserMst userMst = new UserMst();
userMst.setUserId(user);
return userMst;
}
}
@RunWith(SpringRunner.class)
@TestExecutionListeners({
DependencyInjectionTestExecutionListener.class,
DirtiesContextTestExecutionListener.class
})
@DirtiesContext(classMode = DirtiesContext.ClassMode.AFTER_EACH_TEST_METHOD)
public class ServiceImplTest
{
@Mock
private Repository rep;
@InjectMocks
private ServiceImpl service;
@Test
public void testInsertError01()
{
boolean actual = false;
try
{
// TODO:throwされない
doThrow(new NullPointerException()).when(rep).saveAndFlush(new UserMst());
actual = service.insert("user");
}catch(Exception e)
{
}
assertThat(actual).isEqualTo(false); // 結果がtrueとなるためNG
}
}
Exceptionが発生したソースコード
@Service
@Transactional(readOnly = true)
public class ServiceImpl implements Service
{
@Autowired
private Repository _repository;
@Override
@Transactional(readOnly = false, rollbackFor = Exception.class)
public boolean insert(UserMst userMst) throws Exception
{
userMst.setUserId(user);
try
{
_repository.saveAndFlush(userMst);
}catch(Exception e)
{
return false;
}
return true;
}
}
@RunWith(SpringRunner.class)
@TestExecutionListeners({
DependencyInjectionTestExecutionListener.class,
DirtiesContextTestExecutionListener.class
})
@DirtiesContext(classMode = DirtiesContext.ClassMode.AFTER_EACH_TEST_METHOD)
public class ServiceImplTest
{
@Mock
private Repository rep;
@InjectMocks
private ServiceImpl service;
@Test
public void testInsertError01()
{
UserMst userMst = new UserMst();
boolean actual = false;
try
{
// TODO:throwされた
doThrow(new NullPointerException()).when(rep).saveAndFlush(userMst);
actual = service.insert(userMst);
}catch(Exception e)
{
}
assertThat(actual).isEqualTo(false); // 結果がfalseでOK
}
}
上記質問はteratailでも投稿しています。
https://teratail.com/questions/202524
※teratailで回答・解決があった場合は、stackoverflowにも記載します。