Предисловие
В этой статье представлено, как использовать Springboot+Junit+Mockito для модульного тестирования, и выберите класс, который соответствует транзакциям для проведения модульного тестирования.
Понять требования перед модульным тестированием
Чтобы написать хороший единственный тест, вы должны сначала понять требования. Только зная, что делать, вы знаете, как проверить. Но в этой статье в основном рассказывается об использовании Mockito, и нет необходимости обращать внимание на конкретные потребности. Следовательно, в этом разделе пропускается конкретное описание требований.
Изолировать внешние зависимости
Case1. Как контролировать возвращаемое значение объекта зависимости, аннотированного @Autowired или @Resource Annotation в тестируемом классе
Принятие соответствующего (MatchingRoder Buyorder, MatchingRoder Sellorder) метода в разделе Test SatchingServiceImpl.java В качестве примера
Протестированный класс MatchingServiceImpl
открытый класс MatchingServiceImpl реализует MatchingService {private Static Final Logger log = loggerFactory.getLogger (matchingserviceimpl.class); @Autowired Private Quoteservice Quoteservice; ... Общественное совпадение MatchingResult (MatchingRoder Buyorder, MatchingRoder SellOrder) {int currentPrice = Quoteservice.getCurrentPriceByProduct (buyorder.getProductCode ()); MatchingResult result = new MatchingResult (); if (sellorder! = null && buyorder! = null && sellorder.getPrice () <= buyorder.getPrice ()) {...}}quoteservice.getCurrentPriceByProduct (buyorder.getProductCode ()); Чтобы получить доступ к Redis, чтобы получить текущую цитату, нам необходимо высмеивать внешнюю зависимость, чтобы контролировать возвращаемое значение метода GetCurrentPriceByProduct. Вы можете сделать это с помощью Mockito, следующим образом:
Тестовый класс MatchingServiceImpltest
Общедоступный класс MatchingServiceImpltest Extends MockitObasedTest { / *** Объекты, помеченные @Mock, будут автоматически впрыгнуты в объект, помеченный @injectMocks* / @mock private Quoteservice Quoteservice; /** * <pre> * Объекты, которые будут проверены, помеченные @injectmocks, те объекты, помеченные @Mock, будут автоматически вводить в него. * Другое замечание состоит в том, что MatchingServiceImpl непосредственно новый (это нормально, если он не новый после Mockito 1.9), а не вводится через пружинный контейнер. Потому что здесь мне не нужно получать другие зависимости от пружинного контейнера *, и мне не нужна база данных, Redis, Zookeeper, MQ, и от этого ничего не зависит, поэтому я непосредственно новый *</ pre> */ @InjectMocks Private MatchingServiceImpl MatchingingService = new MatchingingServiceImpl (); @Test public void testmatching_successwhencencrentpriceweewweewbuypriceandsellprice () {matchingorder buyorder = new Matchingorder (); buyorder.setprice (1000); buyorder.setCount (23); MatchingROORD SellOrder = новый MatchingRoder (); SellOrder.SetPrice (800); SellOrder.SetCount (20); // Метод загрязняет (метод запор) // Когда (x) .thenreurn (y): возвращает указанное значение, когда указанный метод называется mockito.when (quoteservice.getcurrentpricebyproduct (mockito.anystring ())). Затем Return (900); MatchingResult Result = MatchingService.Matching (Buyorder, SellOrder); org.junit.assert.assertequals (true, result.issuccess ()); // утверждает, является ли совпадение успешным org.junit.assert.assertequals (20, result.gettradecount ()); // утверждать количество транзакции org.junit.assertequals (900, result.gettreprice (););); // утверждает, соответствует ли последняя цитата ожидания}Case2. Когда функция A протестирована, как контролировать возвращаемое значение функции B в тестировании класса?
Например, в MatchingingServiceImpl существует функция startBuyProcess, которая вызывает другие функции в классе, такие как GetTopsellOrder и сопоставление. Как контролировать возвращаемые значения этих двух функций?
Проблема, которая должна быть решена здесь, в том, как фактически выполнить измеренный метод (например, startbuyprocess) класса «Частичный макет», протестированный класс, в то время как другие методы (такие как gettopsellorder) сваливаются (не входят и выполняются).
Протестированный класс MatchingServiceImpl
Protected void startBuyProcess (MatchingRoder Buyorder, Boolean WaitFormatching) {while (true) {// Лучшая цена контрагента MatchingRoder Topsellorder = getTopsellOrder (buckerord.getProductCode ()); MatchingResult MatchingResult = Matching (Buyorder, TopsellOrder); if (matchingresult.issuccess ()) {domatchingsuccess (buyorder, topsellorder, matchingresult, matchingtype.buy); if (buyorder.getCount () <= 0) {break; }} else {if (waitformatching) {// добавить в соответствие с очередью, чтобы соответствовать addTomatchingBuy (buyorder); } else {// отозвать заказ sendCancLemsg (buyorder); } перерыв; }}}}Использование mockito.spy () может достичь «частичного макета»
Тестовый класс matchingserviceimpltest.teststartbuyprocess_incaseofmatchingsuccess
/** * * * Проверьте, соответствует ли обработка метода startBuyProcess после успешного совпадения ожиданий, то есть проверить поведение после входа в следующее суждение. MatchingResult, MatchingType.buy); * * if (buyorder.getCount () <= 0) { * break; *} *}! buyorder.setprice (700); buyorder.setCount (23); // Использовать mockito.spy (), чтобы частично подумать Matchingservice matchingservice = mockito.spy (matchingservice); MatchingResult FirstMatchingResult = new MatchingResult (); FirstMatchingResult.setSuccess (true); FirstMatchingResult.SetTradeCount (20); MatchingResult SecondMatchingResult = new MatchingResult (); SecondMatchingResult.setSuccess (false); // doreturn (x). Когда (obj) .method () После накапливания методов, после накапливания методов, программа вернет указанное значение, как и ожидалось при выполнении этих методов. Методы, которые не сложены, будут выполняться, будут выполняться в режиме реального времени. // Два доретерна означают, что FirstMatchingResult возвращается, когда в первую очередь называется MatchingService. Mockito.doreturn (FirstmatchingResult) .doreturn (SecondMatchingResult). Когда (MatchingService) .matching (mockito.any (matchingorder.class), mockito.any (matchingorder.class)); MatchingROORD SellOrder = новый MatchingRoder (); SellOrder.SetPrice (600); SellOrder.SetCount (20); // Скаливание метода getTopsellOrder mockito.doreturn (sellorder). Когда (MatchingService) .getTopsellOrder (mockito.anystring ()); // Скаливание внешнего метода, который зависит от jedis mockito.when (jedisclient.incrby (mockito.anysstring (), mockito.anylong ())). Затем возвращать (0l); // startBuyProcess - это тестовая функция. Если вы не складываете, matchingservice.startbuyprocess (buyorder, true); // Последующее утверждение проверки состоит в том, чтобы проверить поведение метода DomatchingInsuccess, которое также является целью этого теста .// Проверка может использоваться для проверки того, сколько раз был выполнен определенный метод класса? Вот чтобы проверить, был ли Jedisclient.zremfirst был выполнен после Mockito.verify (jedisclient, mockito.times (1)). Zremfirst (mockito.anystring ()); org.junit.assert.assertequals (3, buyorder.getCount ()); org.junit.assert.assertequals (0, sellorder.getCount ()); } Использование шпиона было продемонстрировано. Давайте поговорим о «гранулярности» модульных тестов от TestStartBuyProcess_incaseOfMatchingSuccess.
Цель TestStartBuyProcess_incaseOfMatchingSuccess - это тестирование DomatchingSuccess. Мы очень усердно работали, чтобы закончить предыдущие препараты, прежде чем мы сможем протестировать DomatchingSuccess.
Лучшая практика должна состоять в том, чтобы запустить новый метод испытаний для тестирования DomatchingSuccess отдельно, и фокус также сосредоточен. После того, как DomatchingSuccess перезаписан, StartBuyProcess может просто покрыть свой собственный отдел суждения. Покрытие все еще достигается, и тестовый код легче поддерживать. TestStartBuyProcess_incaseOfMatchingSuccess легко влияет на изменения из -за слишком многих обязанностей. Изменение мелочей может повлиять на его нормальную функцию.
Представление зависимостей Maven Framework Maven
<dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.11</version> <scope>test</scope></dependency><dependency> <groupId>org.mockito</groupId> <artifactId>mockito-all</artifactId> <version>1.10.19</version> <cracpe> тест </scope> </getyederiation> <dependency> <groupid> org.springframework </groupid> <artifactid> spring-test </artifactid> <sersion> 4.2.5.reeleas
Контекст конструкция Springboot+Junit+Mockito
Mockitobasedtest
@Runwith (springjunit4classrunner.class) @SpringApplicationConfiguration (ClassePplication.class). }} // другие тестовые классы наследуют MockitoBasedTest
Выше всего содержание этой статьи. Я надеюсь, что это будет полезно для каждого обучения, и я надеюсь, что все будут поддерживать Wulin.com больше.