JustRetryFailoverHandler extends ComparableFailoverHandler { @Override public <T> Response<T> handle(final Invocation<T> invocation, final Response<T> response) { logger.debug("Handle {} with {}", response.getError(), this); Response<T> next = response; int countDown = this.count; while (null != next.getError() && 0 < countDown) { try { logger.debug("Just retry with {} after sleep {}ms (count left: {})", invocation, this.interval, countDown); Thread.sleep(this.interval); } catch (Exception e) { throw new HerajException("Unexpected error", e); } try { final T ret = invocation.invoke(); next = Response.success(ret); } catch (Exception e) { next = Response.fail(e); } --countDown; } return next; } JustRetryFailoverHandler(final int count, final Time interval); @Override Response<T> handle(final Invocation<T> invocation, final Response<T> response);  }
@Test public void testHandle() { final int count = 5; final int stop = 2; final JustRetryFailoverHandler justRetryFailoverHandler = new JustRetryFailoverHandler(count, Time.of(100L, TimeUnit.MILLISECONDS)); final AtomicInteger countDown = new AtomicInteger(count); final String expected = randomUUID().toString(); final RequestMethod<Object> requestMethod = new RequestMethod<Object>() { @Getter protected final String name = randomUUID().toString(); @Override protected Object runInternal(List<Object> parameters) throws Exception { countDown.decrementAndGet(); if (stop == countDown.get()) { return expected; } throw new UnsupportedOperationException(); } }; final Response<Object> response = Response.fail(new UnsupportedOperationException()); final Response<Object> handled = justRetryFailoverHandler .handle(new TestInvocation<>(requestMethod), response); assertEquals(expected, handled.getValue()); assertEquals(stop, countDown.get()); }
@Test public void shouldNotRunOnSuccess() { final int count = 3; final JustRetryFailoverHandler justRetryFailoverHandler = new JustRetryFailoverHandler(count, Time.of(100L, TimeUnit.MILLISECONDS)); final AtomicInteger countDown = new AtomicInteger(count); final RequestMethod<String> requestMethod = new RequestMethod<String>() { @Getter protected final String name = randomUUID().toString(); @Override protected String runInternal(List<Object> parameters) throws Exception { countDown.decrementAndGet(); return null; } }; final String expected = randomUUID().toString(); final Response<String> response = Response.success(expected); final Response<String> handled = justRetryFailoverHandler .handle(new TestInvocation<>(requestMethod), response); assertEquals(expected, handled.getValue()); assertEquals(count, countDown.get()); }
@Test public void shouldKeepErrorOnNoSuccess() { final int count = 3; final JustRetryFailoverHandler justRetryFailoverHandler = new JustRetryFailoverHandler(count, Time.of(100L, TimeUnit.MILLISECONDS)); final AtomicInteger countDown = new AtomicInteger(count); final RequestMethod<Object> requestMethod = new RequestMethod<Object>() { @Getter protected final String name = randomUUID().toString(); @Override protected Object runInternal(List<Object> parameters) throws Exception { countDown.decrementAndGet(); throw new UnsupportedOperationException(); } }; final Response<Object> response = Response.fail(new UnsupportedOperationException()); final Response<Object> handled = justRetryFailoverHandler .handle(new TestInvocation<>(requestMethod), response); assertNotNull(handled.getError()); assertEquals(0, countDown.get()); }