Прежде всего, убедитесь, что вы различаете модульные тесты и интеграционные тесты .JUnit - это просто инфраструктура, которая помогает вам организовывать и запускать тесты, но вы должны определить объем ваших тестов.
Я предполагаю, что вы заинтересованы в определении unit test CommentService.findAll()
.Что это значит?Это означает, что я проверю, что вызов метода findAll()
приводит к тому, что CommentService вызывает именованный запрос, названный строковой константой FIND_ALL
.
Благодаря внедрению зависимостей и созданию заглушек вы можете легко добиться этого с помощью, например1014 * Mockito , чтобы заглушить EntityManager
.Что касается модульного теста, мы фокусируемся только на бизнес-логике в findAll()
, поэтому я также не буду беспокоиться о проверке поиска службы Comment - проверке того, что служба Comment может быть найдена и подключена к правильному объектуЭкземпляр менеджера входит в объем интеграционного теста, а не модульного теста.
public class MyCommentServiceUnitTest {
CommentService commentService;
EntityManager entityManager;
@Before
public void setUp() {
commentService = new CommentService();
entityManager = mock(EntityManager.class);
commentService.setEm(entityManager); // inject our stubbed entity manager
}
@Test
public void testFindAll() {
// stub the entity manager to return a meaningful result when somebody asks
// for the FIND_ALL named query
Query query = mock(Query.class);
when(entityManager.createNamedQuery(Comment.FIND_ALL, Comment.class)).thenReturn(query);
// stub the query returned above to return a meaningful result when somebody
// asks for the result list
List<Comment> dummyResult = new LinkedList<Comment>();
when(query.getResultList()).thenReturn(dummyResult);
// let's call findAll() and see what it does
List<Comment> result = commentService.findAll();
// did it request the named query?
verify(entityManager).createNamedQuery(Comment.FIND_ALL, Comment.class);
// did it ask for the result list of the named query?
verify(query).getResultList();
// did it return the result list of the named query?
assertSame(dummyResult, result);
// success, it did all of the above!
}
}
С помощью вышеописанного модульного теста я протестировал поведение реализации findAll()
.Модульный тест подтвердил, что правильный именованный запрос получен и что результат, возвращенный именованным запросом, был возвращен вызываемому объекту.
Более того, приведенный выше модульный тест подтверждает, что реализация findAll()
является правильной независимоосновного поставщика JPA и базовых данных.Я не хочу тестировать JPA и JPA-провайдера, если не подозреваю, что в стороннем коде есть ошибки, поэтому устранение этих зависимостей позволяет мне полностью сосредоточить тест на бизнес-логике сервиса Comment.
Может потребоваться некоторое время, чтобы приспособиться к образу поведения при тестировании с использованием заглушек, но это очень мощный метод для тестирования бизнес-логики ваших компонентов EJB 3.1, поскольку он позволяет изолировать и сузить область действия каждого теста для исключения внешних зависимостей..