А Вы знаете что такое mock-объект? Нет?
Что же говорит по этому поводу википедия: «В объектно-ориентированном программировании mock-объект имитирует поведение реального объекта заданным образом… ». Казалось бы зачем? Википедия продолжает: «Во время unit-тестирования mock-объекты могут симулировать поведение бизнес-объектов и бизнес-логику, что иногда необходимо из-за сложности реального поведения»
И что же дают mock-библиотеки java-разработчику? Конечно же удобство создания и использования тех самых mock-объектов!
java-source.net приводит список аж из 7 библиотек:
Я начал знакомство с mock-объектами c другой библиотеки, которой нет на java-source.net — Mockito. Я просто доверился мнению javaposse, признавших mockito библиотекой недели, а так же настроению java-блогосферы и не разочаровался. Вы тоже оцените насколько это удобно:
Внимание! Сделав глоток — остановиться невозможно.
mock-объект будет запоминать любые вызовы его методов, чтобы после Вы могли проверить какие методы вызывал ваш тестируемый код у mock-объекта
По умолчанию все методы mock объекта возвращают default'ные значение, false для boolean, 0 для int, пустые коллекции, null для остальных объектов.
Вы можете создать mock-объект, (точнее spy-объект) который будет использовать реальный объект при вызовах метода. Перегрузив лишь необходимые вам методы, так сказать частичный mock-объект.
Дополнительная литература:
Спасибо. И да, в этом посте 58 раз упоминается слово mock
Что же говорит по этому поводу википедия: «В объектно-ориентированном программировании mock-объект имитирует поведение реального объекта заданным образом… ». Казалось бы зачем? Википедия продолжает: «Во время unit-тестирования mock-объекты могут симулировать поведение бизнес-объектов и бизнес-логику, что иногда необходимо из-за сложности реального поведения»
И что же дают mock-библиотеки java-разработчику? Конечно же удобство создания и использования тех самых mock-объектов!
java-source.net приводит список аж из 7 библиотек:
Я начал знакомство с mock-объектами c другой библиотеки, которой нет на java-source.net — Mockito. Я просто доверился мнению javaposse, признавших mockito библиотекой недели, а так же настроению java-блогосферы и не разочаровался. Вы тоже оцените насколько это удобно:
Внимание! Сделав глоток — остановиться невозможно.
Проверяем поведение
mock-объект будет запоминать любые вызовы его методов, чтобы после Вы могли проверить какие методы вызывал ваш тестируемый код у mock-объекта
Copy Source | Copy HTML
- //статически импортируем методы (для красоты и легкости кода)
- import static org.mockito.Mockito.*;
-
- //вот он - mock-объект (заметьте: List.class - это интерфейс)
- List mockedList = mock(List.class);
-
- //используем его
- mockedList.add("one");
- mockedList.clear();
-
- //проверяем, были ли вызваны методы add с параметром "one" и clear
- verify(mockedList).add("one");
- verify(mockedList).clear();
А как же stub'ы?
По умолчанию все методы mock объекта возвращают default'ные значение, false для boolean, 0 для int, пустые коллекции, null для остальных объектов.
Copy Source | Copy HTML
- //Вы можете создавать mock для конкретного класса, не только для интерфейса
- LinkedList mockedList = mock(LinkedList.class);
-
- //stub'инг
- when(mockedList.get(0)).thenReturn("first");
- when(mockedList.get(1)).thenThrow(new RuntimeException());
-
- //получим "first"
- System.out.println(mockedList.get(0));
-
- //получим RuntimeException
- System.out.println(mockedList.get(1));
-
- //получим "null" ибо get(999) не был определен
- System.out.println(mockedList.get(999));
Проверяем точное количество вызовов
Copy Source | Copy HTML
- //используем mock-объект
- mockedList.add(«once»);
-
- mockedList.add(«twice»);
- mockedList.add(«twice»);
-
- mockedList.add(«three times»);
- mockedList.add(«three times»);
- mockedList.add(«three times»);
-
- //по умолчанию проверка, что вызывался 1 раз ~ times(1)
- verify(mockedList).add(«once»);
- verify(mockedList, times(1)).add(«once»);
-
- //точное число вызовов
- verify(mockedList, times(2)).add(«twice»);
- verify(mockedList, times(3)).add(«three times»);
-
- //никогда ~ never() ~ times(0)
- verify(mockedList, never()).add(«never happened»);
-
- //как минимум, как максимум
- verify(mockedList, atLeastOnce()).add(«three times»);
- verify(mockedList, atLeast(2)).add(«five times»);
- verify(mockedList, atMost(5)).add(«three times»);
Паразитируем на реальных объектах
Вы можете создать mock-объект, (точнее spy-объект) который будет использовать реальный объект при вызовах метода. Перегрузив лишь необходимые вам методы, так сказать частичный mock-объект.
Copy Source | Copy HTML
- List list = new LinkedList();
- List spy = spy(list);
-
- //опционально, определяем лишь метод size()
- when(spy.size()).thenReturn(100);
-
- //используем реальные методы
- spy.add("one");
- spy.add("two");
-
- //получим "one"
- System.out.println(spy.get(0));
-
- //метод size() нами переопределён - получим 100
- System.out.println(spy.size());
-
- //можем проверить
- verify(spy).add("one");
- verify(spy).add("two");
А так же
- Используем маски в аргументах переопределяемых методов
- Переопределяем методы, возвращающие void
- Проверяем порядок вызовов mock-объекта
- Ищем ненужные вызовы mock-объекта
- Аннотация Mock
- Различные возвращаемые значения, для одних и тех же аргументов
- … остатки сладки
Дополнительная литература:
- Сравнение Mockito и самой похожей на неё EasyMock
- Обзор библиотеки на InfoQ
- Выбор лучшей mock-библиотеки на stackoverflow
- mockobjects.com
Спасибо. И да, в этом посте 58 раз упоминается слово mock