-
Notifications
You must be signed in to change notification settings - Fork 101
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Amélioration récupération du CSV pour le Bail Réel solidaire (#2429)
- Loading branch information
Showing
3 changed files
with
71 additions
and
62 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
121 changes: 60 additions & 61 deletions
121
openfisca_france/model/prestations/bail_reel_solidaire.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,81 +1,80 @@ | ||
from openfisca_france.model.base import * | ||
import os | ||
import openfisca_france | ||
import csv | ||
import codecs | ||
import pkg_resources | ||
import numpy as np | ||
|
||
|
||
def load_zonage_file(period, parameters): | ||
chemin_fichier_zonage_abc = os.path.join(parameters(period).prestations_sociales.bail_reel_solidaire.parametres_generaux.fichier_zonage[0]) | ||
def bail_reel_solidaire_zones_elligibles(): | ||
with pkg_resources.resource_stream(openfisca_france.__name__, 'assets/zonage-communes/zonage-abc-juillet-2024.csv') as csv_file: | ||
utf8_reader = codecs.getreader('utf-8') | ||
csv_reader = csv.DictReader(utf8_reader(csv_file), delimiter=';') | ||
return { | ||
row['CODGEO']: row['Zone en vigueur depuis le 5 juillet 2024'] | ||
for row in csv_reader | ||
} | ||
|
||
if not os.path.exists(chemin_fichier_zonage_abc): | ||
return None | ||
|
||
with open(chemin_fichier_zonage_abc, 'r', encoding='utf-8') as csvfile: | ||
csv_reader = csv.DictReader(csvfile, delimiter=';') | ||
return {row['CODGEO']: row['Zone en vigueur depuis le 5 juillet 2024'] for row in csv_reader} | ||
|
||
|
||
def plafond_par_zone_et_composition(nb_personnes, plafonds_par_zones, zone): | ||
plafond_zone = plafonds_par_zones[f'zone_{zone}'] | ||
|
||
tranches_composition = range(1, 7) | ||
conditions_nb_personnes = [ | ||
nb_personnes == i if i < 6 else nb_personnes >= i | ||
for i in tranches_composition | ||
] | ||
|
||
plafonds_revenus = [ | ||
plafond_zone[f'nb_personnes_{i}'] | ||
for i in tranches_composition | ||
] | ||
|
||
return select(conditions_nb_personnes, plafonds_revenus) | ||
|
||
class bail_reel_solidaire_zones_menage(Variable): | ||
value_type = str | ||
label = 'Zone du ménage pour le Bail Réel Solidaire' | ||
entity = Menage | ||
definition_period = MONTH | ||
|
||
def plafond_supplementaire_par_zone(nb_personnes, plafonds_par_zones, zone, nb_personnes_max): | ||
return where( | ||
nb_personnes > nb_personnes_max, | ||
(nb_personnes - nb_personnes_max) * plafonds_par_zones[f'zone_{zone}']['nb_personnes_supplementaires'], | ||
0 | ||
) | ||
def formula(menage, period): | ||
depcom = menage('depcom', period) | ||
return np.fromiter( | ||
(bail_reel_solidaire_zones_elligibles().get(depcom_cell.decode('utf-8')) for depcom_cell in depcom), | ||
dtype='<U4' # String length max for zones (A, Abis, B1, B2, C) | ||
) | ||
|
||
|
||
class bail_reel_solidaire(Variable): | ||
class bail_reel_solidaire_plafond_total(Variable): | ||
value_type = float | ||
label = 'Plafond de ressources total du Bail Réel Solidaire' | ||
entity = Menage | ||
value_type = bool | ||
reference = [ | ||
'https://www.legifrance.gouv.fr/jorf/id/JORFTEXT000032918488', | ||
'https://www.legifrance.gouv.fr/loda/id/JORFTEXT000000437021' | ||
] | ||
label = 'Bail réel solidaire' | ||
definition_period = MONTH | ||
|
||
def formula(menage, period, parameters): | ||
parametres = parameters(period).prestations_sociales.bail_reel_solidaire.parametres_generaux | ||
zones_abc_eligibles = parametres.zones_abc_eligibles | ||
nb_personnes_max = parametres.nombre_personnes_maximum | ||
|
||
zones_par_depcom = load_zonage_file(period, parameters) | ||
if not zones_par_depcom: | ||
return False | ||
|
||
params = parameters(period).prestations_sociales.bail_reel_solidaire | ||
zones_abc_eligibles = params.parametres_generaux.zones_abc_eligibles | ||
plafonds_par_zones = params.plafonds_par_zones | ||
zones_menage = menage('bail_reel_solidaire_zones_menage', period) | ||
nb_personnes = menage.nb_persons() | ||
depcom = menage('depcom', period.first_month) | ||
zones_menage = np.array([zones_par_depcom.get(d.decode('utf-8'), None) for d in depcom]) | ||
|
||
plafonds_par_zones = parameters(period).prestations_sociales.bail_reel_solidaire.plafonds_par_zones | ||
|
||
plafond_revenu_base = select( | ||
nb_personnes_max = params.parametres_generaux.nombre_personnes_maximum | ||
|
||
def calcul_plafonds_zone(zone): | ||
plafond_zone = plafonds_par_zones[f'zone_{zone}'] | ||
plafond_base = select( | ||
[nb_personnes == i if i < 6 else nb_personnes >= i for i in range(1, 7)], | ||
[plafond_zone[f'nb_personnes_{i}'] for i in range(1, 7)] | ||
) | ||
plafond_supp = where( | ||
nb_personnes > nb_personnes_max, | ||
(nb_personnes - nb_personnes_max) * plafond_zone.nb_personnes_supplementaires, | ||
0 | ||
) | ||
return plafond_base + plafond_supp | ||
|
||
return select( | ||
[zones_menage == zone for zone in zones_abc_eligibles], | ||
[plafond_par_zone_et_composition(nb_personnes, plafonds_par_zones, zone) for zone in zones_abc_eligibles] | ||
[calcul_plafonds_zone(zone) for zone in zones_abc_eligibles] | ||
) | ||
|
||
plafond_revenu_supplementaire = select( | ||
[zones_menage == zone for zone in zones_abc_eligibles], | ||
[plafond_supplementaire_par_zone(nb_personnes, plafonds_par_zones, zone, nb_personnes_max) for zone in zones_abc_eligibles] | ||
) | ||
|
||
rfr = menage.sum(menage.members.foyer_fiscal( | ||
'rfr', period.n_2), role=FoyerFiscal.DECLARANT_PRINCIPAL) | ||
class bail_reel_solidaire(Variable): | ||
value_type = bool | ||
label = 'Éligibilité au Bail Réel Solidaire' | ||
entity = Menage | ||
definition_period = MONTH | ||
reference = [ | ||
'https://www.legifrance.gouv.fr/jorf/id/JORFTEXT000032918488', | ||
'https://www.legifrance.gouv.fr/loda/id/JORFTEXT000000437021' | ||
] | ||
|
||
return where(zones_menage is not None, rfr <= (plafond_revenu_base + plafond_revenu_supplementaire), False) | ||
def formula(menage, period): | ||
plafond_total = menage('bail_reel_solidaire_plafond_total', period) | ||
zones_menage = menage('bail_reel_solidaire_zones_menage', period) | ||
rfr = menage.sum(menage.members.foyer_fiscal('rfr', period.n_2), role=FoyerFiscal.DECLARANT_PRINCIPAL) | ||
return where(zones_menage is not None, rfr <= plafond_total, False) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters