use of io.github.resilience4j.common.timelimiter.monitoring.endpoint.TimeLimiterEventsEndpointResponse in project resilience4j by resilience4j.
the class TimeLimiterAutoConfigurationTest method testTimeLimiterAutoConfigurationTest.
@Test
public void testTimeLimiterAutoConfigurationTest() throws Exception {
assertThat(timeLimiterRegistry).isNotNull();
assertThat(timeLimiterProperties).isNotNull();
assertThat(compositeTimeLimiterConfigCustomizer).isNotNull();
assertThat(compositeTimeLimiterConfigCustomizer.getCustomizer("timeLimiterBackendD").isPresent()).isTrue();
assertThat(timeLimiterRegistry.getTags()).isNotEmpty();
TimeLimiterEventsEndpointResponse timeLimiterEventsBefore = timeLimiterEvents("/actuator/timelimiterevents");
TimeLimiterEventsEndpointResponse timeLimiterEventsForABefore = timeLimiterEvents("/actuator/timelimiterevents/backendA");
try {
dummyService.doSomethingAsync(true).get();
} catch (Exception ex) {
// Do nothing. The IOException is recorded by the TimeLimiter as a failure.
}
final CompletableFuture<String> stringCompletionStage = dummyService.doSomethingAsync(false);
assertThat(stringCompletionStage.get()).isEqualTo("Test result");
TimeLimiter timeLimiter = timeLimiterRegistry.timeLimiter(DummyService.BACKEND);
assertThat(timeLimiter).isNotNull();
assertThat(timeLimiter.getTimeLimiterConfig().getTimeoutDuration()).isEqualTo(Duration.ofSeconds(5));
TimeLimiterEventsEndpointResponse timeLimiterEventList = timeLimiterEvents("/actuator/timelimiterevents");
assertThat(timeLimiterEventList.getTimeLimiterEvents()).hasSize(timeLimiterEventsBefore.getTimeLimiterEvents().size() + 2);
timeLimiterEventList = timeLimiterEvents("/actuator/timelimiterevents/backendA");
assertThat(timeLimiterEventList.getTimeLimiterEvents()).hasSize(timeLimiterEventsForABefore.getTimeLimiterEvents().size() + 2);
assertThat(timeLimiterAspect.getOrder()).isEqualTo(398);
}
use of io.github.resilience4j.common.timelimiter.monitoring.endpoint.TimeLimiterEventsEndpointResponse in project resilience4j by resilience4j.
the class TimeLimiterChain method execute.
@Override
public void execute(Chain chain) throws Exception {
String prefix = chain.getRegistry().get(Resilience4jConfig.class).getEndpoints().getTimelimiter().getPath();
chain.prefix(prefix, chain1 -> {
chain1.get("events", ctx -> Promise.<TimeLimiterEventsEndpointResponse>async(d -> {
List<TimeLimiterEventDTO> eventsList = eventConsumerRegistry.getAllEventConsumer().stream().flatMap(CircularEventConsumer::getBufferedEventsStream).sorted(Comparator.comparing(TimeLimiterEvent::getCreationTime)).map(TimeLimiterEventDTO::createTimeLimiterEventDTO).collect(Collectors.toList());
d.success(new TimeLimiterEventsEndpointResponse(eventsList));
}).then(r -> ctx.render(Jackson.json(r))));
chain1.get("stream/events", ctx -> {
Flux<TimeLimiterEvent> eventStreams = Flux.fromIterable(timeLimiterRegistry.getAllTimeLimiters()).flatMap(timeLimiter -> ReactorAdapter.toFlux(timeLimiter.getEventPublisher()));
Function<TimeLimiterEvent, String> data = r -> Jackson.getObjectWriter(chain1.getRegistry()).writeValueAsString(TimeLimiterEventDTO.createTimeLimiterEventDTO(r));
ServerSentEvents events = ServerSentEvents.serverSentEvents(eventStreams, e -> e.id(TimeLimiterEvent::getTimeLimiterName).event(c -> c.getEventType().name()).data(data));
ctx.render(events);
});
chain1.get("events/:name", ctx -> {
String timeLimiterName = ctx.getPathTokens().get("name");
Promise.<TimeLimiterEventsEndpointResponse>async(d -> {
List<TimeLimiterEventDTO> eventsList = eventConsumerRegistry.getEventConsumer(timeLimiterName).getBufferedEventsStream().sorted(Comparator.comparing(TimeLimiterEvent::getCreationTime)).map(TimeLimiterEventDTO::createTimeLimiterEventDTO).collect(Collectors.toList());
d.success(new TimeLimiterEventsEndpointResponse(eventsList));
}).then(r -> ctx.render(Jackson.json(r)));
});
chain1.get("stream/events/:name", ctx -> {
String timeLimiterName = ctx.getPathTokens().get("name");
TimeLimiter timeLimiter = timeLimiterRegistry.getAllTimeLimiters().stream().filter(tL -> tL.getName().equals(timeLimiterName)).findAny().orElseThrow(() -> new IllegalArgumentException(String.format("time limiter with name %s not found", timeLimiterName)));
Function<TimeLimiterEvent, String> data = r -> Jackson.getObjectWriter(chain1.getRegistry()).writeValueAsString(TimeLimiterEventDTO.createTimeLimiterEventDTO(r));
ServerSentEvents events = ServerSentEvents.serverSentEvents(ReactorAdapter.toFlux(timeLimiter.getEventPublisher()), e -> e.id(TimeLimiterEvent::getTimeLimiterName).event(c -> c.getEventType().name()).data(data));
ctx.render(events);
});
chain1.get("events/:name/:type", ctx -> {
String timeLimiterName = ctx.getPathTokens().get("name");
String eventType = ctx.getPathTokens().get("type");
Promise.<TimeLimiterEventsEndpointResponse>async(d -> {
List<TimeLimiterEventDTO> eventsList = eventConsumerRegistry.getEventConsumer(timeLimiterName).getBufferedEventsStream().sorted(Comparator.comparing(TimeLimiterEvent::getCreationTime)).filter(event -> event.getEventType() == TimeLimiterEvent.Type.valueOf(eventType.toUpperCase())).map(TimeLimiterEventDTO::createTimeLimiterEventDTO).collect(Collectors.toList());
d.success(new TimeLimiterEventsEndpointResponse(eventsList));
}).then(r -> ctx.render(Jackson.json(r)));
});
chain1.get("stream/events/:name/:type", ctx -> {
String timeLimiterName = ctx.getPathTokens().get("name");
String eventType = ctx.getPathTokens().get("type");
TimeLimiter timeLimiter = timeLimiterRegistry.getAllTimeLimiters().stream().filter(rL -> rL.getName().equals(timeLimiterName)).findAny().orElseThrow(() -> new IllegalArgumentException(String.format("time limiter with name %s not found", timeLimiterName)));
Flux<TimeLimiterEvent> eventStream = ReactorAdapter.toFlux(timeLimiter.getEventPublisher()).filter(event -> event.getEventType() == TimeLimiterEvent.Type.valueOf(eventType.toUpperCase()));
Function<TimeLimiterEvent, String> data = r -> Jackson.getObjectWriter(chain1.getRegistry()).writeValueAsString(TimeLimiterEventDTO.createTimeLimiterEventDTO(r));
ServerSentEvents events = ServerSentEvents.serverSentEvents(eventStream, e -> e.id(TimeLimiterEvent::getTimeLimiterName).event(c -> c.getEventType().name()).data(data));
ctx.render(events);
});
});
}
use of io.github.resilience4j.common.timelimiter.monitoring.endpoint.TimeLimiterEventsEndpointResponse in project resilience4j by resilience4j.
the class TimeLimiterAutoConfigurationTest method shouldThrowTimeOutExceptionAndPropagateMDCContext.
@Test
public void shouldThrowTimeOutExceptionAndPropagateMDCContext() throws InterruptedException {
TimeLimiterEventsEndpointResponse timeLimiterEventsBefore = timeLimiterEvents("/actuator/timelimiterevents");
TimeLimiterEventsEndpointResponse timeLimiterEventsForABefore = timeLimiterEvents("/actuator/timelimiterevents/backendB");
TimeLimiter timeLimiter = timeLimiterRegistry.timeLimiter(DummyService.BACKEND_B);
assertThat(timeLimiter).isNotNull();
assertThat(timeLimiter.getTimeLimiterConfig().getTimeoutDuration()).isEqualTo(Duration.ofSeconds(1));
MDC.put("key", "ValueShouldCrossThreadBoundary");
MDC.put("key2", "value2");
final Map<String, String> contextMap = MDC.getCopyOfContextMap();
final CompletableFuture<String> future = dummyService.longDoSomethingAsync().exceptionally(throwable -> {
if (throwable != null) {
assertThat(Thread.currentThread().getName()).contains("ContextAwareScheduledThreadPool-");
assertThat(MDC.getCopyOfContextMap()).hasSize(2).containsExactlyEntriesOf(contextMap);
return MDC.getCopyOfContextMap().get("key");
}
return null;
});
waitAtMost(3, TimeUnit.SECONDS).until(matches(() -> assertThat(future).isCompletedWithValue("ValueShouldCrossThreadBoundary")));
TimeLimiterEventsEndpointResponse timeLimiterEventList = timeLimiterEvents("/actuator/timelimiterevents");
assertThat(timeLimiterEventList.getTimeLimiterEvents()).hasSize(timeLimiterEventsBefore.getTimeLimiterEvents().size() + 1);
timeLimiterEventList = timeLimiterEvents("/actuator/timelimiterevents/backendB");
assertThat(timeLimiterEventList.getTimeLimiterEvents()).hasSize(timeLimiterEventsForABefore.getTimeLimiterEvents().size() + 1);
assertThat(timeLimiterAspect.getOrder()).isEqualTo(398);
}
use of io.github.resilience4j.common.timelimiter.monitoring.endpoint.TimeLimiterEventsEndpointResponse in project resilience4j by resilience4j.
the class TimeLimiterAutoConfigurationTest method shouldThrowTimeOutExceptionAndPropagateContext.
@Test
public void shouldThrowTimeOutExceptionAndPropagateContext() throws InterruptedException {
TimeLimiterEventsEndpointResponse timeLimiterEventsBefore = timeLimiterEvents("/actuator/timelimiterevents");
TimeLimiterEventsEndpointResponse timeLimiterEventsForABefore = timeLimiterEvents("/actuator/timelimiterevents/backendB");
TimeLimiter timeLimiter = timeLimiterRegistry.timeLimiter(DummyService.BACKEND_B);
assertThat(timeLimiter).isNotNull();
assertThat(timeLimiter.getTimeLimiterConfig().getTimeoutDuration()).isEqualTo(Duration.ofSeconds(1));
TestThreadLocalContextHolder.put("ValueShouldCrossThreadBoundary");
final CompletableFuture<String> future = dummyService.longDoSomethingAsync().exceptionally(throwable -> {
if (throwable != null) {
assertThat(Thread.currentThread().getName()).contains("ContextAwareScheduledThreadPool-");
assertThat(TestThreadLocalContextHolder.get().get()).isEqualTo("ValueShouldCrossThreadBoundary");
return (String) TestThreadLocalContextHolder.get().orElse(null);
}
return null;
});
waitAtMost(3, TimeUnit.SECONDS).until(matches(() -> assertThat(future).isCompletedWithValue("ValueShouldCrossThreadBoundary")));
TimeLimiterEventsEndpointResponse timeLimiterEventList = timeLimiterEvents("/actuator/timelimiterevents");
assertThat(timeLimiterEventList.getTimeLimiterEvents()).hasSize(timeLimiterEventsBefore.getTimeLimiterEvents().size() + 1);
timeLimiterEventList = timeLimiterEvents("/actuator/timelimiterevents/backendB");
assertThat(timeLimiterEventList.getTimeLimiterEvents()).hasSize(timeLimiterEventsForABefore.getTimeLimiterEvents().size() + 1);
assertThat(timeLimiterAspect.getOrder()).isEqualTo(398);
}
Aggregations