Skip to content

Commit

Permalink
Legge til type til feltListMap (#1172)
Browse files Browse the repository at this point in the history
Beskrivelse:
Vi ønsker å ha en måte å skille hvordan enkelte deler av pdf-kvitteringen skal se ut og at det skal sende med informasjon fra søknaden.

Løsning:
Lagt til en type i feltlisteMap med tabell barn
  • Loading branch information
SandraLekve authored Nov 8, 2024
1 parent fea9ec0 commit d3b9148
Show file tree
Hide file tree
Showing 6 changed files with 954 additions and 6 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,176 @@
package no.nav.familie.ef.mottak.service

import no.nav.familie.ef.mottak.repository.domain.Ettersending
import no.nav.familie.kontrakter.ef.søknad.Adresse
import no.nav.familie.kontrakter.ef.søknad.Datoperiode
import no.nav.familie.kontrakter.ef.søknad.Dokumentasjon
import no.nav.familie.kontrakter.ef.søknad.MånedÅrPeriode
import no.nav.familie.kontrakter.ef.søknad.SkjemaForArbeidssøker
import no.nav.familie.kontrakter.ef.søknad.SøknadBarnetilsyn
import no.nav.familie.kontrakter.ef.søknad.SøknadOvergangsstønad
import no.nav.familie.kontrakter.ef.søknad.SøknadSkolepenger
import no.nav.familie.kontrakter.ef.søknad.Søknadsfelt
import no.nav.familie.kontrakter.felles.Fødselsnummer
import java.time.LocalDate
import java.time.LocalDateTime
import java.time.Month
import java.time.format.DateTimeFormatter
import kotlin.reflect.KClass
import kotlin.reflect.KParameter
import kotlin.reflect.KProperty1
import kotlin.reflect.KVisibility
import kotlin.reflect.full.declaredMemberProperties
import kotlin.reflect.full.primaryConstructor

object SøknadTilGenereltFormatMapper {
private val endNodes =
setOf<KClass<*>>(
String::class,
Int::class,
Boolean::class,
Double::class,
Dokumentasjon::class,
Fødselsnummer::class,
MånedÅrPeriode::class,
Datoperiode::class,
Adresse::class,
LocalDate::class,
LocalDateTime::class,
Month::class,
Long::class,
)

fun mapOvergangsstønad(
knad: SøknadOvergangsstønad,
vedleggTitler: List<String>,
): Map<String, Any> {
val finnFelter = finnFelter(søknad)
val vedlegg = feltlisteMap("Vedlegg", listOf(Feltformaterer.mapVedlegg(vedleggTitler)))
return feltlisteMap("Søknad om overgangsstønad (NAV 15-00.01)", finnFelter + vedlegg)
}

fun mapBarnetilsyn(
knad: SøknadBarnetilsyn,
vedleggTitler: List<String>,
): Map<String, Any> {
val finnFelter = finnFelter(søknad)
val vedlegg = feltlisteMap("Vedlegg", listOf(Feltformaterer.mapVedlegg(vedleggTitler)))
return feltlisteMap("Søknad om stønad til barnetilsyn (NAV 15-00.02)", finnFelter + vedlegg)
}

fun mapSkolepenger(
knad: SøknadSkolepenger,
vedleggTitler: List<String>,
): Map<String, Any> {
val finnFelter = finnFelter(søknad)
val vedlegg = feltlisteMap("Vedlegg", listOf(Feltformaterer.mapVedlegg(vedleggTitler)))
return feltlisteMap("Søknad om stønad til skolepenger (NAV 15-00.04)", finnFelter + vedlegg)
}

fun mapSkjemafelter(skjema: SkjemaForArbeidssøker): Map<String, Any> {
val finnFelter = finnFelter(skjema)
return feltlisteMap("Skjema for arbeidssøker - 15-08.01", finnFelter)
}

fun mapEttersending(
ettersending: Ettersending,
vedleggTitler: List<String>,
): Map<String, Any> {
val infoMap =
feltlisteMap(
"Ettersending av vedlegg",
listOf(
Feltformaterer.feltMap("Stønadstype", ettersending.stønadType),
Feltformaterer.feltMap("Fødselsnummer", ettersending.fnr),
Feltformaterer.feltMap(
"Dato mottatt",
ettersending.opprettetTid.format(DateTimeFormatter.ofPattern("dd.MM.yyyy HH:mm:ss")),
),
),
)
val vedleggMap = feltlisteMap("Dokumenter vedlagt", listOf(Feltformaterer.mapVedlegg(vedleggTitler)))
return feltlisteMap("Ettersending", listOf(infoMap, vedleggMap))
}

private fun finnFelter(entitet: Any): List<Map<String, *>> {
// Det går ikke å hente elementene i en liste med reflection, så vi traverserer den som vanlig.
if (entitet is List<Any?>) {
return entitet
.filterNotNull()
.map { finnFelter(it) }
.flatten()
}
val parametere = konstruktørparametere(entitet)

val list =
parametere
.asSequence()
.map { finnSøknadsfelt(entitet, it) }
.filter { it.visibility == KVisibility.PUBLIC }
.mapNotNull { getFeltverdi(it, entitet) }
.map { finnFelter(it) } // Kall rekursivt videre
.flatten()
.toList()

if (entitet is Søknadsfelt<*>) {
if (entitet.verdi!! is Dokumentasjon) {
@Suppress("UNCHECKED_CAST")
return listOf(mapDokumentasjon(entitet as Søknadsfelt<Dokumentasjon>))
}
if (entitet.verdi!!::class in endNodes) {
return listOf(Feltformaterer.mapEndenodeTilUtskriftMap(entitet))
}
if (entitet.label == "Barna dine") {
return listOf(feltlisteMap(entitet.label, list, VisningsVariant.TABELL_BARN))
}
if (entitet.verdi is List<*>) {
val verdiliste = entitet.verdi as List<*>
if (verdiliste.isNotEmpty() && verdiliste.first() is String) {
return listOf(Feltformaterer.mapEndenodeTilUtskriftMap(entitet))
}
}
return listOf(feltlisteMap(entitet.label, list))
}
return list
}

private fun mapDokumentasjon(entitet: Søknadsfelt<Dokumentasjon>): Map<String, *> = feltlisteMap(entitet.label, listOf(Feltformaterer.mapEndenodeTilUtskriftMap(entitet.verdi.harSendtInnTidligere)))

private fun feltlisteMap(
label: String,
verdi: List<*>,
type: VisningsVariant? = null,
): Map<String, Any> =
if (type == null) {
mapOf("label" to label, "verdiliste" to verdi)
} else {
mapOf("label" to label, "type" to type.visningsVariantName, "verdiliste" to verdi)
}

/**
* Henter ut verdien for felt på entitet.
*/
private fun getFeltverdi(
felt: KProperty1<out Any, Any?>,
entitet: Any,
) = felt.getter.call(entitet)

/**
* Finn første (og eneste) felt på entiteten som har samme navn som konstruktørparameter.
*/
private fun finnSøknadsfelt(
entity: Any,
konstruktørparameter: KParameter,
) = entity::class.declaredMemberProperties.first { it.name == konstruktørparameter.name }

/**
* Konstruktørparametere er det eneste som gir oss en garantert rekkefølge for feltene, så vi henter disse først.
*/
private fun konstruktørparametere(entity: Any) = entity::class.primaryConstructor?.parameters ?: emptyList()
}

enum class VisningsVariant(
val visningsVariantName: String,
) {
TABELL_BARN("Tabell Barn"),
}
Original file line number Diff line number Diff line change
Expand Up @@ -39,19 +39,19 @@ class SøknadskvitteringService(
when (innsending.dokumenttype) {
DOKUMENTTYPE_OVERGANGSSTØNAD -> {
val dto = SøknadMapper.toDto<SøknadOvergangsstønad>(innsending)
SøknadTreeWalker.mapOvergangsstønad(dto, vedleggTitler)
SøknadTilGenereltFormatMapper.mapOvergangsstønad(dto, vedleggTitler)
}
DOKUMENTTYPE_BARNETILSYN -> {
val dto = SøknadMapper.toDto<SøknadBarnetilsyn>(innsending)
SøknadTreeWalker.mapBarnetilsyn(dto, vedleggTitler)
SøknadTilGenereltFormatMapper.mapBarnetilsyn(dto, vedleggTitler)
}
DOKUMENTTYPE_SKJEMA_ARBEIDSSØKER -> {
val dto = SøknadMapper.toDto<SkjemaForArbeidssøker>(innsending)
SøknadTreeWalker.mapSkjemafelter(dto)
SøknadTilGenereltFormatMapper.mapSkjemafelter(dto)
}
DOKUMENTTYPE_SKOLEPENGER -> {
val dto = SøknadMapper.toDto<SøknadSkolepenger>(innsending)
SøknadTreeWalker.mapSkolepenger(dto, vedleggTitler)
SøknadTilGenereltFormatMapper.mapSkolepenger(dto, vedleggTitler)
}
else -> {
error("Ukjent eller manglende dokumenttype id: ${innsending.id}")
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
package no.nav.familie.ef.mottak.service

import no.nav.familie.ef.mottak.encryption.EncryptedString
import no.nav.familie.ef.mottak.no.nav.familie.ef.mottak.util.IOTestUtil
import no.nav.familie.ef.mottak.repository.domain.Ettersending
import no.nav.familie.kontrakter.felles.objectMapper
import org.assertj.core.api.Assertions
import org.junit.jupiter.api.Test
import java.time.LocalDateTime

class SøknadTilGenereltFormatMapperTest {
@Test
fun `mapSøknadsfelter returnerer en map-struktur med feltene fra søknaden`() {
val søknad = Testdata.søknadOvergangsstønad

val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapOvergangsstønad(søknad, emptyList())

Assertions.assertThat(mapSøknadsfelter).isNotEmpty
Assertions.assertThat(mapSøknadsfelter["label"]).isEqualTo("Søknad om overgangsstønad (NAV 15-00.01)")

val verdiliste = mapSøknadsfelter["verdiliste"] as List<*>
Assertions.assertThat(verdiliste).hasSize(12)
}

@Test
fun `mapSøknadsfelter returnerer en map-struktur med typen 'Barn Tabel'`() {
val søknad = Testdata.søknadOvergangsstønad

val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapOvergangsstønad(søknad, emptyList())

val verdiliste = mapSøknadsfelter["verdiliste"] as List<Map<String, Any>>

val harVisningsVariantBarn = verdiliste.any { it["type"] == "Tabell Barn" }
Assertions.assertThat(harVisningsVariantBarn).isTrue
}

@Test
fun `mapSøknadsfelter returnerer en map-struktur med feltene fra søknaden sammen med vedlegg`() {
val søknad = Testdata.søknadOvergangsstønad

val vedlegg = listOf("Dokumentasjon på at du er syk")
val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapOvergangsstønad(søknad, vedlegg)

Assertions.assertThat(mapSøknadsfelter).isNotEmpty
Assertions.assertThat(mapSøknadsfelter["label"]).isEqualTo("Søknad om overgangsstønad (NAV 15-00.01)")
Assertions.assertThat(mapSøknadsfelter["verdiliste"] as List<Any?>).hasSize(12)
}

@Test
fun `mapSøknadsfelter returnerer en map-struktur med feltene fra skolepengesøknaden sammen med vedlegg`() {
val søknad = Testdata.søknadSkolepenger

val vedlegg = listOf("Dokumentasjon på at du er syk")
val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapSkolepenger(søknad, vedlegg)

Assertions.assertThat(mapSøknadsfelter).isNotEmpty
Assertions.assertThat(mapSøknadsfelter["label"]).isEqualTo("Søknad om stønad til skolepenger (NAV 15-00.04)")
Assertions.assertThat(mapSøknadsfelter["verdiliste"] as List<Any?>).hasSize(9)
}

@Test
fun `mapSkjemafelter returnerer en map-struktur med feltene fra skjema`() {
val skjemaForArbeidssøker = Testdata.skjemaForArbeidssøker

val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapSkjemafelter(skjemaForArbeidssøker)

Assertions.assertThat(mapSøknadsfelter).isNotEmpty
Assertions.assertThat(mapSøknadsfelter["label"]).isEqualTo("Skjema for arbeidssøker - 15-08.01")
Assertions.assertThat(mapSøknadsfelter["verdiliste"] as List<Any?>).hasSize(3)
}

@Test
fun `mapSøknadsfelter printer pdf for å se endringer i pdf-genereringen i PR - overgangsstønad`() {
val søknad = Testdata.søknadOvergangsstønad

val vedlegg =
listOf(
"Dokumentasjon på at du er syk",
"Dokumentasjon på at du er syk",
"Dokumentasjon på at kan arbeide",
)
val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapOvergangsstønad(søknad, vedlegg)
generatePdfAndAssert(mapSøknadsfelter, "pdf_generated_overgangsstønad_med_typer.json")
}

@Test
fun `mapSøknadsfelter printer pdf for å se endringer i pdf-genereringen i PR - skolepenger`() {
val søknad = Testdata.søknadSkolepenger

val vedlegg = listOf("Utgifter til utdanning")
val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapSkolepenger(søknad, vedlegg)
generatePdfAndAssert(mapSøknadsfelter, "pdf_generated_skolepenger.json")
}

@Test
fun `mapSøknadsfelter printer pdf for å se endringer i pdf-genereringen i PR - barnetilsyn`() {
val søknad = Testdata.søknadBarnetilsyn

val vedlegg =
listOf(
"Dokumentasjon på at du er syk",
"Dokumentasjon på at du er syk",
"Dokumentasjon på at kan arbeide",
)
val mapSøknadsfelter = SøknadTilGenereltFormatMapper.mapBarnetilsyn(søknad, vedlegg)
generatePdfAndAssert(mapSøknadsfelter, "pdf_generated_barnetilsyn.json")
}

@Test
fun `map ettersending med vedlegg`() {
val mapEttersending =
SøknadTilGenereltFormatMapper.mapEttersending(
Ettersending(
stønadType = "OVERGANGSSTØNAD",
fnr = "23118612345",
ettersendingJson = EncryptedString(""),
opprettetTid = LocalDateTime.of(2021, 5, 1, 12, 0),
),
listOf("Lærlingkontrakt", "Utgifter til pass av barn"),
)

generatePdfAndAssert(mapEttersending, "pdf_generated_ettersending.json")
}

private fun generatePdfAndAssert(
mapSøknadsfelter: Map<String, Any>,
filename: String,
) {
val pdf = objectMapper.writerWithDefaultPrettyPrinter().writeValueAsString(mapSøknadsfelter)
// kommentere ut for å skrive over fila
// java.nio.file.Files.write(java.nio.file.Path.of("src/test/resources/json/$filename"), pdf.toByteArray())
Assertions.assertThat(pdf).isEqualToIgnoringWhitespace(IOTestUtil.readFile(filename))
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ internal object Testdata {
Søknadsfelt("Opphold i Norge", medlemskapsdetaljer()),
Søknadsfelt("Bosituasjonen din", bosituasjon()),
Søknadsfelt("Sivilstandsplaner", sivilstandsplaner()),
Søknadsfelt("Barn", listOf(barn())),
Søknadsfelt("Barna dine", listOf(barn())),
Søknadsfelt("Arbeid, utdanning og andre aktiviteter", aktivitet()),
Søknadsfelt("Mer om situasjonen din", situasjon()),
Søknadsfelt("Når søker du stønad fra?", stønadsstart()),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@
]
},
{
"label": "Barn",
"label": "Barna dine",
"verdiliste": [
{
"label": "Barnets fulle navn, hvis dette er bestemt",
Expand Down
Loading

0 comments on commit d3b9148

Please sign in to comment.