API DPE Analytics

Trois endpoints analytiques qui transforment les données DPE brutes en intelligence immobilière : prime de prix par classe énergétique, part des passoires thermiques, et évolution historique de l'écart de prix A/B vs F/G.

Ces endpoints croisent les diagnostics DPE d'ADEME (~22 M de records) avec les transactions DVF via référence cadastrale (section + no_plan). Le champ taux_couverture_dpe indique le pourcentage de transactions DVF pour lesquelles un DPE a été trouvé.

GET /v1/dpe/prix-par-classe

GET/v1/dpe/prix-par-classe10 crédits

Filtre de localisation requis : code_postal, commune, code_departement, ou latitude + longitude.

Retourne le prix médian/m² par classe énergétique (A–G) pour une zone, avec :

  • taux_couverture_dpe — part des transactions DVF pour lesquelles un DPE correspondant a été trouvé
  • prime_verte — écart relatif de chaque classe par rapport à la classe D (la référence médiane du marché). Positif = prime, négatif = décote
  • statistically_fragiletrue si la classe a moins de 30 transactions (résultat peu fiable)
prime_verte est calculé uniquement si la classe D a au moins 30 transactions comme référence. Si prime_verte est null, élargissez la zone ou supprimez le filtre type_local.
ParamètreTypeDéfautDescription
code_postalstringCode postal (ex. '69001')
communestringCommune en majuscules (ex. 'LYON', 'PARIS 15')
code_departementstringCode département (ex. '69')
type_localenumMaison | Appartement — filtre le côté DVF du croisement
annee_minintegerN'inclure que les transactions depuis cette année (ex. 2022)
curl "https://mcp.normi.fr/v1/dpe/prix-par-classe?commune=LYON&type_local=Appartement" \
  -H "X-API-Key: normi_votre_token"

Réponse

{
  "nb_transactions_avec_dpe": 1243,
  "nb_transactions_total": 1856,
  "taux_couverture_dpe": 0.670,
  "par_classe": {
    "A": { "nb": 42,  "prix_m2_median": 6200, "prix_m2_p25": 5100, "prix_m2_p75": 7400, "statistically_fragile": false },
    "B": { "nb": 128, "prix_m2_median": 5900, "prix_m2_p25": 4900, "prix_m2_p75": 7100, "statistically_fragile": false },
    "C": { "nb": 298, "prix_m2_median": 5600, "prix_m2_p25": 4700, "prix_m2_p75": 6700, "statistically_fragile": false },
    "D": { "nb": 412, "prix_m2_median": 5200, "prix_m2_p25": 4300, "prix_m2_p75": 6200, "statistically_fragile": false },
    "E": { "nb": 241, "prix_m2_median": 4800, "prix_m2_p25": 3900, "prix_m2_p75": 5700, "statistically_fragile": false },
    "F": { "nb": 89,  "prix_m2_median": 4300, "prix_m2_p25": 3500, "prix_m2_p75": 5100, "statistically_fragile": false },
    "G": { "nb": 33,  "prix_m2_median": 3900, "prix_m2_p25": 3100, "prix_m2_p75": 4700, "statistically_fragile": false }
  },
  "prime_verte": {
    "A_vs_D":  0.192,
    "B_vs_D":  0.135,
    "C_vs_D":  0.077,
    "E_vs_D": -0.077,
    "F_vs_D": -0.173,
    "G_vs_D": -0.250
  },
  "methodology": "Cadastral cross-reference of DPE diagnoses and DVF transactions...",
  "filters": { "commune": "LYON", "type_local": "Appartement", "annee_min": 2022 },
  "_credits": { "used": 10, "remaining": 490 },
  "query_time_ms": 94,
  "cache": { "hit": false, "ttl_seconds": 86400 }
}

Champs de réponse

ChampTypeDescription
nb_transactions_avec_dpenumberTransactions DVF croisées avec un DPE
nb_transactions_totalnumberToutes les transactions DVF dans la zone (hors outliers et ventes en bloc)
taux_couverture_dpenumberRatio nb_avec_dpe / nb_total (0 à 1)
par_classe.{cls}.nbnumberNombre de transactions pour cette classe
par_classe.{cls}.prix_m2_mediannumberPrix médian au m² (€)
par_classe.{cls}.prix_m2_p25number1er quartile du prix/m²
par_classe.{cls}.prix_m2_p75number3ème quartile du prix/m²
par_classe.{cls}.statistically_fragilebooleantrue si nb < 30
prime_verte.A_vs_Dnumber | nullÉcart relatif de la classe A par rapport à D (ex. 0.19 = +19%)

GET /v1/dpe/passoires-thermiques

GET/v1/dpe/passoires-thermiques10 crédits

Filtre de localisation requis : code_postal, commune, code_departement, ou latitude + longitude.

Retourne le nombre et la part des passoires thermiques (classes F et G) dans les transactions DVF récentes (2022+), avec une décomposition par type de bien et une tendance annuelle. Permet de mesurer l'impact de la loi Énergie-Climat sur le marché local.

Couvre uniquement les transactions depuis 2022 — la fenêtre la plus pertinente depuis l'entrée en vigueur des interdictions de location des logements F/G.
ParamètreTypeDéfautDescription
code_postalstringCode postal
communestringCommune en majuscules
code_departementstringCode département
type_localenumMaison | Appartement
curl "https://mcp.normi.fr/v1/dpe/passoires-thermiques?commune=BORDEAUX" \
  -H "X-API-Key: normi_votre_token"

Réponse

{
  "total_transactions_avec_dpe": 1243,
  "nb_passoires": 234,
  "pct_passoires": 18.8,
  "par_type": {
    "Appartement": { "nb": 180, "pct": 20.1 },
    "Maison":      { "nb": 54,  "pct": 14.2 }
  },
  "par_annee": [
    { "annee": 2022, "nb_passoires": 87, "pct_passoires": 21.3 },
    { "annee": 2023, "nb_passoires": 79, "pct_passoires": 19.1 },
    { "annee": 2024, "nb_passoires": 68, "pct_passoires": 16.2 }
  ],
  "_credits": { "used": 10, "remaining": 480 },
  "query_time_ms": 62
}

Champs de réponse

ChampTypeDescription
total_transactions_avec_dpenumberTotal des transactions DVF croisées (2022+)
nb_passoiresnumberTransactions avec DPE F ou G
pct_passoiresnumberPart des passoires en % du total
par_typeobjectDécomposition Appartement / Maison (nb, pct)
par_anneearrayTrend annuel depuis 2022 : annee, nb_passoires, pct_passoires

GET /v1/dpe/evolution-prime-verte

GET/v1/dpe/evolution-prime-verte10 crédits

Série temporelle annuelle de l'écart de prix entre les biens bien classés (A+B) et les passoires thermiques (F+G) depuis 2018. Permet de visualiser l'élargissement (ou non) de cet écart dans le temps — l'effet dit « prime verte » ou « décote brune ».

Seuls le code_postal et la commune sont acceptés — pas le département. À l'échelle départementale, les marchés sont trop hétérogènes pour que la comparaison A/B vs F/G soit interprétable.
Les années avec moins de 10 transactions A+B ou moins de 10 transactions F+G sont exclues de la série. Les données antérieures à juillet 2021 sont issues de l'ancienne méthode de calcul DPE (v1) et sont signalées par methodology_note: "pre-reform DPE".
ParamètreTypeDéfautDescription
code_postalstringCode postal — obligatoire si commune absent
communestringCommune — obligatoire si code_postal absent
type_localenumMaison | Appartement
curl "https://mcp.normi.fr/v1/dpe/evolution-prime-verte?commune=PARIS+15&type_local=Appartement" \
  -H "X-API-Key: normi_votre_token"

Réponse

{
  "series": [
    { "annee": 2018, "nb_AB": 45, "prix_m2_median_AB": 9800,  "nb_FG": 120, "prix_m2_median_FG": 8200,  "gap_pct": 19.5, "methodology_note": "pre-reform DPE" },
    { "annee": 2019, "nb_AB": 52, "prix_m2_median_AB": 10200, "nb_FG": 134, "prix_m2_median_FG": 8400,  "gap_pct": 21.4, "methodology_note": "pre-reform DPE" },
    { "annee": 2020, "nb_AB": 48, "prix_m2_median_AB": 10600, "nb_FG": 118, "prix_m2_median_FG": 8600,  "gap_pct": 23.3, "methodology_note": "pre-reform DPE" },
    { "annee": 2022, "nb_AB": 71, "prix_m2_median_AB": 12400, "nb_FG": 98,  "prix_m2_median_FG": 9100,  "gap_pct": 36.3, "methodology_note": null },
    { "annee": 2023, "nb_AB": 68, "prix_m2_median_AB": 12800, "nb_FG": 89,  "prix_m2_median_FG": 8800,  "gap_pct": 45.5, "methodology_note": null },
    { "annee": 2024, "nb_AB": 62, "prix_m2_median_AB": 13100, "nb_FG": 76,  "prix_m2_median_FG": 8500,  "gap_pct": 54.1, "methodology_note": null }
  ],
  "trend": "widening",
  "methodology": "Yearly median prix/m² for DPE classes A+B vs F+G...",
  "_credits": { "used": 10, "remaining": 470 },
  "query_time_ms": 118
}

Champs de réponse

ChampTypeDescription
series[].anneenumberAnnée de la transaction DVF
series[].nb_ABnumberTransactions avec DPE A ou B
series[].prix_m2_median_ABnumberPrix médian/m² des biens A+B (€)
series[].nb_FGnumberTransactions avec DPE F ou G
series[].prix_m2_median_FGnumberPrix médian/m² des biens F+G (€)
series[].gap_pctnumberÉcart relatif AB vs FG en % : (médiane_AB - médiane_FG) / médiane_FG × 100
series[].methodology_notestring | null"pre-reform DPE" pour les données avant juillet 2021
trendstring | null"widening" | "stable" | "narrowing" — calculé sur au moins 3 points