Skip to content

Commit

Permalink
Upgrade to Java 21 and add detekt (#385)
Browse files Browse the repository at this point in the history
  • Loading branch information
kaja-nav authored Jun 24, 2024
1 parent 86e2b10 commit c5dafba
Show file tree
Hide file tree
Showing 15 changed files with 465 additions and 96 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/build-and-deploy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ on:

jobs:
jar-app:
uses: navikt/teamesyfo-github-actions-workflows/.github/workflows/jar-app.yaml@main
uses: navikt/teamesyfo-github-actions-workflows/.github/workflows/boot-jar-app-21.yaml@main
permissions:
actions: read
contents: write
Expand Down
2 changes: 1 addition & 1 deletion Dockerfile
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
FROM gcr.io/distroless/java17
FROM gcr.io/distroless/java21
WORKDIR /app
COPY build/libs/app.jar app.jar
ENV JDK_JAVA_OPTIONS="-XX:MaxRAMPercentage=75 -Dspring.profiles.active=remote"
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ Applikasjonen pakkes til en stor jar vha. plugin Gradle Shadow og bygges med doc
lokalt på docker hvis jdbc-url legges på path.

### Lint
Kjør `./gradlew --continue ktlintCheck` eller `./gradlew ktlintFormat`
Kjør `./gradlew detekt`

### Pipeline

Expand Down
49 changes: 18 additions & 31 deletions build.gradle.kts
Original file line number Diff line number Diff line change
@@ -1,6 +1,3 @@
import com.github.jengelman.gradle.plugins.shadow.tasks.ShadowJar
import com.github.jengelman.gradle.plugins.shadow.transformers.PropertiesFileTransformer

group = "no.nav.syfo"

val apacheHttpClientVersion = "5.3.1"
Expand All @@ -17,26 +14,20 @@ val logstashVersion = "4.10"
val logbackVersion = "1.4.11"
val javaxInjectVersion = "1"
val owaspSanitizerVersion = "20211018.2"
val apacheCommonsVersion = "3.14.0"
val apacheCommonsTextVersion = "1.12.0"
val jakartaRsApiVersion = "3.1.0"
val hikari = "5.1.0"
val postgres = "42.7.3"
val postgresEmbedded = "0.13.4"
val detektVersion = "1.23.6"

plugins {
id("java")
kotlin("jvm") version "1.9.24"
id("com.github.johnrengelman.shadow") version "7.1.2"
id("org.jetbrains.kotlin.plugin.allopen") version "1.9.24"
id("org.springframework.boot") version "3.3.0"
id("io.spring.dependency-management") version "1.1.5"
id("org.jlleitschuh.gradle.ktlint") version "10.0.0"
}

allOpen {
annotation("org.springframework.context.annotation.Configuration")
annotation("org.springframework.stereotype.Service")
annotation("org.springframework.stereotype.Component")
id("io.gitlab.arturbosch.detekt") version "1.23.6"
kotlin("jvm") version "1.9.23"
kotlin("plugin.spring") version "1.9.23"
}

val githubUser: String by project
Expand Down Expand Up @@ -95,7 +86,7 @@ dependencies {
implementation("no.nav.syfo.dialogmote.avro:isdialogmote-schema:$isdialogmoteSchema")
implementation("javax.inject:javax.inject:$javaxInjectVersion")

implementation("org.apache.commons:commons-lang3:$apacheCommonsVersion")
implementation("org.apache.commons:commons-text:$apacheCommonsTextVersion")
implementation("com.googlecode.owasp-java-html-sanitizer:owasp-java-html-sanitizer:$owaspSanitizerVersion")
implementation("org.jsoup:jsoup:$jsoupVersion")
implementation("jakarta.ws.rs:jakarta.ws.rs-api:$jakartaRsApiVersion")
Expand All @@ -122,33 +113,29 @@ dependencies {
}
}
}

detektPlugins("io.gitlab.arturbosch.detekt:detekt-formatting:$detektVersion")
}

java.toolchain {
languageVersion.set(JavaLanguageVersion.of(17))
languageVersion.set(JavaLanguageVersion.of(21))
}

tasks {
extra["log4j2.version"] = "2.16.0"

withType<ShadowJar> {
manifest.attributes["Main-Class"] = "no.nav.syfo.ApplicationKt"
transform(PropertiesFileTransformer::class.java) {
paths = listOf("META-INF/spring.factories")
mergeStrategy = "append"
isZip64 = true
}
configureEach {
append("META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports")
append("META-INF/spring/org.springframework.boot.actuate.autoconfigure.web.ManagementContextConfiguration.imports")
}
mergeServiceFiles()
archiveBaseName.set("app")
archiveClassifier.set("")
archiveVersion.set("")
named<org.springframework.boot.gradle.tasks.bundling.BootJar>("bootJar") {
this.archiveFileName.set("app.jar")
}

withType<Test> {
useJUnitPlatform()
}
}

detekt {
config.from("detekt-config.yml")
buildUponDefaultConfig = true
baseline = file("detekt-baseline.xml")
}

388 changes: 388 additions & 0 deletions detekt-baseline.xml

Large diffs are not rendered by default.

6 changes: 6 additions & 0 deletions detekt-config.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
style:
MagicNumber:
active: false
config:
validation: true
warningsAsErrors: true
8 changes: 3 additions & 5 deletions src/main/kotlin/no/nav/syfo/config/ApplicationConfig.kt
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
package no.nav.syfo.config

import org.springframework.beans.factory.annotation.Qualifier
import org.springframework.context.annotation.*
import org.springframework.scheduling.TaskScheduler
import org.springframework.context.annotation.Bean
import org.springframework.context.annotation.Configuration
import org.springframework.context.annotation.Primary
import org.springframework.scheduling.annotation.EnableScheduling
import org.springframework.scheduling.concurrent.ConcurrentTaskScheduler
import org.springframework.transaction.annotation.EnableTransactionManagement
import org.springframework.web.client.RestTemplate
import org.springframework.web.reactive.function.client.WebClient
Expand All @@ -13,8 +13,6 @@ import org.springframework.web.reactive.function.client.WebClient
@EnableTransactionManagement
@EnableScheduling
class ApplicationConfig {
@Bean
fun taskScheduler(): TaskScheduler = ConcurrentTaskScheduler()

@Primary
@Bean
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,11 @@ class AzureAdV2TokenConsumer @Autowired constructor(

return tokenResponse.toAzureAdV2Token().accessToken
} catch (e: RestClientResponseException) {
log.error("Call to get AzureADV2Token from AzureAD for scope: $scopeClientId with status: ${e.rawStatusCode} and message: ${e.responseBodyAsString}", e)
log.error(
"Call to get AzureADV2Token from AzureAD for scope: $scopeClientId " +
"with status: ${e.statusCode} and message: ${e.responseBodyAsString}",
e
)
throw e
}
}
Expand Down Expand Up @@ -63,7 +67,8 @@ class AzureAdV2TokenConsumer @Autowired constructor(
azureAdToken.accessToken
} catch (e: RestClientResponseException) {
log.error(
"Call to get AzureADV2Token from AzureAD as system for scope: $scopeClientId with status: ${e.rawStatusCode} and message: ${e.responseBodyAsString}",
"Call to get AzureADV2Token from AzureAD as system for scope: $scopeClientId " +
"with status: ${e.statusCode} and message: ${e.responseBodyAsString}",
e
)
throw e
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,11 +36,11 @@ class BehandlendeEnhetConsumer(
BehandlendeEnhet::class.java
)
val responseBody = response.body!!
metric.countOutgoingReponses(METRIC_CALL_BEHANDLENDEENHET, response.statusCodeValue)
metric.countOutgoingReponses(METRIC_CALL_BEHANDLENDEENHET, response.statusCode.value())
return responseBody
} catch (e: RestClientResponseException) {
LOG.error("Error requesting BehandlendeEnhet from syfobehandlendeenhet with callId ${httpEntity.headers[NAV_CALL_ID_HEADER]}: ", e)
metric.countOutgoingReponses(METRIC_CALL_BEHANDLENDEENHET, e.rawStatusCode)
metric.countOutgoingReponses(METRIC_CALL_BEHANDLENDEENHET, e.statusCode.value())
throw e
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ class TokenDingsConsumer @Inject constructor(
return tokenX.accessToken
} catch (e: RestClientResponseException) {
log.error(
"Call to get TokenX failed with status: ${e.rawStatusCode} and message: ${e.responseBodyAsString}",
"Call to get TokenX failed with status: ${e.statusCode} and message: ${e.responseBodyAsString}",
e,
)
throw e
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,7 @@ class VeilederTilgangConsumer(
private val template: RestTemplate,
private val oidcContextHolder: TokenValidationContextHolder,
) {
private val tilgangskontrollPersonUrl: String

init {
tilgangskontrollPersonUrl = "$istilgangskontrollUrl$TILGANGSKONTROLL_PERSON_PATH"
}
private val tilgangskontrollPersonUrl: String = "$istilgangskontrollUrl$TILGANGSKONTROLL_PERSON_PATH"

fun sjekkVeiledersTilgangTilPersonMedOBO(fnr: String): Boolean {
val token = OIDCUtil.tokenFraOIDC(oidcContextHolder, OIDCIssuer.INTERN_AZUREAD_V2)
Expand All @@ -49,12 +45,12 @@ class VeilederTilgangConsumer(
if (e.statusCode.value() == 403) {
false
} else {
LOG.error("HttpClientErrorException mot istilgangskontroll med status ${e.rawStatusCode}", e)
LOG.error("HttpClientErrorException mot istilgangskontroll med status ${e.statusCode}", e)
metric.tellHendelse(METRIC_CALL_VEILEDERTILGANG_USER_FAIL)
throw e
}
} catch (e: HttpServerErrorException) {
LOG.error("HttpServerErrorException mot istilgangskontroll med status ${e.rawStatusCode}", e)
LOG.error("HttpServerErrorException mot istilgangskontroll med status ${e.statusCode}", e)
metric.tellHendelse(METRIC_CALL_VEILEDERTILGANG_USER_FAIL)
throw e
}
Expand Down
38 changes: 30 additions & 8 deletions src/main/kotlin/no/nav/syfo/metric/Metric.kt
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ import io.micrometer.core.instrument.Tags
import no.nav.syfo.motebehov.MotebehovSvar
import no.nav.syfo.motebehov.motebehovstatus.MotebehovSkjemaType
import no.nav.syfo.oppfolgingstilfelle.database.PersonOppfolgingstilfelle
import org.apache.commons.lang3.StringUtils
import org.springframework.stereotype.Controller
import java.time.LocalDate
import java.time.temporal.ChronoUnit
Expand Down Expand Up @@ -48,7 +47,12 @@ class Metric @Inject constructor(
val dayInOppfolgingstilfelleMotebehovCreated = if (activeOppfolgingstilfelle != null) {
ChronoUnit.DAYS.between(activeOppfolgingstilfelle.fom, LocalDate.now())
} else null
val navn = if (erInnloggetBrukerArbeidstaker) "syfomotebehov_motebehov_besvart_at" else "syfomotebehov_motebehov_besvart"
val navn =
if (erInnloggetBrukerArbeidstaker) {
"syfomotebehov_motebehov_besvart_at"
} else {
"syfomotebehov_motebehov_besvart"
}
registry.counter(
navn,
Tags.of(
Expand All @@ -72,7 +76,8 @@ class Metric @Inject constructor(
harForklaring: Boolean,
erInnloggetBrukerArbeidstaker: Boolean
) {
val dayInOppfolgingstilfelleMotebehovCreated = ChronoUnit.DAYS.between(activeOppfolgingstilfelle.fom, LocalDate.now())
val dayInOppfolgingstilfelleMotebehovCreated =
ChronoUnit.DAYS.between(activeOppfolgingstilfelle.fom, LocalDate.now())
val navn = if (erInnloggetBrukerArbeidstaker) {
"syfomotebehov_motebehov_besvart_oppfolgingstilfelle_dag_at"
} else "syfomotebehov_motebehov_besvart_oppfolgingstilfelle_dag_ag"
Expand All @@ -94,23 +99,38 @@ class Metric @Inject constructor(
}

fun tellMotebehovBesvartNeiAntallTegn(antallTegnIForklaring: Int, erInnloggetBrukerArbeidstaker: Boolean) {
val navn = if (erInnloggetBrukerArbeidstaker) "syfomotebehov_motebehov_besvart_nei_forklaring_lengde_at" else "syfomotebehov_motebehov_besvart_nei_forklaring_lengde"
val navn =
if (erInnloggetBrukerArbeidstaker) {
"syfomotebehov_motebehov_besvart_nei_forklaring_lengde_at"
} else {
"syfomotebehov_motebehov_besvart_nei_forklaring_lengde"
}
registry.counter(
navn,
Tags.of("type", "info")
).increment(antallTegnIForklaring.toDouble())
}

fun tellMotebehovBesvartJaMedForklaringTegn(antallTegnIForklaring: Int, erInnloggetBrukerArbeidstaker: Boolean) {
val navn = if (erInnloggetBrukerArbeidstaker) "syfomotebehov_motebehov_besvart_ja_forklaring_lengde_at" else "syfomotebehov_motebehov_besvart_ja_forklaring_lengde_ag"
val navn =
if (erInnloggetBrukerArbeidstaker) {
"syfomotebehov_motebehov_besvart_ja_forklaring_lengde_at"
} else {
"syfomotebehov_motebehov_besvart_ja_forklaring_lengde_ag"
}
registry.counter(
navn,
Tags.of("type", "info")
).increment(antallTegnIForklaring.toDouble())
}

fun tellMotebehovBesvartJaMedForklaringAntall(erInnloggetBrukerArbeidstaker: Boolean) {
val navn = if (erInnloggetBrukerArbeidstaker) "syfomotebehov_motebehov_besvart_ja_forklaring_at" else "syfomotebehov_motebehov_besvart_ja_forklaring_ag"
val navn =
if (erInnloggetBrukerArbeidstaker) {
"syfomotebehov_motebehov_besvart_ja_forklaring_at"
} else {
"syfomotebehov_motebehov_besvart_ja_forklaring_ag"
}
registry.counter(
navn,
Tags.of("type", "info")
Expand All @@ -133,6 +153,8 @@ class Metric @Inject constructor(
motebehovSvar: MotebehovSvar,
erInnloggetBrukerArbeidstaker: Boolean
) {
val harForklaring = motebehovSvar.forklaring?.isNotBlank() ?: false

tellMotebehovBesvart(
activeOppfolgingstilfelle,
motebehovSkjemaType,
Expand All @@ -143,12 +165,12 @@ class Metric @Inject constructor(
activeOppfolgingstilfelle,
motebehovSkjemaType,
motebehovSvar.harMotebehov,
!StringUtils.isEmpty(motebehovSvar.forklaring),
harForklaring,
erInnloggetBrukerArbeidstaker
)
if (!motebehovSvar.harMotebehov) {
tellMotebehovBesvartNeiAntallTegn(motebehovSvar.forklaring!!.length, erInnloggetBrukerArbeidstaker)
} else if (!StringUtils.isEmpty(motebehovSvar.forklaring)) {
} else if (harForklaring) {
tellMotebehovBesvartJaMedForklaringTegn(motebehovSvar.forklaring!!.length, erInnloggetBrukerArbeidstaker)
tellMotebehovBesvartJaMedForklaringAntall(erInnloggetBrukerArbeidstaker)
}
Expand Down
4 changes: 2 additions & 2 deletions src/main/kotlin/no/nav/syfo/util/DbUtil.kt
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
package no.nav.syfo.util

import org.apache.commons.lang3.StringEscapeUtils
import org.apache.commons.text.StringEscapeUtils
import org.owasp.html.HtmlPolicyBuilder
import org.slf4j.LoggerFactory
import java.sql.Timestamp
import java.time.*

const val MOTEBEHOVSVAR_GYLDIGHET_DAGER = 78 * 7

fun hentTidligsteDatoForGyldigMotebehovSvar(): Timestamp? {
fun hentTidligsteDatoForGyldigMotebehovSvar(): Timestamp {
return convert(LocalDateTime.of(LocalDate.now().minusDays(MOTEBEHOVSVAR_GYLDIGHET_DAGER.toLong()), LocalTime.MIN))
}

Expand Down
35 changes: 1 addition & 34 deletions src/test/kotlin/no/nav/syfo/LocalApplicationConfig.kt
Original file line number Diff line number Diff line change
@@ -1,22 +1,12 @@
package no.nav.syfo

import com.fasterxml.jackson.core.JsonProcessingException
import com.fasterxml.jackson.databind.ObjectMapper
import com.fasterxml.jackson.databind.SerializationFeature
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule
import com.opentable.db.postgres.embedded.EmbeddedPostgres
import no.nav.security.mock.oauth2.MockOAuth2Server
import no.nav.security.token.support.spring.test.MockOAuth2ServerAutoConfiguration
import no.nav.syfo.config.kafka.FunctionSerializer
import org.apache.kafka.common.serialization.StringSerializer
import org.springframework.beans.factory.annotation.Value
import org.springframework.boot.autoconfigure.kafka.KafkaProperties
import org.springframework.context.annotation.Bean
import org.springframework.context.annotation.Configuration
import org.springframework.context.annotation.Import
import org.springframework.kafka.core.DefaultKafkaProducerFactory
import org.springframework.kafka.core.KafkaTemplate
import org.springframework.kafka.core.ProducerFactory
import javax.sql.DataSource

@Configuration
Expand All @@ -30,33 +20,10 @@ class LocalApplicationConfig {
return embeddedPostgres.postgresDatabase
}

@Bean
fun kafkaTemplate(producerFactory: ProducerFactory<String, Any>): KafkaTemplate<String, Any> {
return KafkaTemplate(producerFactory)
}

@Bean
fun mockOAuthServer(@Value("\${mock.token.server.port}") mockTokenServerPort: Int): MockOAuth2Server {
var server = MockOAuth2Server()
val server = MockOAuth2Server()
server.start(mockTokenServerPort)
return server
}

@Bean
fun producerFactory(properties: KafkaProperties): ProducerFactory<String, Any> {
val objectMapper = ObjectMapper()
.registerModule(JavaTimeModule())
.configure(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS, false)
return DefaultKafkaProducerFactory(
properties.buildProducerProperties(),
StringSerializer(),
FunctionSerializer { value ->
try {
return@FunctionSerializer objectMapper.writeValueAsBytes(value)
} catch (jsonProcessingException: JsonProcessingException) {
throw RuntimeException(jsonProcessingException)
}
}
)
}
}
Loading

0 comments on commit c5dafba

Please sign in to comment.