From 863d31643c04d71f8f96eebe84808ec4c07c6f16 Mon Sep 17 00:00:00 2001 From: Ugur Alpay Cenar Date: Thu, 5 Dec 2024 08:17:32 +0100 Subject: [PATCH] Oppdatere gebyr api og feilfiks andre voksne i husstanden (#628) --- .../controller/v2/GebyrController.kt | 22 +-- .../behandling/database/datamodell/Inntekt.kt | 2 +- .../behandling/database/datamodell/Rolle.kt | 1 + .../dto/v2/behandling/BehandlingDtoV2.kt | 6 +- .../dto/v2/gebyr/GebyrValideringsfeilDto.kt | 4 +- ...terManueltGebyr.kt => OppdaterGebyrDto.kt} | 12 +- .../behandling/dto/v2/inntekt/InntektDtoV2.kt | 1 + .../bidrag/behandling/service/GebyrService.kt | 61 ++++--- .../behandling/service/InntektService.kt | 3 + .../service/NotatOpplysningerService.kt | 6 +- .../transformers/BeregningDtoMapping.kt | 15 +- .../behandling/transformers/Dtomapper.kt | 20 ++- .../grunnlag/InnhentetGrunnlagMapping.kt | 4 +- .../tilvedtak/BehandlingTilVedtakMapping.kt | 10 +- .../mapping/tilvedtak/VedtakGrunnlagMapper.kt | 16 +- .../dto/v2/gebyr/GebyrValideringsfeilTest.kt | 8 +- .../behandling/service/GebyrServiceTest.kt | 150 ++++++++++++------ .../service/InntektServiceMockTest.kt | 116 +++++++++++++- .../service/VedtakserviceBidragTest.kt | 41 +++-- .../transformers/DtoMapperMockTest.kt | 23 ++- .../nav/bidrag/behandling/utils/StubUtils.kt | 11 ++ 21 files changed, 386 insertions(+), 146 deletions(-) rename src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/{OppdaterManueltGebyr.kt => OppdaterGebyrDto.kt} (53%) diff --git a/src/main/kotlin/no/nav/bidrag/behandling/controller/v2/GebyrController.kt b/src/main/kotlin/no/nav/bidrag/behandling/controller/v2/GebyrController.kt index 7978d67db..8a0e14798 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/controller/v2/GebyrController.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/controller/v2/GebyrController.kt @@ -3,12 +3,12 @@ package no.nav.bidrag.behandling.controller.v2 import io.swagger.v3.oas.annotations.Operation import io.swagger.v3.oas.annotations.security.SecurityRequirement import jakarta.validation.Valid -import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterGebyrResponsDto -import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterManueltGebyrDto +import no.nav.bidrag.behandling.dto.v2.behandling.GebyrRolleDto +import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterGebyrDto import no.nav.bidrag.behandling.service.BehandlingService import no.nav.bidrag.behandling.service.GebyrService -import no.nav.bidrag.behandling.transformers.behandling.tilDto -import no.nav.bidrag.behandling.transformers.gebyr.tilDto +import no.nav.bidrag.behandling.transformers.tilDto +import no.nav.bidrag.behandling.transformers.vedtak.mapping.tilvedtak.VedtakGrunnlagMapper import org.springframework.web.bind.annotation.PathVariable import org.springframework.web.bind.annotation.PutMapping import org.springframework.web.bind.annotation.RequestBody @@ -17,6 +17,7 @@ import org.springframework.web.bind.annotation.RequestBody class GebyrController( private val gebyrService: GebyrService, private val behandlingService: BehandlingService, + private val vedtakGrunnlagMapper: VedtakGrunnlagMapper, ) { @Suppress("unused") @PutMapping("/behandling/{behandlingsid}/gebyr") @@ -29,8 +30,8 @@ class GebyrController( @PathVariable behandlingsid: Long, @Valid @RequestBody(required = true) - request: OppdaterManueltGebyrDto, - ): OppdaterGebyrResponsDto { + request: OppdaterGebyrDto, + ): GebyrRolleDto { gebyrService.oppdaterManueltOverstyrtGebyr(behandlingService.hentBehandlingById(behandlingsid), request) return tilRespons(behandlingsid, request.rolleId) } @@ -38,13 +39,12 @@ class GebyrController( private fun tilRespons( behandlingsId: Long, rolleId: Long, - ): OppdaterGebyrResponsDto { + ): GebyrRolleDto { val behandling = behandlingService.hentBehandlingById(behandlingsId) return behandling.roller.find { it.id == rolleId }!!.let { rolle -> - OppdaterGebyrResponsDto( - rolle.tilDto(), - rolle.manueltOverstyrtGebyr?.tilDto(), - ) + vedtakGrunnlagMapper + .beregnGebyr(behandling, rolle) + .tilDto(rolle) } } } diff --git a/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Inntekt.kt b/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Inntekt.kt index a4881bf0c..fb7d1ed41 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Inntekt.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Inntekt.kt @@ -32,7 +32,7 @@ open class Inntekt( open var taMed: Boolean, @Id @GeneratedValue(strategy = GenerationType.IDENTITY) - open val id: Long? = null, + open var id: Long? = null, @ManyToOne(fetch = FetchType.EAGER) @JoinColumn(name = "behandling_id", nullable = false) open val behandling: Behandling? = null, diff --git a/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Rolle.kt b/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Rolle.kt index 2988019ce..0377da76e 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Rolle.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/database/datamodell/Rolle.kt @@ -98,6 +98,7 @@ data class RolleManueltOverstyrtGebyr( val overstyrGebyr: Boolean = true, val ilagtGebyr: Boolean? = false, val begrunnelse: String? = null, + val beregnetIlagtGebyr: Boolean? = false, ) fun Rolle.tilPersonident() = ident?.let { Personident(it) } diff --git a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/behandling/BehandlingDtoV2.kt b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/behandling/BehandlingDtoV2.kt index c8ec24ad2..c4526f917 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/behandling/BehandlingDtoV2.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/behandling/BehandlingDtoV2.kt @@ -10,7 +10,6 @@ import no.nav.bidrag.behandling.dto.v1.behandling.SivilstandDto import no.nav.bidrag.behandling.dto.v1.behandling.VirkningstidspunktDto import no.nav.bidrag.behandling.dto.v2.boforhold.BoforholdDtoV2 import no.nav.bidrag.behandling.dto.v2.gebyr.GebyrValideringsfeilDto -import no.nav.bidrag.behandling.dto.v2.gebyr.ManueltOverstyrGebyrDto import no.nav.bidrag.behandling.dto.v2.inntekt.InntekterDtoV2 import no.nav.bidrag.behandling.dto.v2.inntekt.InntektspostDtoV2 import no.nav.bidrag.behandling.dto.v2.samvær.SamværDto @@ -135,10 +134,13 @@ data class GebyrDto( data class GebyrRolleDto( val inntekt: GebyrInntektDto, val beløpGebyrsats: BigDecimal, - val manueltOverstyrtGebyr: ManueltOverstyrGebyrDto? = null, val beregnetIlagtGebyr: Boolean, + val endeligIlagtGebyr: Boolean, + val begrunnelse: String? = null, val rolle: RolleDto, ) { + val erManueltOverstyrt get() = beregnetIlagtGebyr != endeligIlagtGebyr + data class GebyrInntektDto( val skattepliktigInntekt: BigDecimal, val maksBarnetillegg: BigDecimal? = null, diff --git a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilDto.kt b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilDto.kt index 830300e4f..640018eed 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilDto.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilDto.kt @@ -11,7 +11,6 @@ fun Behandling.validerGebyr() = .map { GebyrValideringsfeilDto( gjelder = it.tilDto(), - måBestemmeGebyr = avslag != null && it.manueltOverstyrtGebyr?.ilagtGebyr == null, manglerBegrunnelse = if (it.manueltOverstyrtGebyr?.overstyrGebyr == true) { it.manueltOverstyrtGebyr?.begrunnelse.isNullOrEmpty() @@ -23,10 +22,9 @@ fun Behandling.validerGebyr() = data class GebyrValideringsfeilDto( val gjelder: RolleDto, - val måBestemmeGebyr: Boolean, val manglerBegrunnelse: Boolean, ) { @get:JsonIgnore val harFeil - get() = manglerBegrunnelse || måBestemmeGebyr + get() = manglerBegrunnelse } diff --git a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/OppdaterManueltGebyr.kt b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/OppdaterGebyrDto.kt similarity index 53% rename from src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/OppdaterManueltGebyr.kt rename to src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/OppdaterGebyrDto.kt index c5efc0f2c..a8829ad5b 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/OppdaterManueltGebyr.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/OppdaterGebyrDto.kt @@ -1,16 +1,12 @@ package no.nav.bidrag.behandling.dto.v2.gebyr import io.swagger.v3.oas.annotations.media.Schema -import no.nav.bidrag.behandling.dto.v1.behandling.RolleDto -data class OppdaterManueltGebyrDto( +data class OppdaterGebyrDto( val rolleId: Long, - val overstyrtGebyr: ManueltOverstyrGebyrDto?, -) - -data class OppdaterGebyrResponsDto( - val rolle: RolleDto, - val overstyrtGebyr: ManueltOverstyrGebyrDto?, + @Schema(description = "Om gebyr skal overstyres. Settes til motsatte verdi av beregnet verdi") + val overstyrGebyr: Boolean = false, + val begrunnelse: String? = null, ) data class ManueltOverstyrGebyrDto( diff --git a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/inntekt/InntektDtoV2.kt b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/inntekt/InntektDtoV2.kt index 040bb80a9..05a84f02a 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/inntekt/InntektDtoV2.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/dto/v2/inntekt/InntektDtoV2.kt @@ -96,6 +96,7 @@ data class OppdatereInntektRequest( data class OppdatereInntektResponse( @Schema(description = "Inntekt som ble oppdatert") val inntekt: InntektDtoV2?, + val beregnetGebyrErEndret: Boolean = false, @Schema(description = "Periodiserte inntekter") val beregnetInntekter: List = emptyList(), @Schema(description = "Oppdatert begrunnelse") diff --git a/src/main/kotlin/no/nav/bidrag/behandling/service/GebyrService.kt b/src/main/kotlin/no/nav/bidrag/behandling/service/GebyrService.kt index bdf756868..1933a7c74 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/service/GebyrService.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/service/GebyrService.kt @@ -2,13 +2,12 @@ package no.nav.bidrag.behandling.service import no.nav.bidrag.behandling.database.datamodell.Behandling import no.nav.bidrag.behandling.database.datamodell.RolleManueltOverstyrtGebyr -import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterManueltGebyrDto +import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterGebyrDto import no.nav.bidrag.behandling.transformers.tilType import no.nav.bidrag.behandling.transformers.validerSann import no.nav.bidrag.behandling.transformers.vedtak.mapping.tilvedtak.VedtakGrunnlagMapper import no.nav.bidrag.behandling.ugyldigForespørsel import no.nav.bidrag.domene.enums.behandling.TypeBehandling -import no.nav.bidrag.transport.felles.ifTrue import org.springframework.stereotype.Service import org.springframework.transaction.annotation.Transactional @@ -16,30 +15,46 @@ import org.springframework.transaction.annotation.Transactional class GebyrService( private val vedtakGrunnlagMapper: VedtakGrunnlagMapper, ) { + @Transactional + fun rekalkulerGebyr(behandling: Behandling): Boolean = + behandling + .roller + .filter { it.harGebyrsøknad } + .map { rolle -> + val beregning = vedtakGrunnlagMapper.beregnGebyr(behandling, rolle) + val manueltOverstyrtGebyr = rolle.manueltOverstyrtGebyr ?: RolleManueltOverstyrtGebyr() + val beregnetGebyrErEndret = manueltOverstyrtGebyr.beregnetIlagtGebyr != beregning.ilagtGebyr + if (beregnetGebyrErEndret) { + rolle.manueltOverstyrtGebyr = + manueltOverstyrtGebyr.copy( + overstyrGebyr = false, + ilagtGebyr = beregning.ilagtGebyr, + beregnetIlagtGebyr = beregning.ilagtGebyr, + ) + } + beregnetGebyrErEndret + }.any { it } + @Transactional fun oppdaterGebyrEtterEndringÅrsakAvslag(behandling: Behandling) { behandling .roller .filter { it.harGebyrsøknad } .forEach { rolle -> + val beregning = vedtakGrunnlagMapper.beregnGebyr(behandling, rolle) rolle.manueltOverstyrtGebyr = - (rolle.manueltOverstyrtGebyr ?: RolleManueltOverstyrtGebyr()).let { - it.copy( - overstyrGebyr = behandling.avslag != null, - ilagtGebyr = - (behandling.avslag == null).ifTrue { - val beregning = vedtakGrunnlagMapper.beregnGebyr(behandling, rolle) - !beregning.ilagtGebyr - }, - ) - } + (rolle.manueltOverstyrtGebyr ?: RolleManueltOverstyrtGebyr()).copy( + overstyrGebyr = false, + ilagtGebyr = beregning.ilagtGebyr, + beregnetIlagtGebyr = beregning.ilagtGebyr, + ) } } @Transactional fun oppdaterManueltOverstyrtGebyr( behandling: Behandling, - request: OppdaterManueltGebyrDto, + request: OppdaterGebyrDto, ) { val rolle = behandling.roller.find { it.id == request.rolleId } @@ -49,14 +64,15 @@ class GebyrService( rolle.manueltOverstyrtGebyr = (rolle.manueltOverstyrtGebyr ?: RolleManueltOverstyrtGebyr()).let { it.copy( - overstyrGebyr = request.overstyrtGebyr != null, - ilagtGebyr = request.overstyrtGebyr?.ilagtGebyr ?: (behandling.avslag == null).ifTrue { !beregning.ilagtGebyr }, - begrunnelse = request.overstyrtGebyr?.begrunnelse ?: it.begrunnelse, + overstyrGebyr = request.overstyrGebyr, + ilagtGebyr = request.overstyrGebyr != beregning.ilagtGebyr, + beregnetIlagtGebyr = beregning.ilagtGebyr, + begrunnelse = request.begrunnelse ?: it.begrunnelse, ) } } - private fun Behandling.validerOppdatering(request: OppdaterManueltGebyrDto) { + private fun Behandling.validerOppdatering(request: OppdaterGebyrDto) { val feilListe = mutableSetOf() feilListe.validerSann(tilType() == TypeBehandling.BIDRAG, "Kan bare oppdatere gebyr på en bidragsbehandling") @@ -69,13 +85,10 @@ class GebyrService( rolle.harGebyrsøknad, "Kan ikke endre gebyr på en rolle som ikke har gebyrsøknad", ) - - if (avslag == null) { - feilListe.validerSann( - request.overstyrtGebyr?.ilagtGebyr == null, - "Kan ikke sette gebyr til samme som beregnet gebyr når det ikke er avslag", - ) - } + feilListe.validerSann( + request.overstyrGebyr || request.begrunnelse.isNullOrEmpty(), + "Kan ikke sette begrunnelse hvis gebyr ikke er overstyrt", + ) if (feilListe.isNotEmpty()) { ugyldigForespørsel(feilListe.toSet().joinToString("\n")) diff --git a/src/main/kotlin/no/nav/bidrag/behandling/service/InntektService.kt b/src/main/kotlin/no/nav/bidrag/behandling/service/InntektService.kt index 41c60dec4..ae637d86a 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/service/InntektService.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/service/InntektService.kt @@ -54,6 +54,7 @@ class InntektService( private val behandlingRepository: BehandlingRepository, private val inntektRepository: InntektRepository, private val notatService: NotatService, + private val gebyrService: GebyrService, ) { @Transactional fun rekalkulerPerioderInntekter(behandlingsid: Long) { @@ -174,8 +175,10 @@ class InntektService( behandling.validerKanOppdatere() val oppdatertInntekt = oppdatereInntekt(oppdatereInntektRequest, behandling) + val beregnetGebyrErEndret = gebyrService.rekalkulerGebyr(behandling) return OppdatereInntektResponse( inntekt = oppdatertInntekt, + beregnetGebyrErEndret = beregnetGebyrErEndret, beregnetInntekter = behandling.roller .filter { it.ident == oppdatertInntekt?.ident?.verdi } diff --git a/src/main/kotlin/no/nav/bidrag/behandling/service/NotatOpplysningerService.kt b/src/main/kotlin/no/nav/bidrag/behandling/service/NotatOpplysningerService.kt index 9a13377b0..2bd5fbff5 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/service/NotatOpplysningerService.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/service/NotatOpplysningerService.kt @@ -294,11 +294,13 @@ class NotatOpplysningerService( beregnetIlagtGebyr = it.beregnetIlagtGebyr, beløpGebyrsats = it.beløpGebyrsats, manueltOverstyrtGebyr = - it.manueltOverstyrtGebyr?.let { + if (it.erManueltOverstyrt) { NotatGebyrRolleDto.NotatManueltOverstyrGebyrDto( - ilagtGebyr = it.ilagtGebyr, + ilagtGebyr = it.endeligIlagtGebyr, begrunnelse = it.begrunnelse, ) + } else { + null }, ) }, diff --git a/src/main/kotlin/no/nav/bidrag/behandling/transformers/BeregningDtoMapping.kt b/src/main/kotlin/no/nav/bidrag/behandling/transformers/BeregningDtoMapping.kt index e3d9c276d..222345ada 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/transformers/BeregningDtoMapping.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/transformers/BeregningDtoMapping.kt @@ -75,18 +75,27 @@ import java.math.BigDecimal import java.math.RoundingMode import java.time.LocalDate -fun BeregnGebyrResultat.tilDto(rolle: Rolle) = - GebyrRolleDto( +fun BeregnGebyrResultat.tilDto(rolle: Rolle): GebyrRolleDto { + val erManueltOverstyrt = rolle.manueltOverstyrtGebyr?.overstyrGebyr == true + + return GebyrRolleDto( inntekt = GebyrRolleDto.GebyrInntektDto( skattepliktigInntekt = skattepliktigInntekt, maksBarnetillegg = maksBarnetillegg, ), - manueltOverstyrtGebyr = rolle.manueltOverstyrtGebyr?.tilDto(), beregnetIlagtGebyr = ilagtGebyr, + begrunnelse = if (erManueltOverstyrt) rolle.manueltOverstyrtGebyr?.begrunnelse else null, + endeligIlagtGebyr = + if (erManueltOverstyrt) { + rolle.manueltOverstyrtGebyr!!.ilagtGebyr == true + } else { + ilagtGebyr + }, beløpGebyrsats = beløpGebyrsats, rolle = rolle.tilDto(), ) +} fun Behandling.tilInntektberegningDto(rolle: Rolle): BeregnValgteInntekterGrunnlag = BeregnValgteInntekterGrunnlag( diff --git a/src/main/kotlin/no/nav/bidrag/behandling/transformers/Dtomapper.kt b/src/main/kotlin/no/nav/bidrag/behandling/transformers/Dtomapper.kt index 3b38e7039..66c45f0c3 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/transformers/Dtomapper.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/transformers/Dtomapper.kt @@ -62,7 +62,6 @@ import no.nav.bidrag.behandling.transformers.behandling.tilKanBehandlesINyLøsni import no.nav.bidrag.behandling.transformers.behandling.toSivilstand import no.nav.bidrag.behandling.transformers.beregning.ValiderBeregning import no.nav.bidrag.behandling.transformers.boforhold.tilBostatusperiode -import no.nav.bidrag.behandling.transformers.gebyr.tilDto import no.nav.bidrag.behandling.transformers.grunnlag.tilGrunnlagsreferanse import no.nav.bidrag.behandling.transformers.samvær.tilDto import no.nav.bidrag.behandling.transformers.underhold.tilStønadTilBarnetilsynDtos @@ -393,6 +392,7 @@ class Dtomapper( grunnlag .find { Grunnlagsdatatype.BOFORHOLD_ANDRE_VOKSNE_I_HUSSTANDEN == it.type && it.erBearbeidet } .konvertereData>() + ?.sortedBy { it.periodeFom } ?.map { val periode = ÅrMånedsperiode(it.periodeFom!!, it.periodeTom) OpplysningerFraFolkeregisteretMedDetaljer( @@ -610,7 +610,7 @@ class Dtomapper( if (roller.filter { it.harGebyrsøknad }.isNotEmpty()) { GebyrDto( gebyrRoller = - roller.filter { it.harGebyrsøknad }.map { rolle -> + roller.sortedBy { it.rolletype }.filter { it.harGebyrsøknad }.map { rolle -> vedtakGrunnlagMapper .beregnGebyr(this, rolle) .tilDto(rolle) @@ -743,6 +743,7 @@ class Dtomapper( erAktivert: Boolean = true, ): List { val grunnlag = if (erAktivert) hentSisteAktiv() else hentSisteIkkeAktiv() + val behandling = firstOrNull()?.behandling ?: return emptyList() val boforholdAndreVoksneIHusstanden = grunnlag.find { it.type == Grunnlagsdatatype.BOFORHOLD_ANDRE_VOKSNE_I_HUSSTANDEN && !it.erBearbeidet } @@ -751,9 +752,19 @@ class Dtomapper( .konvertereData>() ?.filter { it.relasjon != Familierelasjon.BARN } ?.filter { + it.fødselsdato == null || + it.fødselsdato!!.withDayOfMonth(1).isBefore(behandling.virkningstidspunktEllerSøktFomDato.minusYears(18)) + }?.filter { it.borISammeHusstandDtoListe.any { p -> - val periodeBorHosBP = ÅrMånedsperiode(p.periodeFra!!, p.periodeTil?.plusMonths(1)) - periodeBorHosBP.fom <= periode.fom && periodeBorHosBP.tilEllerMax() <= periode.tilEllerMax() + val periodeBorHosBP = ÅrMånedsperiode(p.periodeFra!!.withDayOfMonth(1), p.periodeTil?.withDayOfMonth(1)?.minusDays(1)) + val periodeBPErInnenfor = + periodeBorHosBP.fom >= periode.fom && + periodeBorHosBP.til != null && + periode.til != null && + periodeBorHosBP.tilEllerMax() <= periode.tilEllerMax() + val periodeBPLøpendeErInnenfor = + periodeBorHosBP.fom >= periode.fom && periodeBorHosBP.til == null && periode.til == null + periode.omsluttesAv(periodeBorHosBP) || periodeBPErInnenfor || periodeBPLøpendeErInnenfor } }?.map { it.tilAndreVoksneIHusstandenDetaljerDto(Saksnummer(boforholdAndreVoksneIHusstanden?.behandling?.saksnummer!!)) } ?.sorter() ?: emptyList() @@ -798,6 +809,7 @@ class Dtomapper( private fun List.tilPeriodeAndreVoksneIHusstanden(erAktivert: Boolean = true): Set = find { Grunnlagsdatatype.BOFORHOLD_ANDRE_VOKSNE_I_HUSSTANDEN == it.type && it.erBearbeidet } .konvertereData>() + ?.sortedBy { it.periodeFom } ?.map { val periode = ÅrMånedsperiode(it.periodeFom!!, it.periodeTom) PeriodeAndreVoksneIHusstanden( diff --git a/src/main/kotlin/no/nav/bidrag/behandling/transformers/grunnlag/InnhentetGrunnlagMapping.kt b/src/main/kotlin/no/nav/bidrag/behandling/transformers/grunnlag/InnhentetGrunnlagMapping.kt index bfc5a1e0f..fee2066ce 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/transformers/grunnlag/InnhentetGrunnlagMapping.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/transformers/grunnlag/InnhentetGrunnlagMapping.kt @@ -312,7 +312,7 @@ private fun List.mapBarnetilsyn(personobjekter: Set) = ) }.toSet() -private fun List.mapAinntekt(personobjekter: Set) = +fun List.mapAinntekt(personobjekter: Set) = filter { it.type == Grunnlagsdatatype.SKATTEPLIKTIGE_INNTEKTER && !it.erBearbeidet } .groupBy { it.rolle.ident } .map { (ident, grunnlagListe) -> @@ -370,7 +370,7 @@ private fun List.mapUtvidetbarnetrygd(personobjekter: Set ) }.toSet() -private fun List.mapSkattegrunnlag(personobjekter: Set) = +fun List.mapSkattegrunnlag(personobjekter: Set) = filter { it.type == Grunnlagsdatatype.SKATTEPLIKTIGE_INNTEKTER && !it.erBearbeidet } .groupBy { it.rolle.ident } .flatMap { (ident, grunnlagListe) -> diff --git a/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/BehandlingTilVedtakMapping.kt b/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/BehandlingTilVedtakMapping.kt index f10498fec..87dde7629 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/BehandlingTilVedtakMapping.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/BehandlingTilVedtakMapping.kt @@ -110,9 +110,10 @@ class BehandlingTilVedtakMapping( bidragspliktig!!.harGebyrsøknad.ifTrue { val beregning = mapper.beregnGebyr(this, bidragspliktig!!, grunnlagslisteGebyr) gebyrGrunnlagsliste.addAll(beregning.grunnlagsliste) + val ilagtGebyr = beregning.ilagtGebyr OpprettEngangsbeløpRequestDto( type = Engangsbeløptype.GEBYR_SKYLDNER, - beløp = beregning.beløpGebyrsats, + beløp = if (ilagtGebyr) beregning.beløpGebyrsats else null, betaltBeløp = null, resultatkode = beregning.resultatkode.name, eksternReferanse = null, @@ -122,16 +123,17 @@ class BehandlingTilVedtakMapping( skyldner = Personident(bidragspliktig!!.ident!!), kravhaver = skyldnerNav, mottaker = skyldnerNav, - valutakode = "NOK", + valutakode = if (ilagtGebyr) "NOK" else null, sak = Saksnummer(saksnummer), ) }, bidragsmottaker!!.harGebyrsøknad.ifTrue { val beregning = mapper.beregnGebyr(this, bidragsmottaker!!, grunnlagslisteGebyr) gebyrGrunnlagsliste.addAll(beregning.grunnlagsliste) + val ilagtGebyr = beregning.ilagtGebyr OpprettEngangsbeløpRequestDto( type = Engangsbeløptype.GEBYR_MOTTAKER, - beløp = beregning.beløpGebyrsats, + beløp = if (ilagtGebyr) beregning.beløpGebyrsats else null, betaltBeløp = null, resultatkode = beregning.resultatkode.name, eksternReferanse = null, @@ -141,7 +143,7 @@ class BehandlingTilVedtakMapping( skyldner = Personident(bidragsmottaker!!.ident!!), kravhaver = skyldnerNav, mottaker = skyldnerNav, - valutakode = "NOK", + valutakode = if (ilagtGebyr) "NOK" else null, sak = Saksnummer(saksnummer), ) }, diff --git a/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/VedtakGrunnlagMapper.kt b/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/VedtakGrunnlagMapper.kt index d821875b0..50ffe75c3 100644 --- a/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/VedtakGrunnlagMapper.kt +++ b/src/main/kotlin/no/nav/bidrag/behandling/transformers/vedtak/mapping/tilvedtak/VedtakGrunnlagMapper.kt @@ -10,6 +10,7 @@ import no.nav.bidrag.behandling.service.PersonService import no.nav.bidrag.behandling.transformers.beregning.EvnevurderingBeregningResultat import no.nav.bidrag.behandling.transformers.beregning.ValiderBeregning import no.nav.bidrag.behandling.transformers.grunnlag.manglerRolleIGrunnlag +import no.nav.bidrag.behandling.transformers.grunnlag.mapAinntekt import no.nav.bidrag.behandling.transformers.grunnlag.tilGrunnlagPerson import no.nav.bidrag.behandling.transformers.grunnlag.tilGrunnlagsreferanse import no.nav.bidrag.behandling.transformers.grunnlag.valider @@ -91,10 +92,21 @@ class VedtakGrunnlagMapper( val gebyrBeregning = if (behandling.avslag != null) { beregnGebyrApi.beregnGebyr(grunnlagsliste, rolle.tilGrunnlagsreferanse()) + - mapper.run { behandling.tilGrunnlagInntektSiste12Mnd(rolle) } + mapper.run { + val grunnlagSkatteGrunnlag = behandling.tilGrunnlagInntektSiste12Mnd(rolle) + if (grunnlagSkatteGrunnlag != null) { + listOf(grunnlagSkatteGrunnlag) + + behandling.grunnlag + .toList() + .mapAinntekt(behandling.tilPersonobjekter()) + .filter { it.gjelderReferanse == rolle.tilGrunnlagsreferanse() } + } else { + emptyList() + } + } } else { beregnGebyrApi.beregnGebyr(grunnlagsliste, rolle.tilGrunnlagsreferanse()) - }.filterNotNull() + } val delberegningSumInntekt = gebyrBeregning.gebyrDelberegningSumInntekt val inntektSiste12Mnd = gebyrBeregning.finnInntektSiste12Mnd(rolle) return BeregnGebyrResultat( diff --git a/src/test/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilTest.kt b/src/test/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilTest.kt index 279cb48ac..c1bd38c50 100644 --- a/src/test/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilTest.kt +++ b/src/test/kotlin/no/nav/bidrag/behandling/dto/v2/gebyr/GebyrValideringsfeilTest.kt @@ -10,20 +10,19 @@ import org.junit.jupiter.api.Test class GebyrValideringsfeilTest { @Test - fun `skal feile validering hvis ingen begrunnelse for manuelt overstyrt gebyr`() { + fun `skal feile validering hvis ingen begrunnelse for overstyrt gebyr`() { val behandling = opprettGyldigBehandlingForBeregningOgVedtak(true, typeBehandling = TypeBehandling.BIDRAG) behandling.bidragspliktig!!.harGebyrsøknad = false val bm = behandling.bidragsmottaker!! bm.harGebyrsøknad = true - bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, null) + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, null, true) val resultat = behandling.validerGebyr() resultat.shouldHaveSize(1) resultat.first().manglerBegrunnelse shouldBe true - resultat.first().måBestemmeGebyr shouldBe false } @Test - fun `skal feile validering hvis gebyr ikke satt ved avslag`() { + fun `skal feile validering hvis gebyr begrunnelse ikke satt ved avslag`() { val behandling = opprettGyldigBehandlingForBeregningOgVedtak(true, typeBehandling = TypeBehandling.BIDRAG) behandling.avslag = Resultatkode.BIDRAGSPLIKTIG_ER_DØD behandling.bidragspliktig!!.harGebyrsøknad = false @@ -33,7 +32,6 @@ class GebyrValideringsfeilTest { val resultat = behandling.validerGebyr() resultat.shouldHaveSize(1) resultat.first().manglerBegrunnelse shouldBe true - resultat.first().måBestemmeGebyr shouldBe true } @Test diff --git a/src/test/kotlin/no/nav/bidrag/behandling/service/GebyrServiceTest.kt b/src/test/kotlin/no/nav/bidrag/behandling/service/GebyrServiceTest.kt index b0d8d76cb..fce7bd498 100644 --- a/src/test/kotlin/no/nav/bidrag/behandling/service/GebyrServiceTest.kt +++ b/src/test/kotlin/no/nav/bidrag/behandling/service/GebyrServiceTest.kt @@ -8,8 +8,7 @@ import io.mockk.junit5.MockKExtension import no.nav.bidrag.behandling.database.datamodell.Behandling import no.nav.bidrag.behandling.database.datamodell.Inntekt import no.nav.bidrag.behandling.database.datamodell.RolleManueltOverstyrtGebyr -import no.nav.bidrag.behandling.dto.v2.gebyr.ManueltOverstyrGebyrDto -import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterManueltGebyrDto +import no.nav.bidrag.behandling.dto.v2.gebyr.OppdaterGebyrDto import no.nav.bidrag.behandling.transformers.beregning.ValiderBeregning import no.nav.bidrag.behandling.transformers.vedtak.mapping.tilvedtak.BehandlingTilGrunnlagMappingV2 import no.nav.bidrag.behandling.transformers.vedtak.mapping.tilvedtak.VedtakGrunnlagMapper @@ -58,35 +57,20 @@ class GebyrServiceTest { val bm = behandling.bidragsmottaker!! gebyrService.oppdaterManueltOverstyrtGebyr( behandling, - OppdaterManueltGebyrDto( + OppdaterGebyrDto( rolleId = bm.id!!, - overstyrtGebyr = ManueltOverstyrGebyrDto(begrunnelse = "Begrunnelse"), + overstyrGebyr = true, + begrunnelse = "Begrunnelse", ), ) bm.manueltOverstyrtGebyr.shouldNotBeNull() bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe true bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" } - @Test - fun `skal feile hvis det settes gebyr for en rolle som ikke har gebyrsøknad`() { - val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) - val bm = behandling.bidragsmottaker!! - val exception = - assertThrows { - gebyrService.oppdaterManueltOverstyrtGebyr( - behandling, - OppdaterManueltGebyrDto( - rolleId = bm.id!!, - overstyrtGebyr = ManueltOverstyrGebyrDto(ilagtGebyr = false, begrunnelse = "Begrunnelse"), - ), - ) - } - exception.message shouldContain "Kan ikke sette gebyr til samme som beregnet gebyr når det ikke er avslag" - } - @Test fun `skal feile hvis gebyrvalg blir satt hvis ikke avslag`() { val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) @@ -96,9 +80,9 @@ class GebyrServiceTest { assertThrows { gebyrService.oppdaterManueltOverstyrtGebyr( behandling, - OppdaterManueltGebyrDto( + OppdaterGebyrDto( rolleId = bm.id!!, - overstyrtGebyr = ManueltOverstyrGebyrDto(begrunnelse = "Begrunnelse"), + overstyrGebyr = true, ), ) } @@ -111,15 +95,17 @@ class GebyrServiceTest { val bm = behandling.bidragsmottaker!! gebyrService.oppdaterManueltOverstyrtGebyr( behandling, - OppdaterManueltGebyrDto( + OppdaterGebyrDto( rolleId = bm.id!!, - overstyrtGebyr = ManueltOverstyrGebyrDto(begrunnelse = "Begrunnelse"), + overstyrGebyr = true, + begrunnelse = "Begrunnelse", ), ) bm.manueltOverstyrtGebyr.shouldNotBeNull() bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" } @@ -127,69 +113,93 @@ class GebyrServiceTest { fun `skal fjerne manuelt overstyrt gebyr`() { val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) val bm = behandling.bidragsmottaker!! - bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(overstyrGebyr = true, ilagtGebyr = true, begrunnelse = "Begrunnelse") + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(overstyrGebyr = true, ilagtGebyr = true, beregnetIlagtGebyr = false, begrunnelse = "Begrunnelse") gebyrService.oppdaterManueltOverstyrtGebyr( behandling, - OppdaterManueltGebyrDto( + OppdaterGebyrDto( rolleId = bm.id!!, - overstyrtGebyr = null, + overstyrGebyr = false, ), ) bm.manueltOverstyrtGebyr.shouldNotBeNull() bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false - bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" } @Test - fun `skal oppdatere uten gebyrvalg ved avslag`() { + fun `skal ikke kunne sette begrunnelse hvis ikke overstyrt`() { + val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) + val bm = behandling.bidragsmottaker!! + val exception = + assertThrows { + gebyrService.oppdaterManueltOverstyrtGebyr( + behandling, + OppdaterGebyrDto( + rolleId = bm.id!!, + overstyrGebyr = false, + begrunnelse = "Test", + ), + ) + } + exception.message shouldContain "Kan ikke sette begrunnelse hvis gebyr ikke er overstyrt" + } + + @Test + fun `skal oppdatere til defaultverdi fritatt ved avslag når ikke overstyr gebyr`() { val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) val bm = behandling.bidragsmottaker!! behandling.avslag = Resultatkode.BIDRAGSPLIKTIG_ER_DØD + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, null, true) gebyrService.oppdaterManueltOverstyrtGebyr( behandling, - OppdaterManueltGebyrDto( + OppdaterGebyrDto( rolleId = bm.id!!, - overstyrtGebyr = ManueltOverstyrGebyrDto(ilagtGebyr = null, begrunnelse = "Begrunnelse"), + overstyrGebyr = false, ), ) bm.manueltOverstyrtGebyr.shouldNotBeNull() - bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true - bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe null - bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" + bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe null } @Test - fun `skal sette gebyrvalg og begrunnelse ved avslag`() { - val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) + fun `skal sette gebyrvalg og begrunnelse ved avslag til innvilget`() { + val behandling = opprettBehandlingForGebyrberegning(BigDecimal(1000000000000)) val bm = behandling.bidragsmottaker!! behandling.avslag = Resultatkode.BIDRAGSPLIKTIG_ER_DØD gebyrService.oppdaterManueltOverstyrtGebyr( behandling, - OppdaterManueltGebyrDto( + OppdaterGebyrDto( rolleId = bm.id!!, - overstyrtGebyr = ManueltOverstyrGebyrDto(ilagtGebyr = false, begrunnelse = "Begrunnelse"), + overstyrGebyr = true, + begrunnelse = "Begrunnelse", ), ) bm.manueltOverstyrtGebyr.shouldNotBeNull() bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true - bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" } @Test - fun `skal oppdatere gebyr når det endres til avslag`() { + fun `skal oppdatere gebyr til fritatt når det endres til avslag`() { val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) val bm = behandling.bidragsmottaker!! behandling.avslag = Resultatkode.BIDRAGSPLIKTIG_ER_DØD gebyrService.oppdaterGebyrEtterEndringÅrsakAvslag(behandling) bm.manueltOverstyrtGebyr.shouldNotBeNull() - bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true - bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe null + bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe null } @@ -197,12 +207,27 @@ class GebyrServiceTest { fun `skal oppdatere gebyr når det endres til ikke avslag`() { val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) val bm = behandling.bidragsmottaker!! - bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, "Begrunnelse") + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(false, true, "Begrunnelse", true) gebyrService.oppdaterGebyrEtterEndringÅrsakAvslag(behandling) bm.manueltOverstyrtGebyr.shouldNotBeNull() bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false - bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" + } + + @Test + fun `skal oppdatere gebyr når det endres til ikke avslag hvis overstyrt`() { + val behandling = opprettBehandlingForGebyrberegning(BigDecimal(100)) + val bm = behandling.bidragsmottaker!! + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, "Begrunnelse", true) + gebyrService.oppdaterGebyrEtterEndringÅrsakAvslag(behandling) + + bm.manueltOverstyrtGebyr.shouldNotBeNull() + bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" } @@ -213,9 +238,44 @@ class GebyrServiceTest { bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, "Begrunnelse") gebyrService.oppdaterGebyrEtterEndringÅrsakAvslag(behandling) + bm.manueltOverstyrtGebyr.shouldNotBeNull() + bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" + } + + @Test + fun `skal rekalkulere men ikke oppdatere gebyr når beregnet verdi er samme`() { + val behandling = opprettBehandlingForGebyrberegning(BigDecimal(10000000)) + val bp = behandling.bidragspliktig + bp!!.harGebyrsøknad = false + val bm = behandling.bidragsmottaker!! + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, "Begrunnelse", true) + val resultat = gebyrService.rekalkulerGebyr(behandling) + + resultat shouldBe false + bm.manueltOverstyrtGebyr.shouldNotBeNull() + bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe true + bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" + } + + @Test + fun `skal rekalkulere og oppdatere gebyr når beregnet verdi er endret`() { + val behandling = opprettBehandlingForGebyrberegning(BigDecimal(1000)) + val bp = behandling.bidragspliktig + bp!!.harGebyrsøknad = false + val bm = behandling.bidragsmottaker!! + bm.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, "Begrunnelse", true) + val resultat = gebyrService.rekalkulerGebyr(behandling) + + resultat shouldBe true bm.manueltOverstyrtGebyr.shouldNotBeNull() bm.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe false bm.manueltOverstyrtGebyr!!.ilagtGebyr shouldBe false + bm.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe false bm.manueltOverstyrtGebyr!!.begrunnelse shouldBe "Begrunnelse" } } diff --git a/src/test/kotlin/no/nav/bidrag/behandling/service/InntektServiceMockTest.kt b/src/test/kotlin/no/nav/bidrag/behandling/service/InntektServiceMockTest.kt index e0d5f533a..dde7ee84c 100644 --- a/src/test/kotlin/no/nav/bidrag/behandling/service/InntektServiceMockTest.kt +++ b/src/test/kotlin/no/nav/bidrag/behandling/service/InntektServiceMockTest.kt @@ -8,12 +8,21 @@ import io.mockk.every import io.mockk.impl.annotations.MockK import io.mockk.junit5.MockKExtension import no.nav.bidrag.behandling.database.datamodell.Inntekt +import no.nav.bidrag.behandling.database.datamodell.RolleManueltOverstyrtGebyr import no.nav.bidrag.behandling.database.grunnlag.SummerteInntekter import no.nav.bidrag.behandling.database.repository.BehandlingRepository import no.nav.bidrag.behandling.database.repository.InntektRepository +import no.nav.bidrag.behandling.dto.v2.inntekt.OppdatereInntektRequest +import no.nav.bidrag.behandling.dto.v2.inntekt.OppdatereManuellInntekt +import no.nav.bidrag.behandling.transformers.beregning.ValiderBeregning +import no.nav.bidrag.behandling.transformers.vedtak.mapping.tilvedtak.BehandlingTilGrunnlagMappingV2 +import no.nav.bidrag.behandling.transformers.vedtak.mapping.tilvedtak.VedtakGrunnlagMapper import no.nav.bidrag.behandling.utils.testdata.opprettInntekt import no.nav.bidrag.behandling.utils.testdata.oppretteBehandling import no.nav.bidrag.behandling.utils.testdata.oppretteBehandlingRoller +import no.nav.bidrag.beregn.barnebidrag.BeregnGebyrApi +import no.nav.bidrag.beregn.barnebidrag.BeregnSamværsklasseApi +import no.nav.bidrag.commons.web.mock.stubSjablonService import no.nav.bidrag.domene.enums.diverse.Kilde import no.nav.bidrag.domene.enums.inntekt.Inntektsrapportering import no.nav.bidrag.domene.ident.Personident @@ -22,6 +31,8 @@ import no.nav.bidrag.transport.behandling.inntekt.response.SummertÅrsinntekt import org.junit.jupiter.api.BeforeEach import org.junit.jupiter.api.Test import org.junit.jupiter.api.extension.ExtendWith +import stubInntektRepository +import stubPersonConsumer import java.math.BigDecimal import java.time.LocalDate import java.time.YearMonth @@ -35,14 +46,26 @@ class InntektServiceMockTest { @MockK lateinit var notatService: NotatService - @MockK lateinit var inntektRepository: InntektRepository + @MockK + lateinit var evnevurderingService: BeregningEvnevurderingService + lateinit var inntektService: InntektService @BeforeEach fun initMock() { - inntektService = InntektService(behandlingRepository, inntektRepository, notatService) + inntektRepository = stubInntektRepository() + val personService = PersonService(stubPersonConsumer()) + val vedtakGrunnlagMapper = + VedtakGrunnlagMapper( + BehandlingTilGrunnlagMappingV2(personService, BeregnSamværsklasseApi(stubSjablonService())), + ValiderBeregning(), + evnevurderingService, + personService, + BeregnGebyrApi(stubSjablonService()), + ) + inntektService = InntektService(behandlingRepository, inntektRepository, notatService, GebyrService(vedtakGrunnlagMapper)) every { inntektRepository.saveAll(any()) } answers { firstArg() } } @@ -386,4 +409,93 @@ class InntektServiceMockTest { datoTom shouldBe null } } + + @Test + fun `skal oppdatere gebyr ved endring av inntekter`() { + val behandling = oppretteBehandling(1) + val virkningstidspunkt = LocalDate.now().plusMonths(4) + behandling.virkningstidspunkt = virkningstidspunkt + behandling.roller = oppretteBehandlingRoller(behandling, generateId = true) + + behandling.bidragsmottaker!!.harGebyrsøknad = true + behandling.bidragsmottaker!!.manueltOverstyrtGebyr = + RolleManueltOverstyrtGebyr( + overstyrGebyr = false, + ilagtGebyr = false, + beregnetIlagtGebyr = false, + ) + every { behandlingRepository.findBehandlingById(any()) } returns Optional.of(behandling) + val forespørselOmOppdateringAvInntekter = + OppdatereInntektRequest( + oppdatereManuellInntekt = + OppdatereManuellInntekt( + type = Inntektsrapportering.LØNN_MANUELT_BEREGNET, + beløp = BigDecimal(3052003), + datoFom = LocalDate.now().minusYears(1).withDayOfYear(1), + datoTom = + LocalDate + .now() + .minusYears(1) + .withMonth(12) + .withDayOfMonth(31), + ident = Personident(behandling.bidragsmottaker!!.ident!!), + gjelderBarn = null, + ), + ) + + // hvis + val response = + inntektService.oppdatereInntektManuelt( + behandling.id!!, + forespørselOmOppdateringAvInntekter, + ) + + response.beregnetGebyrErEndret shouldBe true + behandling.bidragsmottaker!!.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe true + } + + @Test + fun `skal ikke oppdatere gebyr ved hvis ingen endring av beregnet gebyr`() { + val behandling = oppretteBehandling(1) + val virkningstidspunkt = LocalDate.now().plusMonths(4) + behandling.virkningstidspunkt = virkningstidspunkt + behandling.roller = oppretteBehandlingRoller(behandling, generateId = true) + + behandling.bidragsmottaker!!.harGebyrsøknad = true + behandling.bidragsmottaker!!.manueltOverstyrtGebyr = + RolleManueltOverstyrtGebyr( + overstyrGebyr = true, + ilagtGebyr = false, + beregnetIlagtGebyr = true, + ) + every { behandlingRepository.findBehandlingById(any()) } returns Optional.of(behandling) + val forespørselOmOppdateringAvInntekter = + OppdatereInntektRequest( + oppdatereManuellInntekt = + OppdatereManuellInntekt( + type = Inntektsrapportering.LØNN_MANUELT_BEREGNET, + beløp = BigDecimal(3052003), + datoFom = LocalDate.now().minusYears(1).withDayOfYear(1), + datoTom = + LocalDate + .now() + .minusYears(1) + .withMonth(12) + .withDayOfMonth(31), + ident = Personident(behandling.bidragsmottaker!!.ident!!), + gjelderBarn = null, + ), + ) + + // hvis + val response = + inntektService.oppdatereInntektManuelt( + behandling.id!!, + forespørselOmOppdateringAvInntekter, + ) + + response.beregnetGebyrErEndret shouldBe false + behandling.bidragsmottaker!!.manueltOverstyrtGebyr!!.beregnetIlagtGebyr shouldBe true + behandling.bidragsmottaker!!.manueltOverstyrtGebyr!!.overstyrGebyr shouldBe true + } } diff --git a/src/test/kotlin/no/nav/bidrag/behandling/service/VedtakserviceBidragTest.kt b/src/test/kotlin/no/nav/bidrag/behandling/service/VedtakserviceBidragTest.kt index 68324ce0e..316f38bd4 100644 --- a/src/test/kotlin/no/nav/bidrag/behandling/service/VedtakserviceBidragTest.kt +++ b/src/test/kotlin/no/nav/bidrag/behandling/service/VedtakserviceBidragTest.kt @@ -90,6 +90,7 @@ import org.junit.jupiter.api.extension.ExtendWith import org.springframework.test.context.junit.jupiter.SpringExtension import stubPersonConsumer import java.math.BigDecimal +import java.time.LocalDate import java.time.YearMonth @ExtendWith(SpringExtension::class) @@ -221,7 +222,8 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { shouldHaveSize(2) val gebyrMottaker = it.find { it.type == Engangsbeløptype.GEBYR_MOTTAKER }!! - gebyrMottaker.beløp shouldBe BigDecimal(1277) + gebyrMottaker.beløp shouldBe null + gebyrMottaker.valutakode shouldBe null gebyrMottaker.kravhaver shouldBe Personident("NAV") gebyrMottaker.mottaker shouldBe Personident("NAV") gebyrMottaker.innkreving shouldBe Innkrevingstype.MED_INNKREVING @@ -237,6 +239,7 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { val gebyrSkyldner = it.find { it.type == Engangsbeløptype.GEBYR_SKYLDNER }!! gebyrSkyldner.beløp shouldBe BigDecimal(1277) + gebyrSkyldner.valutakode shouldBe "NOK" gebyrSkyldner.kravhaver shouldBe Personident("NAV") gebyrSkyldner.mottaker shouldBe Personident("NAV") gebyrSkyldner.innkreving shouldBe Innkrevingstype.MED_INNKREVING @@ -396,7 +399,7 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { shouldHaveSize(2) val gebyrMottaker = it.find { it.type == Engangsbeløptype.GEBYR_MOTTAKER }!! - gebyrMottaker.beløp shouldBe BigDecimal(1277) + gebyrMottaker.beløp shouldBe null gebyrMottaker.kravhaver shouldBe Personident("NAV") gebyrMottaker.mottaker shouldBe Personident("NAV") gebyrMottaker.innkreving shouldBe Innkrevingstype.MED_INNKREVING @@ -842,7 +845,8 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { it.any { it.type == Engangsbeløptype.GEBYR_MOTTAKER }.shouldBeTrue() it.any { it.type == Engangsbeløptype.GEBYR_SKYLDNER }.shouldBeTrue() assertSoftly(it.find { it.type == Engangsbeløptype.GEBYR_MOTTAKER }!!) { - beløp shouldBe BigDecimal(1277) + beløp shouldBe null + valutakode shouldBe null kravhaver shouldBe Personident("NAV") mottaker shouldBe Personident("NAV") innkreving shouldBe Innkrevingstype.MED_INNKREVING @@ -854,6 +858,7 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { } assertSoftly(it.find { it.type == Engangsbeløptype.GEBYR_SKYLDNER }!!) { beløp shouldBe BigDecimal(1277) + valutakode shouldBe "NOK" kravhaver shouldBe Personident("NAV") mottaker shouldBe Personident("NAV") innkreving shouldBe Innkrevingstype.MED_INNKREVING @@ -891,11 +896,13 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { behandling.inntekter.add( Inntekt( belop = BigDecimal(90000), - datoFom = behandling.virkningstidspunkt, + datoFom = null, datoTom = null, - ident = behandling.bidragsmottaker!!.ident!!, + ident = behandling.bidragspliktig!!.ident!!, taMed = false, - kilde = Kilde.MANUELL, + opprinneligFom = LocalDate.parse("2023-02-01"), + opprinneligTom = LocalDate.parse("2024-01-31"), + kilde = Kilde.OFFENTLIG, behandling = behandling, type = Inntektsrapportering.AINNTEKT_BEREGNET_12MND, id = 1, @@ -935,35 +942,39 @@ class VedtakserviceBidragTest : CommonVedtakTilBehandlingTest() { it.any { it.type == Engangsbeløptype.GEBYR_MOTTAKER }.shouldBeTrue() it.any { it.type == Engangsbeløptype.GEBYR_SKYLDNER }.shouldBeTrue() - assertSoftly(it.find { it.type == Engangsbeløptype.GEBYR_MOTTAKER }!!) { + assertSoftly(it.find { it.type == Engangsbeløptype.GEBYR_SKYLDNER }!!) { beløp shouldBe BigDecimal(1277) + valutakode shouldBe "NOK" kravhaver shouldBe Personident("NAV") mottaker shouldBe Personident("NAV") innkreving shouldBe Innkrevingstype.MED_INNKREVING - resultatkode shouldBe Resultatkode.GEBYR_FRITTATT.name + resultatkode shouldBe Resultatkode.GEBYR_ILAGT.name sak shouldBe Saksnummer(SAKSNUMMER) - skyldner shouldBe Personident(testdataBM.ident) + skyldner shouldBe Personident(testdataBP.ident) grunnlagReferanseListe shouldHaveSize 2 opprettVedtakRequest.grunnlagListe.validerHarReferanseTilGrunnlagIReferanser(Grunnlagstype.SLUTTBEREGNING_GEBYR, grunnlagReferanseListe) opprettVedtakRequest.grunnlagListe.validerHarReferanseTilGrunnlagIReferanser(Grunnlagstype.INNTEKT_RAPPORTERING_PERIODE, grunnlagReferanseListe) val sluttberegningGebyrBM = opprettVedtakRequest.grunnlagListe.finnGrunnlagSomErReferertFraGrunnlagsreferanseListe(Grunnlagstype.SLUTTBEREGNING_GEBYR, grunnlagReferanseListe).firstOrNull() - sluttberegningGebyrBM!!.gjelderReferanse shouldBe behandling.bidragsmottaker!!.tilGrunnlagsreferanse() + sluttberegningGebyrBM!!.gjelderReferanse shouldBe behandling.bidragspliktig!!.tilGrunnlagsreferanse() sluttberegningGebyrBM.grunnlagsreferanseListe shouldHaveSize 2 + opprettVedtakRequest.grunnlagListe.filter { it.type == Grunnlagstype.INNHENTET_INNTEKT_AINNTEKT }.shouldHaveSize(1) + opprettVedtakRequest.grunnlagListe.filter { it.type == Grunnlagstype.INNHENTET_INNTEKT_AINNTEKT && it.gjelderReferanse == behandling.bidragspliktig!!.tilGrunnlagsreferanse() }.shouldHaveSize(1) opprettVedtakRequest.grunnlagListe.validerHarReferanseTilGrunnlagIReferanser(Grunnlagstype.MANUELT_OVERSTYRT_GEBYR, sluttberegningGebyrBM.grunnlagsreferanseListe) opprettVedtakRequest.grunnlagListe.validerHarReferanseTilSjablonIReferanser(SjablonTallNavn.FASTSETTELSESGEBYR_BELØP, sluttberegningGebyrBM.grunnlagsreferanseListe) } - assertSoftly(it.find { it.type == Engangsbeløptype.GEBYR_SKYLDNER }!!) { - beløp shouldBe BigDecimal(1277) + assertSoftly(it.find { it.type == Engangsbeløptype.GEBYR_MOTTAKER }!!) { + beløp shouldBe null + valutakode shouldBe null kravhaver shouldBe Personident("NAV") mottaker shouldBe Personident("NAV") innkreving shouldBe Innkrevingstype.MED_INNKREVING - resultatkode shouldBe Resultatkode.GEBYR_ILAGT.name + resultatkode shouldBe Resultatkode.GEBYR_FRITTATT.name sak shouldBe Saksnummer(SAKSNUMMER) - skyldner shouldBe Personident(testdataBP.ident) + skyldner shouldBe Personident(testdataBM.ident) grunnlagReferanseListe shouldHaveSize 1 opprettVedtakRequest.grunnlagListe.validerHarReferanseTilGrunnlagIReferanser(Grunnlagstype.SLUTTBEREGNING_GEBYR, grunnlagReferanseListe) val sluttberegningGebyrBP = opprettVedtakRequest.grunnlagListe.finnGrunnlagSomErReferertFraGrunnlagsreferanseListe(Grunnlagstype.SLUTTBEREGNING_GEBYR, grunnlagReferanseListe).firstOrNull() - sluttberegningGebyrBP!!.gjelderReferanse shouldBe behandling.bidragspliktig!!.tilGrunnlagsreferanse() + sluttberegningGebyrBP!!.gjelderReferanse shouldBe behandling.bidragsmottaker!!.tilGrunnlagsreferanse() sluttberegningGebyrBP.grunnlagsreferanseListe shouldHaveSize 2 opprettVedtakRequest.grunnlagListe.validerHarReferanseTilGrunnlagIReferanser(Grunnlagstype.MANUELT_OVERSTYRT_GEBYR, sluttberegningGebyrBP.grunnlagsreferanseListe) opprettVedtakRequest.grunnlagListe.validerHarReferanseTilSjablonIReferanser(SjablonTallNavn.FASTSETTELSESGEBYR_BELØP, sluttberegningGebyrBP.grunnlagsreferanseListe) diff --git a/src/test/kotlin/no/nav/bidrag/behandling/transformers/DtoMapperMockTest.kt b/src/test/kotlin/no/nav/bidrag/behandling/transformers/DtoMapperMockTest.kt index d560aaca6..fa0fce3b4 100644 --- a/src/test/kotlin/no/nav/bidrag/behandling/transformers/DtoMapperMockTest.kt +++ b/src/test/kotlin/no/nav/bidrag/behandling/transformers/DtoMapperMockTest.kt @@ -139,14 +139,12 @@ class DtoMapperMockTest { it.inntekt.maksBarnetillegg shouldBe BigDecimal(20000) it.inntekt.totalInntekt shouldBe BigDecimal(920000) it.beregnetIlagtGebyr shouldBe true - it.manueltOverstyrtGebyr.shouldBeNull() } assertSoftly(gebyr.gebyrRoller.find { it.rolle.rolletype == Rolletype.BIDRAGSPLIKTIG }!!) { it.inntekt.skattepliktigInntekt shouldBe BigDecimal(20000) it.inntekt.maksBarnetillegg shouldBe null it.inntekt.totalInntekt shouldBe BigDecimal(20000) it.beregnetIlagtGebyr shouldBe false - it.manueltOverstyrtGebyr.shouldBeNull() } } @@ -193,16 +191,14 @@ class DtoMapperMockTest { it.inntekt.maksBarnetillegg shouldBe null it.inntekt.totalInntekt shouldBe BigDecimal(50000) it.beregnetIlagtGebyr shouldBe false - it.manueltOverstyrtGebyr.shouldNotBeNull() - it.manueltOverstyrtGebyr.ilagtGebyr shouldBe true - it.manueltOverstyrtGebyr.begrunnelse shouldBe "Begrunnelse" + it.endeligIlagtGebyr shouldBe true + it.begrunnelse shouldBe "Begrunnelse" } assertSoftly(gebyr.gebyrRoller.find { it.rolle.rolletype == Rolletype.BIDRAGSPLIKTIG }!!) { it.inntekt.skattepliktigInntekt shouldBe BigDecimal(500000) it.inntekt.maksBarnetillegg shouldBe BigDecimal(2000) it.inntekt.totalInntekt shouldBe BigDecimal(502000) it.beregnetIlagtGebyr shouldBe true - it.manueltOverstyrtGebyr.shouldBeNull() } } @@ -249,7 +245,8 @@ class DtoMapperMockTest { ), ) - behandling.bidragsmottaker!!.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, false, "Begrunnelse") + behandling.bidragsmottaker!!.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(false, false, "Begrunnelse") + behandling.bidragspliktig!!.manueltOverstyrtGebyr = RolleManueltOverstyrtGebyr(true, true, null) val behandlingDto = dtomapper.tilDto(behandling) behandlingDto.shouldNotBeNull() @@ -259,25 +256,25 @@ class DtoMapperMockTest { gebyr.valideringsfeil!!.shouldHaveSize(1) assertSoftly(gebyr.valideringsfeil.first()) { it.gjelder.rolletype shouldBe Rolletype.BIDRAGSPLIKTIG - it.måBestemmeGebyr shouldBe true - it.manglerBegrunnelse shouldBe false + it.manglerBegrunnelse shouldBe true it.harFeil shouldBe true } assertSoftly(gebyr.gebyrRoller.find { it.rolle.rolletype == Rolletype.BIDRAGSMOTTAKER }!!) { it.inntekt.skattepliktigInntekt shouldBe BigDecimal(90000) it.inntekt.maksBarnetillegg shouldBe null it.inntekt.totalInntekt shouldBe BigDecimal(90000) + it.endeligIlagtGebyr shouldBe false it.beregnetIlagtGebyr shouldBe false - it.manueltOverstyrtGebyr.shouldNotBeNull() - it.manueltOverstyrtGebyr.ilagtGebyr shouldBe false - it.manueltOverstyrtGebyr.begrunnelse shouldBe "Begrunnelse" + it.erManueltOverstyrt shouldBe false + it.begrunnelse shouldBe null } assertSoftly(gebyr.gebyrRoller.find { it.rolle.rolletype == Rolletype.BIDRAGSPLIKTIG }!!) { it.inntekt.skattepliktigInntekt shouldBe BigDecimal(0) it.inntekt.maksBarnetillegg shouldBe null it.inntekt.totalInntekt shouldBe BigDecimal(0) it.beregnetIlagtGebyr shouldBe false - it.manueltOverstyrtGebyr.shouldBeNull() + it.endeligIlagtGebyr shouldBe true + it.begrunnelse shouldBe null } } } diff --git a/src/test/kotlin/no/nav/bidrag/behandling/utils/StubUtils.kt b/src/test/kotlin/no/nav/bidrag/behandling/utils/StubUtils.kt index 908f796a8..b608a4edf 100644 --- a/src/test/kotlin/no/nav/bidrag/behandling/utils/StubUtils.kt +++ b/src/test/kotlin/no/nav/bidrag/behandling/utils/StubUtils.kt @@ -22,9 +22,11 @@ import no.nav.bidrag.behandling.consumer.BidragPersonConsumer import no.nav.bidrag.behandling.consumer.ForsendelseResponsTo import no.nav.bidrag.behandling.consumer.OpprettForsendelseRespons import no.nav.bidrag.behandling.database.datamodell.Behandling +import no.nav.bidrag.behandling.database.datamodell.Inntekt import no.nav.bidrag.behandling.database.datamodell.Person import no.nav.bidrag.behandling.database.datamodell.Rolle import no.nav.bidrag.behandling.database.datamodell.Underholdskostnad +import no.nav.bidrag.behandling.database.repository.InntektRepository import no.nav.bidrag.behandling.database.repository.PersonRepository import no.nav.bidrag.behandling.database.repository.UnderholdskostnadRepository import no.nav.bidrag.behandling.service.PersonService @@ -110,6 +112,15 @@ fun stubUnderholdskostnadRepository(underholdskostnadRepository: Underholdskostn return underholdskostnadRepository } +fun stubInntektRepository(inntektRepository: InntektRepository = mockkClass(InntektRepository::class)): InntektRepository { + every { inntektRepository.save(any()) }.answers { + val inntekt = firstArg() + inntekt.id = inntekt.id ?: 1 + inntekt + } + return inntektRepository +} + fun stubPersonConsumer(): BidragPersonConsumer { try { clearMocks(BidragPersonConsumer::class)