diff options
| -rw-r--r-- | src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt | 4 | ||||
| -rw-r--r-- | src/main/kotlin/dev/dnpm/etl/processor/config/AppKafkaConfiguration.kt | 9 | ||||
| -rw-r--r-- | src/main/kotlin/dev/dnpm/etl/processor/config/AppRestConfiguration.kt | 12 | ||||
| -rw-r--r-- | src/main/kotlin/dev/dnpm/etl/processor/monitoring/ConnectionCheckService.kt | 85 | ||||
| -rw-r--r-- | src/main/kotlin/dev/dnpm/etl/processor/web/ConfigController.kt (renamed from src/main/kotlin/dev/dnpm/etl/processor/web/TransformationController.kt) | 18 | ||||
| -rw-r--r-- | src/main/resources/templates/configs.html (renamed from src/main/resources/templates/transformations.html) | 35 | ||||
| -rw-r--r-- | src/main/resources/templates/fragments.html | 2 |
7 files changed, 154 insertions, 11 deletions
diff --git a/src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt b/src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt index c8e86fb..b6bedf5 100644 --- a/src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt +++ b/src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt @@ -1,7 +1,7 @@ /* * This file is part of ETL-Processor * - * Copyright (c) 2023 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors + * Copyright (c) 2024 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published @@ -32,6 +32,7 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty import org.springframework.boot.context.properties.EnableConfigurationProperties import org.springframework.context.annotation.Bean import org.springframework.context.annotation.Configuration +import org.springframework.scheduling.annotation.EnableScheduling import reactor.core.publisher.Sinks @Configuration @@ -42,6 +43,7 @@ import reactor.core.publisher.Sinks GPasConfigProperties::class ] ) +@EnableScheduling class AppConfiguration { private val logger = LoggerFactory.getLogger(AppConfiguration::class.java) diff --git a/src/main/kotlin/dev/dnpm/etl/processor/config/AppKafkaConfiguration.kt b/src/main/kotlin/dev/dnpm/etl/processor/config/AppKafkaConfiguration.kt index 309ff2d..c8fbdf5 100644 --- a/src/main/kotlin/dev/dnpm/etl/processor/config/AppKafkaConfiguration.kt +++ b/src/main/kotlin/dev/dnpm/etl/processor/config/AppKafkaConfiguration.kt @@ -1,7 +1,7 @@ /* * This file is part of ETL-Processor * - * Copyright (c) 2023 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors + * Copyright (c) 2024 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published @@ -20,6 +20,8 @@ package dev.dnpm.etl.processor.config import com.fasterxml.jackson.databind.ObjectMapper +import dev.dnpm.etl.processor.monitoring.ConnectionCheckService +import dev.dnpm.etl.processor.monitoring.KafkaConnectionCheckService import dev.dnpm.etl.processor.output.KafkaMtbFileSender import dev.dnpm.etl.processor.output.MtbFileSender import dev.dnpm.etl.processor.services.kafka.KafkaResponseProcessor @@ -76,4 +78,9 @@ class AppKafkaConfiguration { return KafkaResponseProcessor(applicationEventPublisher, objectMapper) } + @Bean + fun connectionCheckService(consumerFactory: ConsumerFactory<String, String>): ConnectionCheckService { + return KafkaConnectionCheckService(consumerFactory.createConsumer()) + } + }
\ No newline at end of file diff --git a/src/main/kotlin/dev/dnpm/etl/processor/config/AppRestConfiguration.kt b/src/main/kotlin/dev/dnpm/etl/processor/config/AppRestConfiguration.kt index a830597..2596e1c 100644 --- a/src/main/kotlin/dev/dnpm/etl/processor/config/AppRestConfiguration.kt +++ b/src/main/kotlin/dev/dnpm/etl/processor/config/AppRestConfiguration.kt @@ -1,7 +1,7 @@ /* * This file is part of ETL-Processor * - * Copyright (c) 2023 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors + * Copyright (c) 2024 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published @@ -19,6 +19,8 @@ package dev.dnpm.etl.processor.config +import dev.dnpm.etl.processor.monitoring.ConnectionCheckService +import dev.dnpm.etl.processor.monitoring.RestConnectionCheckService import dev.dnpm.etl.processor.output.MtbFileSender import dev.dnpm.etl.processor.output.RestMtbFileSender import org.slf4j.LoggerFactory @@ -54,5 +56,13 @@ class AppRestConfiguration { return RestMtbFileSender(restTemplate, restTargetProperties) } + @Bean + fun connectionCheckService( + restTemplate: RestTemplate, + restTargetProperties: RestTargetProperties + ): ConnectionCheckService { + return RestConnectionCheckService(restTemplate, restTargetProperties) + } + } diff --git a/src/main/kotlin/dev/dnpm/etl/processor/monitoring/ConnectionCheckService.kt b/src/main/kotlin/dev/dnpm/etl/processor/monitoring/ConnectionCheckService.kt new file mode 100644 index 0000000..d109326 --- /dev/null +++ b/src/main/kotlin/dev/dnpm/etl/processor/monitoring/ConnectionCheckService.kt @@ -0,0 +1,85 @@ +/* + * This file is part of ETL-Processor + * + * Copyright (c) 2024 Comprehensive Cancer Center Mainfranken, Datenintegrationszentrum Philipps-Universität Marburg and Contributors + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published + * by the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <https://www.gnu.org/licenses/>. + */ + + +package dev.dnpm.etl.processor.monitoring + +import dev.dnpm.etl.processor.config.RestTargetProperties +import jakarta.annotation.PostConstruct +import org.apache.kafka.clients.consumer.Consumer +import org.apache.kafka.common.errors.TimeoutException +import org.springframework.http.HttpStatus +import org.springframework.scheduling.annotation.Scheduled +import org.springframework.web.client.RestTemplate +import kotlin.time.Duration.Companion.seconds +import kotlin.time.toJavaDuration + +interface ConnectionCheckService { + + fun connectionAvailable(): Boolean + +} + +class KafkaConnectionCheckService( + private val consumer: Consumer<String, String> +) : ConnectionCheckService { + + private var connectionAvailable: Boolean = false + + + @PostConstruct + @Scheduled(cron = "0 * * * * *") + fun check() { + connectionAvailable = try { + null != consumer.listTopics(5.seconds.toJavaDuration()) + } catch (e: TimeoutException) { + false + } + } + + override fun connectionAvailable(): Boolean { + return this.connectionAvailable + } + +} + +class RestConnectionCheckService( + private val restTemplate: RestTemplate, + private val restTargetProperties: RestTargetProperties +) : ConnectionCheckService { + + private var connectionAvailable: Boolean = false + + @PostConstruct + @Scheduled(cron = "0 * * * * *") + fun check() { + connectionAvailable = try { + restTemplate.getForEntity( + restTargetProperties.uri?.replace("/etl/api", "").toString(), + String::class.java + ).statusCode == HttpStatus.OK + } catch (e: Exception) { + false + } + } + + override fun connectionAvailable(): Boolean { + return this.connectionAvailable + } +}
\ No newline at end of file diff --git a/src/main/kotlin/dev/dnpm/etl/processor/web/TransformationController.kt b/src/main/kotlin/dev/dnpm/etl/processor/web/ConfigController.kt index f811e9e..7bdbb82 100644 --- a/src/main/kotlin/dev/dnpm/etl/processor/web/TransformationController.kt +++ b/src/main/kotlin/dev/dnpm/etl/processor/web/ConfigController.kt @@ -19,6 +19,9 @@ package dev.dnpm.etl.processor.web +import dev.dnpm.etl.processor.monitoring.ConnectionCheckService +import dev.dnpm.etl.processor.output.MtbFileSender +import dev.dnpm.etl.processor.pseudonym.Generator import dev.dnpm.etl.processor.services.TransformationService import org.springframework.stereotype.Controller import org.springframework.ui.Model @@ -26,16 +29,23 @@ import org.springframework.web.bind.annotation.GetMapping import org.springframework.web.bind.annotation.RequestMapping @Controller -@RequestMapping(path = ["transformations"]) -class TransformationController( - private val transformationService: TransformationService +@RequestMapping(path = ["configs"]) +class ConfigController( + private val transformationService: TransformationService, + private val pseudonymGenerator: Generator, + private val mtbFileSender: MtbFileSender, + private val connectionCheckService: ConnectionCheckService + ) { @GetMapping fun index(model: Model): String { + model.addAttribute("pseudonymGenerator", pseudonymGenerator.javaClass.simpleName) + model.addAttribute("mtbFileSender", mtbFileSender.javaClass.simpleName) + model.addAttribute("connectionAvailable", connectionCheckService.connectionAvailable()) model.addAttribute("transformations", transformationService.getTransformations()) - return "transformations" + return "configs" } }
\ No newline at end of file diff --git a/src/main/resources/templates/transformations.html b/src/main/resources/templates/configs.html index b8e2f37..1d76063 100644 --- a/src/main/resources/templates/transformations.html +++ b/src/main/resources/templates/configs.html @@ -8,16 +8,45 @@ <body> <div th:replace="~{fragments.html :: nav}"></div> <main> - <h1>Transformationen</h1> + <h1>Konfiguration</h1> - <h2>Syntax</h2> + <h2>Allgemeine Konfiguration</h2> + <table> + <thead> + <tr> + <th>Name</th> + <th>Wert</th> + </tr> + </thead> + <tbody> + <tr> + <td>Pseudonym erzeugt über</td> + <td>[[ ${pseudonymGenerator} ]]</td> + </tr> + <tr> + <td>MTBFile-Sender</td> + <td>[[ ${mtbFileSender} ]]</td> + </tr> + </tbody> + </table> + + <h2><span th:if="${connectionAvailable}">✅</span><span th:if="${not(connectionAvailable)}">⚡</span> Verbindung zum bwHC-Backend</h2> + <p> + Verbindung über <code>[[ ${mtbFileSender} ]]</code>. Die Verbindung ist aktuell + <strong th:if="${connectionAvailable}" style="color: green">verfügbar.</strong> + <strong th:if="${not(connectionAvailable)}" style="color: red">nicht verfügbar!</strong> + </p> + + <h2>Transformationen</h2> + + <h3>Syntax</h3> Hier einige Beispiele zum Syntax des JSON-Path <ul> <li style="padding: 0.6rem 0;"><span class="bg-path">diagnoses[*].icdO3T.version</span>: Ersetze die ICD-O3T-Version in allen Diagnosen, z.B. zur Version der deutschen Übersetzung</li> <li style="padding: 0.6rem 0;"><span class="bg-path">patient.gender</span>: Ersetze das Geschlecht des Patienten, z.B. in das von bwHC verlangte Format</li> </ul> - <h2>Konfigurierte Transformationen</h2> + <h3>Konfigurierte Transformationen</h3> <p> Hier sehen Sie eine Übersicht der konfigurierten Transformationen. </p> diff --git a/src/main/resources/templates/fragments.html b/src/main/resources/templates/fragments.html index ea0fe1d..fbbe47d 100644 --- a/src/main/resources/templates/fragments.html +++ b/src/main/resources/templates/fragments.html @@ -10,7 +10,7 @@ <ul> <li><a th:href="@{/}">Übersicht</a></li> <li><a th:href="@{/statistics}">Statistiken</a></li> - <li><a th:href="@{/transformations}">Transformationen</a></li> + <li><a th:href="@{/configs}">Konfiguration</a></li> </ul> </nav> </div> |
