diff options
| author | Paul-Christian Volkmer | 2026-03-10 09:01:58 +0100 |
|---|---|---|
| committer | GitHub | 2026-03-10 08:01:58 +0000 |
| commit | 1a0011765fa2d34f7d0075f463beb9e614ec8812 (patch) | |
| tree | fb55eb32700d21c3ab6da5b1e68c07a7e21e4014 /src/main | |
| parent | 48f6124e2cc27476dba8ebfb398c1b4ad8875164 (diff) | |
feat: request update audit (#258)
This adds the date and username when a request gets updated.
If the request gets updated by an async Kafka response, "SYSTEM" will be used as username.
Diffstat (limited to 'src/main')
7 files changed, 44 insertions, 3 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 cb04db3..2d520d3 100644 --- a/src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt +++ b/src/main/kotlin/dev/dnpm/etl/processor/config/AppConfiguration.kt @@ -32,8 +32,6 @@ import dev.dnpm.etl.processor.security.TokenService import dev.dnpm.etl.processor.services.ConsentProcessor import dev.dnpm.etl.processor.services.Transformation import dev.dnpm.etl.processor.services.TransformationService -import kotlin.time.Duration.Companion.seconds -import kotlin.time.toJavaDuration import org.apache.cxf.jaxws.JaxWsProxyFactoryBean import org.slf4j.LoggerFactory import org.springframework.boot.autoconfigure.condition.AnyNestedCondition @@ -46,6 +44,7 @@ import org.springframework.context.annotation.Conditional import org.springframework.context.annotation.Configuration import org.springframework.context.annotation.ConfigurationCondition import org.springframework.data.jdbc.repository.config.AbstractJdbcConfiguration +import org.springframework.data.jdbc.repository.config.EnableJdbcAuditing import org.springframework.http.converter.StringHttpMessageConverter import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter import org.springframework.retry.RetryCallback @@ -60,6 +59,8 @@ import org.springframework.security.provisioning.InMemoryUserDetailsManager import org.springframework.web.client.HttpClientErrorException import org.springframework.web.client.RestTemplate import reactor.core.publisher.Sinks +import kotlin.time.Duration.Companion.seconds +import kotlin.time.toJavaDuration @Configuration @EnableConfigurationProperties( diff --git a/src/main/kotlin/dev/dnpm/etl/processor/config/AuditConfiguration.kt b/src/main/kotlin/dev/dnpm/etl/processor/config/AuditConfiguration.kt new file mode 100644 index 0000000..45763ee --- /dev/null +++ b/src/main/kotlin/dev/dnpm/etl/processor/config/AuditConfiguration.kt @@ -0,0 +1,21 @@ +package dev.dnpm.etl.processor.config + +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.Configuration +import org.springframework.data.domain.AuditorAware +import org.springframework.data.jdbc.repository.config.EnableJdbcAuditing +import org.springframework.security.core.context.SecurityContextHolder +import java.util.* + +@Configuration +@EnableJdbcAuditing +class AuditConfiguration { + + @Bean + fun audit(): AuditorAware<String> { + return AuditorAware { + Optional.of(SecurityContextHolder.getContext().authentication?.name ?: "SYSTEM") + } + } + +} diff --git a/src/main/kotlin/dev/dnpm/etl/processor/monitoring/Request.kt b/src/main/kotlin/dev/dnpm/etl/processor/monitoring/Request.kt index 4ed071d..5dbba2b 100644 --- a/src/main/kotlin/dev/dnpm/etl/processor/monitoring/Request.kt +++ b/src/main/kotlin/dev/dnpm/etl/processor/monitoring/Request.kt @@ -20,10 +20,13 @@ package dev.dnpm.etl.processor.monitoring import dev.dnpm.etl.processor.* +import org.springframework.data.annotation.CreatedDate import java.time.Instant import java.time.temporal.ChronoUnit import java.util.* import org.springframework.data.annotation.Id +import org.springframework.data.annotation.LastModifiedBy +import org.springframework.data.annotation.LastModifiedDate import org.springframework.data.domain.Page import org.springframework.data.domain.Pageable import org.springframework.data.jdbc.repository.query.Query @@ -44,7 +47,9 @@ data class Request( @Column("submission_type") val submissionType: SubmissionType, var status: RequestStatus, @Column("tan") val tan: Tan = Tan.empty(), - var processedAt: Instant = Instant.now(), + @CreatedDate var processedAt: Instant = Instant.now(), + @LastModifiedDate var updatedAt: Instant? = null, + @LastModifiedBy var updatedBy: String? = null, @Embedded.Nullable var report: Report? = null, @Column("submission_accepted") var submissionAccepted: Boolean = false, ) { diff --git a/src/main/resources/db/migration/mariadb/V0_15_0_2__UpdatedAtBy.sql b/src/main/resources/db/migration/mariadb/V0_15_0_2__UpdatedAtBy.sql new file mode 100644 index 0000000..2005c4f --- /dev/null +++ b/src/main/resources/db/migration/mariadb/V0_15_0_2__UpdatedAtBy.sql @@ -0,0 +1,2 @@ +ALTER TABLE request ADD COLUMN updated_at datetime; +ALTER TABLE request ADD COLUMN updated_by varchar(255);
\ No newline at end of file diff --git a/src/main/resources/db/migration/postgresql/V0_15_0_2__UpdatedAtBy.sql b/src/main/resources/db/migration/postgresql/V0_15_0_2__UpdatedAtBy.sql new file mode 100644 index 0000000..ed5c807 --- /dev/null +++ b/src/main/resources/db/migration/postgresql/V0_15_0_2__UpdatedAtBy.sql @@ -0,0 +1,2 @@ +ALTER TABLE request ADD COLUMN updated_at timestamp with time zone; +ALTER TABLE request ADD COLUMN updated_by varchar(255);
\ No newline at end of file diff --git a/src/main/resources/templates/index.html b/src/main/resources/templates/index.html index cea3f73..da85025 100644 --- a/src/main/resources/templates/index.html +++ b/src/main/resources/templates/index.html @@ -75,6 +75,11 @@ <th:block th:if="${request.submissionType.value != 'unknown'}">([[ ${request.submissionType} ]])</th:block> </span> </div> + <div sec:authorize="hasRole('USER') or hasRole('ADMIN')">Letzte Aktualisierung</div> + <div sec:authorize="hasRole('USER') or hasRole('ADMIN')"> + <time th:if="${request.updatedAt}" th:datetime="${request.updatedAt}">[[ ${request.updatedAt} ]]</time> + <span th:if="${request.updatedBy}"> durch [[ ${request.updatedBy} ]]</span> + </div> <div sec:authorize="hasRole('USER') or hasRole('ADMIN')">Patienten-Pseudonym</div> <div class="patient-id" th:if="${patientPseudonym != null}" sec:authorize="hasRole('USER') or hasRole('ADMIN')"> [[ ${request.patientPseudonym} ]] diff --git a/src/main/resources/templates/report.html b/src/main/resources/templates/report.html index 1e2d97c..cd26672 100644 --- a/src/main/resources/templates/report.html +++ b/src/main/resources/templates/report.html @@ -41,6 +41,11 @@ <th:block th:if="${request.submissionType.value != 'unknown'}">([[ ${request.submissionType} ]])</th:block> </span> </div> + <div sec:authorize="hasRole('USER') or hasRole('ADMIN')">Letzte Aktualisierung</div> + <div sec:authorize="hasRole('USER') or hasRole('ADMIN')"> + <time th:if="${request.updatedAt}" th:datetime="${request.updatedAt}">[[ ${request.updatedAt} ]]</time> + <span th:if="${request.updatedBy}"> durch [[ ${request.updatedBy} ]]</span> + </div> <div sec:authorize="hasRole('USER') or hasRole('ADMIN')">Patienten-Pseudonym</div> <div class="patient-id" th:if="${patientPseudonym != null}" sec:authorize="hasRole('USER') or hasRole('ADMIN')"> [[ ${request.patientPseudonym} ]] |
