#java #многопоточность #исключения #тестирование
Мы тестируем код и знаем, что у нас должно вывалиться исключение. К примеру мы тестируем итератор и знаем, что больше элементов нету и если мы вызовем next (), тогда получим NoSuchElementException, и чтобы всё было нормально мы пишем: @Test(expected = NoSuchElementException.class) public void shoulThrowNoSuchElementException() { it = new Iteratorrmatrixmass(new int[][]{}); it.next(); } У нас есть несколько потоков и один из потоков должен выбросить исключение OptimisticException: @Test (expected = OptimisticException.class) public void update() throws InterruptedException { Base base = new Base(1, 1, "12321"); Base base1 = new Base(1, 2, ""); СacheBase data = new СacheBase(); data.add(base); Thread r1 = new Thread(new Update(data, base1), "r1"); Thread r2 = new Thread(new Update(data, base1), "r2"); // здесь должна быть OptimisticException.class r1.start(); r2.start(); r1.join(); r2.join(); System.out.println(base.getVersion()); } Но в этом случае (expected = OptimisticException.class) эта надпись нам не помогла, в консоли всё равно вылазит надпись: Exception in thread "r2" ru.job4j.blockhash.OptimisticException: Объект уже обновлён до текущей версии, в обновлении отказано Я полагаю из-за того, что это исключение выскакивает не в основном потоке. Что сделать чтобы тестирование прошло успешно?
Ответы
Ответ 1
Есть такой "костыльный", но рабочий вариант : @Test public void test() { CompletableFuturefuture = CompletableFuture.runAsync(() -> { throw new OptimisticException("Optimistic Exception"); // ваш runnable код }); assertThatThrownBy(future::get) .hasCauseExactlyInstanceOf(OptimisticException.class) .hasMessageContaining("Optimistic Exception"); } Как это работает : Создается лямбда, которая выполняется когда вызывается метод get. Затем перехватывается ошибка и из нее достается исключение, которое выкинулось в вашем коде. P.S библиотека для ассертов - AssertJ Ответ 2
Для того, что бы тест выполнился вам надо бросить исключение в текущем потоке. Чтобы обработать исключение, возникающее в потоках надо в основном потоке установить обработчик Thread.setDefaultExceptionHandler((t, e) -> { throw new OptimisticException(e); });
Комментариев нет:
Отправить комментарий