From f694ca21841a5bd50c945f2d2493fe23b954f29d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=98yvind=20Nordsted=20Wed=C3=B8e?= Date: Mon, 30 Oct 2023 16:12:15 +0100 Subject: [PATCH] Log errors in WebClient. --- .../kabaljsontopdf/KabalJsonToPdfClient.kt | 13 +++++++ .../KabalSmartEditorApiClient.kt | 37 +++++++++++++++++++ .../clients/klagefileapi/FileApiClient.kt | 13 +++++++ .../arbeidoginntekt/ArbeidOgInntektClient.kt | 8 ++++ .../clients/azure/MicrosoftGraphClient.kt | 23 ++++++++++++ .../klage/oppgave/clients/ereg/EregClient.kt | 13 +++++++ .../kabaldocument/KabalDocumentClient.kt | 13 +++++++ .../KabalInnstillingerClient.kt | 17 +++++++++ .../oppgave/clients/kaka/KakaApiClient.kt | 14 +++++++ .../klagefssproxy/KlageFssProxyClient.kt | 19 ++++++++++ .../oppgave/clients/norg2/Norg2Client.kt | 7 ++++ .../oppgave/clients/pdl/graphql/PdlClient.kt | 5 +++ .../clients/saf/graphql/SafGraphQlClient.kt | 8 ++++ .../oppgave/clients/saf/rest/SafRestClient.kt | 8 ++++ .../clients/skjermede/SkjermedeApiClient.kt | 5 +++ .../no/nav/klage/oppgave/util/LoggerUtils.kt | 11 ++++++ 16 files changed, 214 insertions(+) diff --git a/src/main/kotlin/no/nav/klage/dokument/clients/kabaljsontopdf/KabalJsonToPdfClient.kt b/src/main/kotlin/no/nav/klage/dokument/clients/kabaljsontopdf/KabalJsonToPdfClient.kt index bd29ac809..7610aac13 100644 --- a/src/main/kotlin/no/nav/klage/dokument/clients/kabaljsontopdf/KabalJsonToPdfClient.kt +++ b/src/main/kotlin/no/nav/klage/dokument/clients/kabaljsontopdf/KabalJsonToPdfClient.kt @@ -5,6 +5,9 @@ import no.nav.klage.dokument.clients.kabaljsontopdf.domain.DocumentValidationRes import no.nav.klage.dokument.clients.kabaljsontopdf.domain.InnholdsfortegnelseRequest import no.nav.klage.dokument.domain.PDFDocument import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -19,6 +22,7 @@ class KabalJsonToPdfClient( companion object { @Suppress("JAVA_CLASS_ON_COMPANION") private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() } fun getPDFDocument(json: String): PDFDocument { @@ -28,6 +32,9 @@ class KabalJsonToPdfClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(json) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getPDFDocument.name, secureLogger) + } .toEntity(ByteArray::class.java) .map { val filename = it.headers["filename"]?.first() @@ -47,6 +54,9 @@ class KabalJsonToPdfClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(innholdsfortegnelseRequest) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getInnholdsfortegnelse.name, secureLogger) + } .toEntity(ByteArray::class.java) .map { val filename = it.headers["filename"]?.first() @@ -65,6 +75,9 @@ class KabalJsonToPdfClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(json) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::validateJsonDocument.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Response null") } diff --git a/src/main/kotlin/no/nav/klage/dokument/clients/kabalsmarteditorapi/KabalSmartEditorApiClient.kt b/src/main/kotlin/no/nav/klage/dokument/clients/kabalsmarteditorapi/KabalSmartEditorApiClient.kt index f591a1e96..1440673ae 100644 --- a/src/main/kotlin/no/nav/klage/dokument/clients/kabalsmarteditorapi/KabalSmartEditorApiClient.kt +++ b/src/main/kotlin/no/nav/klage/dokument/clients/kabalsmarteditorapi/KabalSmartEditorApiClient.kt @@ -8,7 +8,10 @@ import no.nav.klage.dokument.clients.kabalsmarteditorapi.model.response.CommentO import no.nav.klage.dokument.clients.kabalsmarteditorapi.model.response.DocumentOutput import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -24,6 +27,7 @@ class KabalSmartEditorApiClient( companion object { @Suppress("JAVA_CLASS_ON_COMPANION") private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() } fun createDocument( @@ -38,6 +42,9 @@ class KabalSmartEditorApiClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(jsonInput) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::createDocument.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Document could not be created") } @@ -55,6 +62,9 @@ class KabalSmartEditorApiClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(jsonInput) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::updateDocument.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Document could not be updated") } @@ -69,6 +79,9 @@ class KabalSmartEditorApiClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithKabalSmartEditorApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getDocument.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Document could not be retrieved") } @@ -83,6 +96,9 @@ class KabalSmartEditorApiClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithKabalSmartEditorApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::deleteDocument.name, secureLogger) + } .bodyToMono() .block() } @@ -97,6 +113,9 @@ class KabalSmartEditorApiClient( "Bearer ${tokenUtil.getAppAccessTokenWithKabalSmartEditorApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::deleteDocumentAsSystemUser.name, secureLogger) + } .bodyToMono() .block() } @@ -114,6 +133,9 @@ class KabalSmartEditorApiClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::createComment.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Comment could not be created") } @@ -128,6 +150,9 @@ class KabalSmartEditorApiClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithKabalSmartEditorApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getAllCommentsWithPossibleThreads.name, secureLogger) + } .bodyToMono>() .block() ?: throw RuntimeException("Comments could not be retrieved") } @@ -146,6 +171,9 @@ class KabalSmartEditorApiClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::replyToComment.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Comment could not be replied to") } @@ -161,6 +189,9 @@ class KabalSmartEditorApiClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithKabalSmartEditorApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getCommentWithPossibleThread.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Comment could not be retrieved") } @@ -182,6 +213,9 @@ class KabalSmartEditorApiClient( ) ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::deleteCommentWithPossibleThread.name, secureLogger) + } .bodyToMono() .block() } @@ -200,6 +234,9 @@ class KabalSmartEditorApiClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::modifyComment.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Comment could not be modified") } diff --git a/src/main/kotlin/no/nav/klage/dokument/clients/klagefileapi/FileApiClient.kt b/src/main/kotlin/no/nav/klage/dokument/clients/klagefileapi/FileApiClient.kt index 64694fd9d..419906309 100644 --- a/src/main/kotlin/no/nav/klage/dokument/clients/klagefileapi/FileApiClient.kt +++ b/src/main/kotlin/no/nav/klage/dokument/clients/klagefileapi/FileApiClient.kt @@ -3,7 +3,10 @@ package no.nav.klage.dokument.clients.klagefileapi import io.micrometer.tracing.Tracer import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.http.client.MultipartBodyBuilder import org.springframework.stereotype.Component import org.springframework.web.reactive.function.BodyInserters @@ -19,6 +22,7 @@ class FileApiClient( companion object { @Suppress("JAVA_CLASS_ON_COMPANION") private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() } fun getDocument(id: String, systemUser: Boolean = false): ByteArray { @@ -34,6 +38,9 @@ class FileApiClient( .uri { it.path("/document/{id}").build(id) } .header(HttpHeaders.AUTHORIZATION, "Bearer $token") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getDocument.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Document could not be fetched") } @@ -53,6 +60,9 @@ class FileApiClient( .uri { it.path("/document/{id}").build(id) } .header(HttpHeaders.AUTHORIZATION, "Bearer $token") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::deleteDocument.name, secureLogger) + } .bodyToMono() .block() @@ -83,6 +93,9 @@ class FileApiClient( .header(HttpHeaders.AUTHORIZATION, "Bearer $token") .body(BodyInserters.fromMultipartData(bodyBuilder.build())) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::uploadDocument.name, secureLogger) + } .bodyToMono() .block() diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/arbeidoginntekt/ArbeidOgInntektClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/arbeidoginntekt/ArbeidOgInntektClient.kt index 4867bd312..0e84bfff9 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/arbeidoginntekt/ArbeidOgInntektClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/arbeidoginntekt/ArbeidOgInntektClient.kt @@ -2,6 +2,8 @@ package no.nav.klage.oppgave.clients.arbeidoginntekt import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse +import org.springframework.http.HttpStatusCode import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient import org.springframework.web.reactive.function.client.bodyToMono @@ -28,6 +30,9 @@ class ArbeidOgInntektClient( personIdent ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getAInntektUrl.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("No AInntekt url returned") } @@ -42,6 +47,9 @@ class ArbeidOgInntektClient( personIdent ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getAARegisterUrl.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("No AAreg url returned") } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/azure/MicrosoftGraphClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/azure/MicrosoftGraphClient.kt index f23feee8e..d3978545a 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/azure/MicrosoftGraphClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/azure/MicrosoftGraphClient.kt @@ -4,7 +4,9 @@ import no.nav.klage.oppgave.config.CacheWithJCacheConfiguration import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.cache.annotation.Cacheable +import org.springframework.http.HttpStatusCode import org.springframework.retry.annotation.Retryable import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -45,6 +47,9 @@ class MicrosoftGraphClient( }.header("Authorization", "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithGraphScope()}") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getInnloggetSaksbehandler.name, secureLogger) + } .bodyToMono() .block().let { secureLogger.debug("me: {}", it); it } ?: throw RuntimeException("AzureAD data about authenticated user could not be fetched") @@ -67,6 +72,9 @@ class MicrosoftGraphClient( .build() }.header("Authorization", "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithGraphScope()}") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getInnloggetSaksbehandlersGroups.name, secureLogger) + } .bodyToMono() .block()?.value?.map { secureLogger.debug("AD Gruppe: {}", it); it } ?: throw RuntimeException("AzureAD data about authenticated users groups could not be fetched") @@ -112,6 +120,9 @@ class MicrosoftGraphClient( .build() }.header("Authorization", "Bearer ${tokenUtil.getAppAccessTokenWithGraphScope()}") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getDisplayNames.name, secureLogger) + } .bodyToMono() } catch (e: Exception) { logger.warn("Could not fetch displayname for idents: $navIdents", e) @@ -131,6 +142,9 @@ class MicrosoftGraphClient( } .header("Authorization", "Bearer ${tokenUtil.getAppAccessTokenWithGraphScope()}") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getGroupMembersNavIdents.name, secureLogger) + } .bodyToMono().block()?.value ?: throw RuntimeException("AzureAD data about group members nav idents could not be fetched") return azureGroupMember.map { secureLogger.debug("Group member {}", it); it } @@ -153,6 +167,9 @@ class MicrosoftGraphClient( .header("Authorization", "Bearer ${tokenUtil.getAppAccessTokenWithGraphScope()}") .header("ConsistencyLevel", "eventual") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getEnhetensAnsattesNavIdents.name, secureLogger) + } .bodyToMono() .block() .let { userList -> userList?.value?.map { it.onPremisesSamAccountName } } @@ -168,6 +185,9 @@ class MicrosoftGraphClient( } .header("Authorization", "Bearer ${tokenUtil.getAppAccessTokenWithGraphScope()}") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getGroupsByUserPrincipalName.name, secureLogger) + } .bodyToMono().block()?.value?.map { secureLogger.debug("AD Gruppe by navident: {}", it); it } ?: throw RuntimeException("AzureAD data about groups by user principal name could not be fetched") return aadAzureGroups @@ -187,6 +207,9 @@ class MicrosoftGraphClient( .header("Authorization", "Bearer ${tokenUtil.getAppAccessTokenWithGraphScope()}") .header("ConsistencyLevel", "eventual") .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::findUserByNavIdent.name, secureLogger) + } .bodyToMono().block()?.value?.firstOrNull() ?.let { secureLogger.debug("Saksbehandler: {}", it); it } ?: throw RuntimeException("AzureAD data about user by nav ident could not be fetched") diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/ereg/EregClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/ereg/EregClient.kt index 18b165cce..bd17b3c1d 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/ereg/EregClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/ereg/EregClient.kt @@ -2,7 +2,11 @@ package no.nav.klage.oppgave.clients.ereg import no.nav.klage.oppgave.exceptions.EREGOrganizationNotFoundException +import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.beans.factory.annotation.Value +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -17,6 +21,12 @@ class EregClient( @Value("\${spring.application.name}") lateinit var applicationName: String + companion object { + @Suppress("JAVA_CLASS_ON_COMPANION") + private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() + } + fun hentOrganisasjon(orgnummer: String): Organisasjon { return kotlin.runCatching { eregWebClient.get() @@ -29,6 +39,9 @@ class EregClient( .accept(MediaType.APPLICATION_JSON) .header("Nav-Consumer-Id", applicationName) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::hentOrganisasjon.name, secureLogger) + } .bodyToMono() .block() ?: throw EREGOrganizationNotFoundException("Search for organization $orgnummer in Ereg returned null.") }.fold( diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/kabaldocument/KabalDocumentClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/kabaldocument/KabalDocumentClient.kt index 33d06aabb..430c501cb 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/kabaldocument/KabalDocumentClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/kabaldocument/KabalDocumentClient.kt @@ -6,7 +6,10 @@ import no.nav.klage.oppgave.clients.kabaldocument.model.response.DokumentEnhetFu import no.nav.klage.oppgave.clients.kabaldocument.model.response.DokumentEnhetOutput import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -21,6 +24,7 @@ class KabalDocumentClient( companion object { @Suppress("JAVA_CLASS_ON_COMPANION") private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() } fun createDokumentEnhetWithDokumentreferanser( @@ -35,6 +39,9 @@ class KabalDocumentClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::createDokumentEnhetWithDokumentreferanser.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Dokumentenhet could not be created") } @@ -49,6 +56,9 @@ class KabalDocumentClient( "Bearer ${tokenUtil.getAppAccessTokenWithKabalDocumentScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::fullfoerDokumentEnhet.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("DokumentEnhet could not be finalized") } @@ -68,6 +78,9 @@ class KabalDocumentClient( ) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::updateDocumentTitle.name, secureLogger) + } .bodyToMono() .block() } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/kabalinnstillinger/KabalInnstillingerClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/kabalinnstillinger/KabalInnstillingerClient.kt index be90ee2e9..cea27e340 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/kabalinnstillinger/KabalInnstillingerClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/kabalinnstillinger/KabalInnstillingerClient.kt @@ -4,7 +4,9 @@ import no.nav.klage.oppgave.clients.kabalinnstillinger.model.* import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -30,6 +32,9 @@ class KabalInnstillingerClient( "Bearer ${tokenUtil.getUserAccessTokenWithKabalInnstillingerScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getTildelteYtelserForEnhet.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Could not get tildelte ytelser for enhet $enhet") } @@ -43,6 +48,9 @@ class KabalInnstillingerClient( "Bearer ${tokenUtil.getUserAccessTokenWithKabalInnstillingerScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getSaksbehandlersTildelteYtelser.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Could not get tildelte ytelser") } @@ -58,6 +66,9 @@ class KabalInnstillingerClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::searchMedunderskrivere.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Could not search medunderskrivere") } @@ -73,6 +84,9 @@ class KabalInnstillingerClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::searchSaksbehandlere.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Could not search saksbehandlere") } @@ -88,6 +102,9 @@ class KabalInnstillingerClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::searchROL.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Could not search rol") } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/kaka/KakaApiClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/kaka/KakaApiClient.kt index 03130de99..a3dab3345 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/kaka/KakaApiClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/kaka/KakaApiClient.kt @@ -6,7 +6,9 @@ import no.nav.klage.oppgave.clients.kaka.model.response.ValidationErrors import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -34,6 +36,9 @@ class KakaApiClient( ) .contentType(MediaType.APPLICATION_JSON) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::createKvalitetsvurdering.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Kvalitetsvurdering could not be created") } @@ -48,6 +53,9 @@ class KakaApiClient( .contentType(MediaType.APPLICATION_JSON) .bodyValue(saksdataInput) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::finalizeBehandling.name, secureLogger) + } .bodyToMono() .block() } @@ -60,6 +68,9 @@ class KakaApiClient( "Bearer ${tokenUtil.getAppAccessTokenWithKakaApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::deleteKvalitetsvurderingV2.name, secureLogger) + } .bodyToMono() .block() } @@ -83,6 +94,9 @@ class KakaApiClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithKakaApiScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getValidationErrors.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Validation errors could not be retrieved") } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/klagefssproxy/KlageFssProxyClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/klagefssproxy/KlageFssProxyClient.kt index 81ddca161..72092bb06 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/klagefssproxy/KlageFssProxyClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/klagefssproxy/KlageFssProxyClient.kt @@ -3,7 +3,10 @@ package no.nav.klage.oppgave.clients.klagefssproxy import no.nav.klage.oppgave.clients.klagefssproxy.domain.* import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient import org.springframework.web.reactive.function.client.bodyToMono @@ -17,6 +20,7 @@ class KlageFssProxyClient( companion object { @Suppress("JAVA_CLASS_ON_COMPANION") private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() } fun getSak(sakId: String): SakFromKlanke { @@ -27,6 +31,9 @@ class KlageFssProxyClient( "Bearer ${tokenUtil.getOnBehalfOfTokenWithKlageFSSProxyScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getSak.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Empty result") @@ -41,6 +48,9 @@ class KlageFssProxyClient( ) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::setToHandledInKabal.name, secureLogger) + } .bodyToMono() .block() } @@ -54,6 +64,9 @@ class KlageFssProxyClient( ) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::setToFinished.name, secureLogger) + } .bodyToMono() .block() } @@ -67,6 +80,9 @@ class KlageFssProxyClient( ) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::setToAssigned.name, secureLogger) + } .bodyToMono() .block() } @@ -80,6 +96,9 @@ class KlageFssProxyClient( ) .bodyValue(input) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::setToFeilregistrertInKabal.name, secureLogger) + } .bodyToMono() .block() } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/norg2/Norg2Client.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/norg2/Norg2Client.kt index 2e83b4d18..04ec19ecc 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/norg2/Norg2Client.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/norg2/Norg2Client.kt @@ -2,7 +2,10 @@ package no.nav.klage.oppgave.clients.norg2 import no.nav.klage.oppgave.config.CacheWithJCacheConfiguration.Companion.ENHET_CACHE import no.nav.klage.oppgave.util.getLogger +import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.cache.annotation.Cacheable +import org.springframework.http.HttpStatusCode import org.springframework.retry.annotation.Retryable import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -14,6 +17,7 @@ class Norg2Client(private val norg2WebClient: WebClient) { companion object { @Suppress("JAVA_CLASS_ON_COMPANION") private val logger = getLogger(javaClass.enclosingClass) + private val secureLogger = getSecureLogger() } @Retryable @@ -23,6 +27,9 @@ class Norg2Client(private val norg2WebClient: WebClient) { norg2WebClient.get() .uri("/enhet/{enhetNr}", enhetNr) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::fetchEnhet.name, secureLogger) + } .bodyToMono() .block() ?.asEnhet() ?: throw RuntimeException("No enhet returned for enhetNr $enhetNr") diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/pdl/graphql/PdlClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/pdl/graphql/PdlClient.kt index 82b7f2fb9..7dc63b0d6 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/pdl/graphql/PdlClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/pdl/graphql/PdlClient.kt @@ -3,7 +3,9 @@ package no.nav.klage.oppgave.clients.pdl.graphql import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.retry.annotation.Retryable import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -40,6 +42,9 @@ class PdlClient( .header(HttpHeaders.AUTHORIZATION, "Bearer $stsSystembrukerToken") .bodyValue(hentPersonQuery(fnr)) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getPersonInfo.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Person not found") } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/saf/graphql/SafGraphQlClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/saf/graphql/SafGraphQlClient.kt index 18fb39c1f..3fa97d826 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/saf/graphql/SafGraphQlClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/saf/graphql/SafGraphQlClient.kt @@ -3,7 +3,9 @@ package no.nav.klage.oppgave.clients.saf.graphql import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.retry.annotation.Retryable import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient @@ -39,6 +41,9 @@ class SafGraphQlClient( ) .bodyValue(hentDokumentoversiktBrukerQuery(fnr, tema, pageSize, previousPageRef)) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getDokumentoversiktBruker.name, secureLogger) + } .bodyToMono() .block() ?.let { logErrorsFromSaf(it, fnr, pageSize, previousPageRef); it } @@ -79,6 +84,9 @@ class SafGraphQlClient( ) .bodyValue(hentJournalpostQuery(journalpostId)) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, "getJournalpostWithToken", secureLogger) + } .bodyToMono() .block() .let { if (it == null) throw RuntimeException("No response from SAF") ; it } diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/saf/rest/SafRestClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/saf/rest/SafRestClient.kt index 1b6f34380..ae14c2670 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/saf/rest/SafRestClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/saf/rest/SafRestClient.kt @@ -4,9 +4,11 @@ import io.micrometer.tracing.Tracer import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.core.io.buffer.DataBuffer import org.springframework.core.io.buffer.DataBufferUtils import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.http.MediaType import org.springframework.retry.annotation.Retryable import org.springframework.stereotype.Component @@ -50,6 +52,9 @@ class SafRestClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithSafScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::getDokument.name, secureLogger) + } .toEntity(ByteArray::class.java) .map { val type = it.headers.contentType @@ -96,6 +101,9 @@ class SafRestClient( "Bearer ${tokenUtil.getSaksbehandlerAccessTokenWithSafScope()}" ) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::downloadDocumentAsMono.name, secureLogger) + } .bodyToFlux(DataBuffer::class.java) DataBufferUtils.write(flux, pathToFile) diff --git a/src/main/kotlin/no/nav/klage/oppgave/clients/skjermede/SkjermedeApiClient.kt b/src/main/kotlin/no/nav/klage/oppgave/clients/skjermede/SkjermedeApiClient.kt index 632714625..17f301bcc 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/clients/skjermede/SkjermedeApiClient.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/clients/skjermede/SkjermedeApiClient.kt @@ -4,7 +4,9 @@ import io.micrometer.tracing.Tracer import no.nav.klage.oppgave.util.TokenUtil import no.nav.klage.oppgave.util.getLogger import no.nav.klage.oppgave.util.getSecureLogger +import no.nav.klage.oppgave.util.logErrorResponse import org.springframework.http.HttpHeaders +import org.springframework.http.HttpStatusCode import org.springframework.stereotype.Component import org.springframework.web.reactive.function.client.WebClient import org.springframework.web.reactive.function.client.bodyToMono @@ -32,6 +34,9 @@ class SkjermedeApiClient( ) .bodyValue(SkjermetRequest(personident = fnr)) .retrieve() + .onStatus(HttpStatusCode::isError) { response -> + logErrorResponse(response, ::isSkjermet.name, secureLogger) + } .bodyToMono() .block() ?: throw RuntimeException("Null response from skjermede") } diff --git a/src/main/kotlin/no/nav/klage/oppgave/util/LoggerUtils.kt b/src/main/kotlin/no/nav/klage/oppgave/util/LoggerUtils.kt index 5ace853a8..3e1bab07c 100644 --- a/src/main/kotlin/no/nav/klage/oppgave/util/LoggerUtils.kt +++ b/src/main/kotlin/no/nav/klage/oppgave/util/LoggerUtils.kt @@ -2,6 +2,8 @@ package no.nav.klage.oppgave.util import org.slf4j.Logger import org.slf4j.LoggerFactory +import org.springframework.web.reactive.function.client.ClientResponse +import reactor.core.publisher.Mono import java.util.* fun getLogger(forClass: Class<*>): Logger = LoggerFactory.getLogger(forClass) @@ -34,4 +36,13 @@ fun logMethodDetails(methodName: String, innloggetIdent: String, logger: Logger) methodName, innloggetIdent, ) +} + +fun logErrorResponse(response: ClientResponse, functionName: String, logger: Logger): Mono { + return response.bodyToMono(String::class.java).map { + val errorString = + "Got ${response.statusCode()} when requesting $functionName - response body: '$it'" + logger.error(errorString) + RuntimeException(errorString) + } } \ No newline at end of file