Как добавить сводку по времени выполнения JUnit-тестов

Есть удобный класс Stopwatch, который позволяет получить время выполнения теста. При большом количестве тестов удобно сделать отдельный утильный класс, который будет накапливать результаты каждого метода в классе с помощью StringBuilder, и обнулять перед запуском тестов в новом классе:

import org.junit.rules.ExternalResource;
import org.junit.rules.Stopwatch;
import org.junit.runner.Description;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.concurrent.TimeUnit;

public class TimingRules {

    private static final Logger log = LoggerFactory.getLogger("result");

    private static final StringBuilder results = new StringBuilder();

    public static final Stopwatch STOPWATCH = new Stopwatch() {
        @Override
        protected void finished(long nanos, Description description) {
            String result = String.format("%-95s %7d", description.getDisplayName(), TimeUnit.NANOSECONDS.toMillis(nanos));
            results.append(result).append('\n');
            log.info(result + " ms\n");
        }
    };

    // элемент разметки
    //    https://dzone.com/articles/applying-new-jdk-11-string-methods 
    private static final String DELIM = "-".repeat(103);

    //форматируем красивый вывод в консоль
    public static final ExternalResource SUMMARY = new ExternalResource() {

        //обнуляем перед запуском тестов класса
        @Override
        protected void before() throws Throwable {
            results.setLength(0);
        }

        //выводим отформатированный результат
        @Override
        protected void after() {
            log.info("\n" + DELIM +
                    "\nTest                                                                                       Duration, ms" +
                    "\n" + DELIM + "\n" + results + DELIM + "\n");
        }
    };
}

И после этого достаточно в нужном тесте просто обратиться к созданным объектам с аннотацией @Rule :

public class ServiceTest {

    @ClassRule
    public static ExternalResource summary = TimingRules.SUMMARY;

    @Rule
    public Stopwatch stopwatch = TimingRules.STOPWATCH;

    @Test
    void test1() {
    ...

}

И получаем вот такой вывод:

Класс Stopwatch позволяет доставать время выполнения не только успешных тестов (как в примере выше), но и тестов с любым статусом — проваленные, пропущенные и пр. Для этого надо переопределить соответствующий метод.

Код в примерах взят из проекта Topjava стажировки JavaOps.

Источники и дополнительная информация: 

Leave A Comment

Please be polite. We appreciate that. Your email address will not be published and required fields are marked