Чтобы продемонстрировать это, я собираюсь переписать код из моего последнего блога (2) это тестирует мой простой AddressService . Сценарий тот же, AddressService должен загрузить свойство сайта и решить, стоит ли возвращать адрес:
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
|
public Address findAddress( int id) { logger.info( "In Address Service with id: " + id); Address address = Address.INVALID_ADDRESS; if (isAddressServiceEnabled()) { address = addressDao.findAddress(id); address = businessMethod(address); } logger.info( "Leaving Address Service with id: " + id); return address; } private boolean isAddressServiceEnabled() { return new Boolean(propManager.findProperty( "address.enabled" )); } |
… кроме того, я собираюсь притвориться, что SitePropertiesManager заблокирован внутри файла JAR.
Все пункты о том, как сделать унаследованный код более тестируемым, о чем я говорил ранее, остаются в силе: вам нужно перейти к внедрению зависимостей с помощью реализации SpringFactoryBean и перестать полагаться на метод статической фабрики getInstance (). Вам также нужен способ создания заглушки, которая позволит вам изолировать ваш код от базы данных и файловой системы, которая успешно используется нашим мошенническим классом. SitePropertiesManager . В этом случае, поскольку класс заблокирован в файле JAR, вы не можете просто извлечь интерфейс, вам нужно быть немного хитрее и использовать наследование. Написание заглушки с использованием наследования довольно тривиально и занимает всего несколько строк кода, как показано ниже:
01
02
03
04
05
06
07
08
09
10
11
12
13
|
public class StubSitePropertiesUsingInheritance extends SitePropertiesManager { private final Map<String, String> propMap = new HashMap<String, String>(); public void setProperty(String key, String value) { propMap.put(key, value); } @Override public String findProperty(String propertyName) { return propMap.get(propertyName); } } |
Основная идея заключается в том, что теперь я могу полиморфно внедрить мой экземпляр-заглушку в мой класс AddressService, не зная, что его обманули.
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
|
public class LegacyAddressServiceUsingInheritanceTest { private StubAddressDao addressDao; private StubSitePropertiesUsingInheritance stubProperties; private LegacyAddressService instance; @Before public void setUp() { instance = new LegacyAddressService(); stubProperties = new StubSitePropertiesUsingInheritance(); instance.setPropertiesManager(stubProperties); } @Test public void testAddressSiteProperties_AddressServiceDisabled() { /* Set up the AddressDAO Stubb for this test */ Address address = new Address( 1 , "15 My Street" , "My Town" , "POSTCODE" , "My Country" ); addressDao = new StubAddressDao(address); instance.setAddressDao(addressDao); stubProperties.setProperty( "address.enabled" , "false" ); Address expected = Address.INVALID_ADDRESS; Address result = instance.findAddress( 1 ); assertEquals(expected, result); } @Test public void testAddressSiteProperties_AddressServiceEnabled() { /* Set up the AddressDAO Stubb for this test */ Address address = new Address( 1 , "15 My Street" , "My Town" , "POSTCODE" , "My Country" ); addressDao = new StubAddressDao(address); instance.setAddressDao(addressDao); stubProperties.setProperty( "address.enabled" , "true" ); Address result = instance.findAddress( 1 ); assertEquals(address, result); } } |
Вы можете спросить: почему не всегда используется наследование, и ответ заключается в том, что недостатком этого метода является то, что тестовый код тесно связан с диким классом SitePropertiesManager . В этом случае это не слишком большая проблема, и, будучи прагматичным программистом, я полагаю, что это на самом деле не имеет значения, так как иметь аккуратный, проверенный и надежный код лучше, чем иметь свободный код, но без модульных тестов.
(1) Разработан без учета модульного тестирования.
(2) Исходный код доступен на GitHub по адресу:
мерзавец: //github.com/roghughe/captaindebug.git
Ссылка: Подробнее о создании заглушек для устаревшего кода — Методы тестирования 7 от нашего партнера по JCG Роджера Хьюза в блоге Captain Debug .
Статьи по Теме :
- Методы тестирования — не писать тесты
- Неправильное использование сквозных тестов — Методы тестирования 2
- Что следует тестировать? — Методы испытаний 3
- Регулярные юнит-тесты и заглушки — Методы испытаний 4
- Модульное тестирование с использованием макетов — Методы тестирования 5
- Создание заглушек для устаревшего кода — методы тестирования 6
- Почему вы должны писать модульные тесты — методы тестирования 8
- Некоторые определения — методы тестирования 9