Модульное тестирование, которое регистрирует сообщение, записанное при обнаружении исключения

#java #unit-testing #exception-handling #mocking #mockito

#java #модульное тестирование #обработка исключений #издевательство #mockito

Вопрос:

Вот код, с которым я работаю. В этом тесте я хочу убедиться, что метод журнала вызывается при обнаружении исключения.

 public class SuperClass(){
   public void log()
   {
      do some logging;
   }
}

public class ClassUnderTest extends SuperClass(){

    public String methodbeingtested(Object param)
    {
      try
         {
             String a = SomeObject.
                              methodthatthrowsexception(param);//static method, throws JAXB/NPE
         }
      catch(Exception exp)
         {
             log("log msg",exp);//inherited method
         }
    }
}


public class ClassUnderTestTest {

    @Test
    public testmethodbeingtested(){
       ClassUnderTest cut = new ClassUnderTest()
       ClassUnderTest cutspy = Mockito.spy(cut);

       cutspy.methodbeingtested(param);

       Mockito.verify(cutspy).log("log msg", new Exception()); // exp is needed to here.  
    }
}
  

Просмотрев несколько примеров, приведенное выше было самым близким, что я мог получить. Этот тестовый случай вызывает исключение. Но не удается проверить вызов метода журнала как Mockito.для проверки требуется точное перехваченное исключение (exp), к которому у тестового примера нет доступа.

Есть ли какой-либо другой способ протестировать этот сценарий?

Комментарии:

1. Есть ли причина, по которой вы не можете просто написать verify(cutspy).log(eq("log msg"), any(Exception.class)); , если это то, чего вы пытаетесь достичь?

2. Пробовал, не сработало. Как упоминалось в OP, для проверки требуется точный экземпляр объекта исключения.

3. Нет, verify не требует точного экземпляра. Что пошло не так, когда вы попробовали мое предложение?

4. Дэвид, ты был прав, это работает. Я думаю, что я отвечал на комментарий Рахула. Клянусь, я видел комментарий, сделанный им. В любом случае, если вы можете добавить свой комментарий в качестве ответа, я могу принять.

5. Перехват Exception обычно является ошибкой. Можете ли вы перехватить более конкретный класс исключений?

Ответ №1:

verify Метод Mockito можно использовать с сопоставителями аргументов. Если вы хотите проверить, что log это было вызвано, с любым Exception вообще в качестве второго аргумента, вы можете просто написать

 verify(cutspy).log(eq("log msg"), any(Exception.class));
  

Я предположил, что у вас есть правильный статический импорт для verify , eq и any .

Кроме того, для этого теста не требуется PowerMock. Ваша строка PowerMock.expectLastCall().once(); является избыточной и запутанной и, вероятно, должна быть удалена вместе с @PrepareForTest аннотацией.

Ответ №2:

Вместо того, чтобы шпионить за ClassUnderTest, вы должны смоделировать структуру ведения журнала, внедрить ее в класс, а затем убедиться, что вызывается метод log. Id’ также издевается над классом SomeObject и вызывает исключение.

Кроме того, вам действительно следует оценить, нужно ли вам проверять свои операторы журнала. Возможно, у вас есть веская причина для этого, но, как правило, утверждение / проверка в такой степени не требуется и только сделает ваши тесты хрупкими.