{
  "profile": "tabular-data-package",
  "name": "energy-class-asking-prices",
  "title": "Advertised homes and asking prices by energy class, Luxembourg and border regions",
  "description": "How the homes advertised for sale and for rent in Luxembourg and in the neighbouring areas of France, Belgium (Wallonia) and Germany are distributed across energy-performance classes, and what they ask per square metre in each class. Each country keeps its own certificate scheme and headline indicator: the Luxembourg CPE primary-energy class (A+ to I), the French DPE energy-consumption class (A to G), the Walloon PEB class (A++ to G) and the German Energieausweis class (A+ to H). Letters are never pooled or converted across schemes. A listing whose class is missing, on another axis or outside its scheme's scale counts as not stated, and not-stated rows are published so the gap stays visible. The source is a one-day snapshot of the public ChatHome catalogue of active listings, which ChatHome collects from estate-agency websites. Counts and shares need at least 5 listings, because smaller counts are unreliable; the adverts are public and this is not a confidentiality guarantee, as a hidden count can sometimes be worked out from the shares. Median, 25th and 75th percentile asking prices per m² and new-build shares need at least 10. A second table gives the class mix by Luxembourg canton. The shares describe advertised stock on the snapshot date. They are not the national certificate registers and not the housing stock.",
  "version": "2026.10",
  "created": "2026-10-18T22:40:40.398Z",
  "homepage": "https://chathome.lu/en/data/energy-class-asking-prices",
  "licenses": [
    {
      "name": "CC-BY-4.0",
      "path": "https://creativecommons.org/licenses/by/4.0/",
      "title": "Creative Commons Attribution 4.0 International"
    }
  ],
  "contributors": [
    {
      "title": "ChatHome",
      "role": "publisher",
      "path": "https://chathome.lu",
      "email": "hello@chathome.lu"
    }
  ],
  "sources": [
    {
      "title": "ChatHome public listing catalogue: active residential listings collected from estate-agency websites",
      "path": "https://chathome.lu"
    },
    {
      "title": "Administration du cadastre et de la topographie / Geoportail Luxembourg: Limites administratives du Grand-Duché de Luxembourg (official commune codes) (CC0 1.0)",
      "path": "https://data.public.lu/fr/datasets/limites-administratives-du-grand-duche-de-luxembourg/"
    }
  ],
  "keywords": [
    "Luxembourg",
    "Greater Region",
    "energy performance certificate",
    "energy class",
    "CPE",
    "DPE",
    "PEB",
    "Energieausweis",
    "asking prices",
    "housing",
    "open data"
  ],
  "resources": [
    {
      "name": "energy_class_asking_prices",
      "path": "energy_class_asking_prices.csv",
      "title": "Advertised homes and asking prices by energy class",
      "description": "Apartments (studios included) and houses advertised for sale or rent on the snapshot date, by country, tenure, property type and energy-performance class, with each class's share and its asking price per m². The class is the one each country's certificate states on its headline scale: Luxembourg CPE primary energy, French DPE energy consumption, Walloon PEB overall performance, German Energieausweis overall performance. Values on another indicator or off the scheme's scale count as not_stated. Letters are not comparable across countries. Rooms, colocations, multi-unit buildings and land are excluded. Price per m² is the asking price (or monthly base rent) divided by the living area, kept only for areas of 10–2,000 m², sale prices of 500–40,000 EUR/m² and rents of 3–120 EUR/m² a month; listings outside these bands still count in class shares, because their class is known, but not in price statistics. Asking prices are not transaction prices. Every class of the scale and not_stated is listed for each country, tenure and type with at least one listing, so absence is explicit. Grain: one row per country × tenure × property type × energy class (every class of the country's scale, plus not_stated).",
      "profile": "tabular-data-resource",
      "format": "csv",
      "mediatype": "text/csv",
      "encoding": "utf-8",
      "bytes": 16486,
      "hash": "sha256:c4ed99a3f8731f66cfb14545659180a7a4b56d26605bbb625a0d96a7c887cd43",
      "schema": {
        "fields": [
          {
            "name": "snapshot_date",
            "type": "string",
            "description": "Date the catalog was read (YYYY-MM-DD, UTC)."
          },
          {
            "name": "country",
            "type": "string",
            "description": "ISO country of the home: LU, FR, BE or DE."
          },
          {
            "name": "energy_scheme",
            "type": "string",
            "description": "Certificate scheme: LU_CPE, FR_DPE, BE_WAL_PEB or DE_ENERGIEAUSWEIS."
          },
          {
            "name": "indicator",
            "type": "string",
            "description": "The scheme's headline indicator used for the class: primary_energy (LU), energy_consumption (FR), overall_performance (BE, DE)."
          },
          {
            "name": "tenure",
            "type": "string",
            "description": "sale or rent."
          },
          {
            "name": "property_type",
            "type": "string",
            "description": "apartment (studios included) or house."
          },
          {
            "name": "energy_class",
            "type": "string",
            "description": "Class label on the scheme's own scale, or not_stated when the advert states no class on the headline indicator, states one off the scale, or states two different ones."
          },
          {
            "name": "class_rank",
            "type": "integer",
            "description": "Position on the scheme's own scale, 0 = best. Comparable only within one scheme. Null for not_stated."
          },
          {
            "name": "listings",
            "type": "integer",
            "description": "Listings in this cell. Null when fewer than 5, because such small counts are unreliable (the row is then suppressed)."
          },
          {
            "name": "share_of_listings_pct",
            "type": "number",
            "description": "Share of this class among all listings of the same country, tenure and property type, not_stated included, in percent (1 decimal). Null when suppressed."
          },
          {
            "name": "share_of_stated_pct",
            "type": "number",
            "description": "Share of this class among the listings of the same country, tenure and property type that state a class, in percent (1 decimal). Null for not_stated and when suppressed."
          },
          {
            "name": "new_build_share_pct",
            "type": "number",
            "description": "Share of the cell's listings that are new builds, under construction, planned, or units of a multi-unit project, in percent (1 decimal). Null when fewer than 10 listings."
          },
          {
            "name": "price_listings",
            "type": "integer",
            "description": "Listings of the cell with a price per m² inside the plausibility bands. Null when fewer than 10."
          },
          {
            "name": "unit",
            "type": "string",
            "description": "Unit of median, p25 and p75: eur_per_m2 (sale) or eur_per_m2_per_month (rent)."
          },
          {
            "name": "median",
            "type": "number",
            "description": "Median asking price per m² of the price listings. Sale rounded to whole euros, rent to 0.1 euro. Null unless price_listings is at least 10."
          },
          {
            "name": "p25",
            "type": "number",
            "description": "25th percentile of asking price per m² (linear interpolation). Null unless price_listings is at least 10."
          },
          {
            "name": "p75",
            "type": "number",
            "description": "75th percentile of asking price per m² (linear interpolation). Null unless price_listings is at least 10."
          },
          {
            "name": "suppressed",
            "type": "boolean",
            "description": "True when the cell has fewer than 5 listings: its counts, shares and prices are then null, because such small counts are unreliable. The adverts are public and this is not a confidentiality guarantee: a hidden count can sometimes be worked out from the shares."
          }
        ],
        "missingValues": [
          ""
        ]
      }
    },
    {
      "name": "energy_class_asking_prices_parquet",
      "path": "energy_class_asking_prices.parquet",
      "title": "Advertised homes and asking prices by energy class (Parquet)",
      "format": "parquet",
      "mediatype": "application/vnd.apache.parquet",
      "bytes": 5990,
      "hash": "sha256:ff806a668d790ba800e2ce39cc550f42295ba6847098f5c26deb6ad9adcbbe4d"
    },
    {
      "name": "canton_energy_class_mix",
      "path": "canton_energy_class_mix.csv",
      "title": "Energy-class mix of advertised homes by Luxembourg canton",
      "description": "Share of each Luxembourg CPE primary-energy class among the apartments (studios included) and houses advertised for sale or rent on the snapshot date, per canton. The canton comes from the listing's official commune (STATEC locality id). Rooms, colocations, multi-unit buildings and land are excluded. Shares describe advertised stock, not the housing stock. Every class of the scale and not_stated is listed for each canton and tenure with at least one listing. Grain: one row per Luxembourg canton × tenure × energy class (every LU CPE class, plus not_stated).",
      "profile": "tabular-data-resource",
      "format": "csv",
      "mediatype": "text/csv",
      "encoding": "utf-8",
      "bytes": 12564,
      "hash": "sha256:33f6cf08fec67bf3a24c1c70eba116ed6ed2b784b958d157fcf7651d6cbe8e97",
      "schema": {
        "fields": [
          {
            "name": "snapshot_date",
            "type": "string",
            "description": "Date the catalog was read (YYYY-MM-DD, UTC)."
          },
          {
            "name": "canton",
            "type": "string",
            "description": "Canton key of the ChatHome commune registry, e.g. esch (joins commune_registry.canton)."
          },
          {
            "name": "canton_name",
            "type": "string",
            "description": "Official canton name, e.g. Esch-sur-Alzette."
          },
          {
            "name": "tenure",
            "type": "string",
            "description": "sale or rent."
          },
          {
            "name": "energy_class",
            "type": "string",
            "description": "LU CPE primary-energy class (A+ to I), or not_stated when the advert states none on that indicator, one off the scale, or two different ones."
          },
          {
            "name": "listings",
            "type": "integer",
            "description": "Listings in this cell. Null when fewer than 5, because such small counts are unreliable (the row is then suppressed)."
          },
          {
            "name": "share_of_listings_pct",
            "type": "number",
            "description": "Share of this class among all listings of the canton and tenure, not_stated included, in percent (1 decimal). Null when suppressed."
          },
          {
            "name": "suppressed",
            "type": "boolean",
            "description": "True when the cell has fewer than 5 listings: its count and share are then null, because such small counts are unreliable. The adverts are public and this is not a confidentiality guarantee: a hidden count can sometimes be worked out from the shares."
          }
        ],
        "missingValues": [
          ""
        ]
      }
    },
    {
      "name": "canton_energy_class_mix_parquet",
      "path": "canton_energy_class_mix.parquet",
      "title": "Energy-class mix of advertised homes by Luxembourg canton (Parquet)",
      "format": "parquet",
      "mediatype": "application/vnd.apache.parquet",
      "bytes": 2681,
      "hash": "sha256:71eb319ad5880f72c9b5c9d9b0c3369994f550daab3459d1a1cc4100fef6e3f7"
    }
  ]
}
