diff --git a/src/main/java/de/ozgcloud/processor/processor/ProcessorService.java b/src/main/java/de/ozgcloud/processor/processor/ProcessorService.java index c318ef6bac7adce1ed5fe0227e2ec039179b887c..650cecca12201291ddd63e430349d59427858b7d 100644 --- a/src/main/java/de/ozgcloud/processor/processor/ProcessorService.java +++ b/src/main/java/de/ozgcloud/processor/processor/ProcessorService.java @@ -45,8 +45,10 @@ import de.ozgcloud.common.errorhandling.TechnicalException; import de.ozgcloud.processor.ProcessorManagerConfiguration; import de.ozgcloud.processor.processor.ProcessorProperties.Form; import de.ozgcloud.processor.processor.ProcessorProperties.Processor; -import de.ozgcloud.processor.result.ProcessorTechnicalException; +import de.ozgcloud.processor.result.Action; +import de.ozgcloud.processor.result.AktennotizFactory; import de.ozgcloud.processor.vorgang.Vorgang; +import de.ozgcloud.processor.vorgang.VorgangId; import lombok.RequiredArgsConstructor; import lombok.extern.log4j.Log4j2; import reactor.core.publisher.Mono; @@ -61,6 +63,7 @@ public class ProcessorService { @Qualifier(ProcessorManagerConfiguration.PROCESSOR_PROPERTIES_NAME) // NOSONAR private final ProcessorProperties properties; + private final AktennotizFactory aktennotizFactory; private final WebClient webClient; @@ -103,11 +106,17 @@ public class ProcessorService { .retrieve() .onStatus(HttpStatusCode::is3xxRedirection, this::buildRedirectError) .bodyToMono(ProcessorResult.class) - .onErrorMap(exception -> new ProcessorTechnicalException(vorgang.getId(), processor.getName(), "Failed to request Vorgang processor.", - exception)) + .onErrorResume(exception -> Mono.just(buildErrorResult(exception, processor, vorgang))) .doOnSuccess(processorResult -> processorResult.toBuilder().processorName(processor.getName()).build()); } + private ProcessorResult buildErrorResult(Throwable exception, Processor processor, Vorgang vorgang) { + return ProcessorResult.builder() + .action(Action.CREATE_AKTENNOTIZ) + .body(aktennotizFactory.createErrorAktennotiz(VorgangId.from(vorgang.getId()), processor.getName(), exception)) + .build(); + } + MultiValueMap<String, HttpEntity<?>> createRequestBody(Vorgang vorgang) { // NOSONAR var multipartBodyBuilder = new MultipartBodyBuilder(); multipartBodyBuilder.part(KEY_VORGANG, vorgang, MediaType.APPLICATION_JSON); diff --git a/src/main/java/de/ozgcloud/processor/result/AktennotizFactory.java b/src/main/java/de/ozgcloud/processor/result/AktennotizFactory.java index ab21c063e9669b00f07e5af63e0c3552e097b229..e9e96d08addfa3bc3d69e2e48ee8376b8425daac 100644 --- a/src/main/java/de/ozgcloud/processor/result/AktennotizFactory.java +++ b/src/main/java/de/ozgcloud/processor/result/AktennotizFactory.java @@ -39,6 +39,11 @@ public class AktennotizFactory { Meldung: %s. """; + static final String ERROR_TEXT_WO_EXCEPTIONID = """ + Bei der Verarbeitung im Processor '%s' ist ein Fehler aufgetreten. + Meldung: %s. + """; + public Aktennotiz createFrom(ProcessorResult processorResult) { var resultBody = processorResult.getBody(); return Aktennotiz.builder() @@ -55,6 +60,12 @@ public class AktennotizFactory { .build(); } + public Aktennotiz createErrorAktennotiz(VorgangId vorgangId, String processorName, Throwable cause) { + return createErrorAktennotizBuilder(vorgangId) + .text(ERROR_TEXT_WO_EXCEPTIONID.formatted(processorName, ExceptionUtils.getRootCauseMessage(cause))) + .build(); + } + public Aktennotiz.AktennotizBuilder createErrorAktennotizBuilder(VorgangId vorgangId) { return Aktennotiz.builder() .vorgangId(vorgangId.toString()) diff --git a/src/test/java/de/ozgcloud/processor/processor/ProcessorServiceITCase.java b/src/test/java/de/ozgcloud/processor/processor/ProcessorServiceITCase.java index e1c09dfbcc05c00109d5e096993aecaac0ab3cf4..cf95b8880c942a47ef1070d4fc14d3c06fc966f2 100644 --- a/src/test/java/de/ozgcloud/processor/processor/ProcessorServiceITCase.java +++ b/src/test/java/de/ozgcloud/processor/processor/ProcessorServiceITCase.java @@ -24,7 +24,6 @@ package de.ozgcloud.processor.processor; import static org.assertj.core.api.Assertions.*; -import static org.junit.jupiter.api.Assertions.*; import java.time.Duration; import java.util.Collections; @@ -47,15 +46,14 @@ import org.springframework.test.util.ReflectionTestUtils; import de.ozgcloud.common.test.ITCase; import de.ozgcloud.processor.processor.ProcessorProperties.Processor; -import de.ozgcloud.processor.result.ProcessorTechnicalException; import de.ozgcloud.processor.result.ResultService; +import de.ozgcloud.processor.result.Severity; import de.ozgcloud.processor.vorgang.Vorgang; import de.ozgcloud.processor.vorgang.VorgangTestFactory; import lombok.SneakyThrows; import okhttp3.mockwebserver.MockResponse; import okhttp3.mockwebserver.MockWebServer; import okhttp3.mockwebserver.RecordedRequest; -import reactor.core.publisher.Mono; @ITCase class ProcessorServiceITCase { @@ -149,7 +147,9 @@ class ProcessorServiceITCase { mockWebServer.enqueue(createResponse(ProcessorResultTestFactory.KEY_RESULT_ACTION, action)); var vorgang = VorgangTestFactory.create(); - assertThrows(ProcessorTechnicalException.class, () -> sendRequest(vorgang)); + var result = service.callProcessor(processor, vorgang).block(); + + assertThat(result.getBody().getSeverity()).isEqualTo(Severity.ERROR); } @Test @@ -157,7 +157,9 @@ class ProcessorServiceITCase { mockWebServer.enqueue(createResponse("body", null)); var vorgang = VorgangTestFactory.create(); - assertThrows(ProcessorTechnicalException.class, () -> sendRequest(vorgang)); + var result = service.callProcessor(processor, vorgang).block(); + + assertThat(result.getBody().getSeverity()).isEqualTo(Severity.ERROR); } private MockResponse createResponse(String actionKey, String actionValue) { @@ -197,9 +199,9 @@ class ProcessorServiceITCase { MockResponse response = new MockResponse().setResponseCode(HttpStatus.BAD_REQUEST.value()); mockWebServer.enqueue(response); - var results = service.processVorgang(vorgang, FormTestFactory.EVENT); + var result = service.callProcessor(processor, vorgang).block(); - assertThrows(ProcessorTechnicalException.class, () -> results.forEach(Mono::block)); + assertThat(result.getBody().getSeverity()).isEqualTo(Severity.ERROR); } @Test @@ -207,18 +209,18 @@ class ProcessorServiceITCase { MockResponse response = new MockResponse().setResponseCode(HttpStatus.BAD_GATEWAY.value()); mockWebServer.enqueue(response); - var results = service.processVorgang(vorgang, FormTestFactory.EVENT); + var result = service.callProcessor(processor, vorgang).block(); - assertThrows(ProcessorTechnicalException.class, () -> results.forEach(Mono::block)); + assertThat(result.getBody().getSeverity()).isEqualTo(Severity.ERROR); } @Test void shouldHandleRedirectStatus() { mockWebServer.enqueue(new MockResponse().setResponseCode(301)); - var results = service.processVorgang(vorgang, FormTestFactory.EVENT); + var result = service.callProcessor(processor, vorgang).block(); - assertThrows(ProcessorTechnicalException.class, () -> results.forEach(Mono::block)); + assertThat(result.getBody().getSeverity()).isEqualTo(Severity.ERROR); } @Test @@ -226,9 +228,9 @@ class ProcessorServiceITCase { MockResponse response = new MockResponse().addHeader("content-type", MediaType.APPLICATION_JSON).setBody("test"); mockWebServer.enqueue(response); - var results = service.processVorgang(vorgang, FormTestFactory.EVENT); + var result = service.callProcessor(processor, vorgang).block(); - assertThrows(ProcessorTechnicalException.class, () -> results.forEach(Mono::block)); + assertThat(result.getBody().getSeverity()).isEqualTo(Severity.ERROR); } }