---
title: "Building Energy Management System (BEMS)"
description: "A BEMS is the energy data layer between BMS telemetry and analytics. Learn how to model sub-metering, demand monitoring, and M&V queries on Postgres."
section: "Postgres for IoT"
---

> **TimescaleDB is now Tiger Data.**

A single building's energy submeters look manageable. One meter at the main service entrance, maybe a handful more for major equipment. Then a portfolio team decides to submeter by floor. Then by tenant. Then, because a demand-charge tariff kicked in, by circuit. Multiply that hierarchy across a portfolio and layer a 15-minute interval requirement on top, and what looked like "a few more data points" is now a different data-modeling problem than storing building telemetry.

That's the building energy management system (BEMS) data problem, and it's a different problem than "where do we store BMS telemetry."

A building management system (BMS) operates equipment in real time: setpoints, schedules, alarms. A BEMS is specifically the energy-consumption and demand data layer, something [<u>EnergyCAP's own BEMS guide</u>](https://www.energycap.com/blog/building-energy-monitoring/) frames as collecting interval data from meters and submeters and turning it into trends, alerts, and savings verification. That data layer feeds both the BMS below it and the analytics layer above it. Related systems, not identical ones.

This piece assumes general BMS storage is already settled. If BACnet and Modbus protocol handling, the narrow-row schema, and hypertables aren't sorted out yet, start with the [<u>building management system database</u>](https://www.tigerdata.com/learn/building-management-system-database) guide first. It also assumes portfolio-level energy benchmarking and anomaly detection are a separate concern, covered in [<u>Smart Building Analytics</u>](https://www.tigerdata.com/learn/smart-building-analytics). What's left, and what this piece owns, is submetering's cardinality fan-out, demand monitoring as distinct from consumption rollups, and measurement and verification (M&V) as its own query pattern.

**In short:** a BEMS is the energy-specific data-capture layer sitting between BMS equipment telemetry and portfolio analytics. The database underneath it needs to do two things a general BMS schema doesn't: model a sub-meter hierarchy without exploding point count, and support M&V's baseline-and-adjust comparison alongside demand-specific peak queries. A building running one or two utility meters with no submetering program, demand-charge tariff, or M&V requirement doesn't need most of what follows. A single continuous aggregate, per the pillar, covers that case.

One more thing worth saying plainly: Tiger Data builds a Postgres-based time-series database, so this piece leans toward that answer. The goal here is an honest look at the data problem, not a sales pitch.

## What a building energy management system actually monitors

Two signals drive everything a BEMS handles, and they're different in kind: consumption and demand.

Consumption is kWh, a rolled-up total over a period. Demand is kW, an instantaneous rate at a single point in time. A consumption query answers "how much energy did this building use in March." A demand query answers "what was the highest draw this meter recorded in any 15-minute window this month." Those are different questions, and as later sections show, they need different query shapes.

BEMS data itself usually comes from the same source a BMS already produces: utility-meter feeds and sub-meters, often BACnet- or Modbus-sourced energy points. This piece picks up downstream of that capture step. For the protocol-level detail on how those readings land in a database in the first place, the [<u>BMS page</u>](https://www.tigerdata.com/learn/building-management-system-database) covers it.

From here, a BEMS data layer has three distinct jobs: model a sub-meter hierarchy without the point count becoming unmanageable, support demand-specific queries separate from consumption rollups, and support M&V's baseline-and-adjust computation. Three query problems over related data, each covered below.

## Submetering: modeling the fan-out problem

One building-level meter becomes many once a portfolio submeters. A floor-level meter multiplies into per-tenant meters. Tenant meters can multiply again into per-circuit meters below that. Submetering isn't "more of the same point type" arriving at a higher rate. It's a hierarchy problem: a floor meter's readings relate to the tenant meters beneath it, and that parent-child relationship needs to be represented in the schema, not just tracked in a spreadsheet somewhere.

The fix is additive, not a redesign. The BMS pillar's narrow-row schema (`time`, a point identifier, `value`) already handles high-cardinality telemetry well. Extend it with a meter hierarchy: give each sub-meter its own identifier alongside a parent-meter reference.

`ALTER TABLE energy_data
  ADD COLUMN meter_id text,
  ADD COLUMN parent_meter_id text;`

A floor meter's row carries its own `meter_id` and a `parent_meter_id` pointing at the building-level meter. A tenant meter points at its floor. Rolling a tenant's usage up to its floor, or a floor's up to the building, becomes a join or recursive query against that hierarchy, rather than a manual reconciliation exercise.

There's a real regulatory driver behind why this is showing up now. [<u>ASHRAE 90.1-2022</u>](https://www.ashrae.org/about/news/2023/newly-released-ashrae-90-1-2022-includes-expanded-scope-for-building-sites) requires metering devices that track electricity usage by load type in commercial buildings over 25,000 square feet in many jurisdictions, specifically at 15-minute intervals. That's not this piece's angle, but it's worth naming as context: interval-metering requirements are pushing more buildings into exactly the submetering fan-out described above.

The row-count math backs that up. A single building-level meter at hourly resolution produces a modest, easy-to-ignore number of rows per year. The same building with a meter hierarchy at 15-minute intervals, retained across a multi-year window, produces meaningfully more. That's the practical reason the fan-out matters for storage and retention planning, and it matters well before schema design.

## Demand monitoring: peak demand, load curves, and alerting

Demand needs a different query shape than a consumption rollup, and the reason is financial as much as technical. Many commercial utility tariffs bill a demand charge based on the single highest interval of usage in a billing period. A building that stays well under its average consumption target but spikes once, briefly, to a high draw can still take a real hit on its bill for that one interval. Catching and managing that peak is a distinct, high-value query problem, separate from tracking total consumption.

That means the query isn't a sum over `time_bucket`. It's peak-window detection: finding the highest reading within a rolling window, fast enough to matter for alerting rather than only for month-end reporting.

The following is an illustrative pattern, not a drop-in production query, meant to show the shape of the problem:

`SELECT
  meter_id,
  time,
  kw_reading,
  max(kw_reading) OVER (
    PARTITION BY meter_id
    ORDER BY time
    RANGE BETWEEN INTERVAL '1 hour' PRECEDING
      AND CURRENT ROW
  ) AS rolling_peak_kw
FROM demand_readings
WHERE time > now() - INTERVAL '7 days';`

This is a rolling maximum over a bounded time window, grouped by meter. It's a different computation from the standard-deviation-based anomaly-detection pattern that [<u>Smart Building Analytics</u>](https://www.tigerdata.com/learn/smart-building-analytics) already covers for HVAC fault detection. Both are queries over related telemetry, but a demand-charge question and an equipment-anomaly question ask for different math.

Demand alerting, flagging a live interval reading as it approaches a known threshold, is a natural extension of this same query shape. It's worth a mention here rather than a section of its own: once a rolling-max query exists, comparing the latest value against a threshold and firing a notification is a small addition.

## Measurement and verification (M&V): proving savings, not just monitoring usage

Monitoring answers "what's happening now." M&V answers a harder question: "what would have happened without this project." You can never directly meter the energy an efficiency retrofit stopped you from using. That's what a baseline comparison is for.

M&V, as defined by the [<u>International Performance Measurement and Verification Protocol (IPMVP)</u>](https://evo-world.org), works by establishing a baseline period, adjusting that baseline for weather and occupancy differences, and then comparing actual post-intervention usage against the adjusted baseline. IPMVP is the industry standard for this practice.

The distinction from Smart Building Analytics' benchmarking is worth stating plainly, because both look like "compare energy data" on the surface. M&V compares a building against its own adjusted baseline over time, a before-and-after question. Portfolio benchmarking compares buildings against each other, or against a portfolio average, at a point in time, a peer-comparison question. Both are queries over energy data. They need different query shapes.

At a conceptual level, an M&V query needs three things from the database: the ability to compute a baseline from a defined historical window, the ability to apply an adjustment factor to that baseline, and the ability to compare the adjusted result against a later window. That's a comparison-across-time-ranges problem, closer to a windowed join than a single rollup.

`WITH baseline AS (
  SELECT
    avg(kwh_reading) AS baseline_avg
  FROM energy_data
  WHERE time BETWEEN '2025-01-01' AND '2025-06-30'
),
adjusted AS (
  SELECT baseline_avg * 1.04 AS adjusted_baseline
  FROM baseline
),
post_period AS (
  SELECT avg(kwh_reading) AS actual_avg
  FROM energy_data
  WHERE time BETWEEN '2026-01-01' AND '2026-06-30'
)
SELECT
  adjusted.adjusted_baseline,
  post_period.actual_avg,
  adjusted.adjusted_baseline - post_period.actual_avg
    AS verified_savings
FROM adjusted, post_period;`

That 1.04 adjustment factor is illustrative, standing in for whatever weather- or occupancy-normalization coefficient an M&V program actually calculates. The shape of the query, baseline window, adjustment, comparison window, is the point.

If there's one section in this piece that most directly answers "how do you store building energy data over time for verification, not just dashboards," this is it.

## Migrating to a BEMS data layer: common starting points

Most teams arrive at this problem from one of four places.

**From spreadsheets and manual utility-bill tracking.** Energy data exists only as monthly totals pulled from a bill. The shift here is to an automated pipeline that captures interval-level meter data as it's generated, instead of a monthly number typed into a spreadsheet.

**From a vendor BEMS dashboard with no queryable database underneath.** The interval data exists, but it's locked inside a closed SaaS UI. The path forward is extracting or streaming that same meter data into a database the team controls, so custom M&V and demand queries become possible instead of whatever the vendor's dashboard happens to expose.

**From a BMS that only stores equipment points today.** No dedicated energy or meter schema exists yet. Adding the meter hierarchy described earlier is additive to existing BMS storage. It's not a second database and not a rip-and-replace migration.

**From a single hourly continuous aggregate already in place.** A team that followed the [<u>building management system database</u>](https://www.tigerdata.com/learn/building-management-system-database) guide's basic example, or came from [<u>Smart Building Analytics</u>](https://www.tigerdata.com/learn/smart-building-analytics)' benchmarking layer, can add a meter-hierarchy dimension and a demand-specific rolling-window query without re-architecting ingestion. The [<u>continuous aggregate refresh policy</u>](https://www.tigerdata.com/docs/reference/timescaledb/continuous-aggregates/add_continuous_aggregate_policy) that's already keeping that hourly rollup current keeps working the same way once the underlying table carries a meter hierarchy.

Each of these is a change from a specific starting point, not a repeat of the schema and query material already covered above.

## Decision framework: do you need a dedicated BEMS data layer?

Not every building or portfolio needs submetering, demand monitoring, and M&V solved at the same time. Use this to identify which of these problems actually applies right now.

### Extend your BMS schema with a meter hierarchy if:

You're moving from one utility meter to a handful of sub-meters, by floor, tenant, or circuit, and need to model that hierarchy, but don't yet need demand-charge alerting or savings verification.

### Add demand monitoring if:

You're on a utility tariff with a demand charge, and peak kW during any interval materially affects your bill. You need peak-window and rolling-max queries, not just consumption sums.

### Build an M&V layer if:

You're running, or verifying the results of, efficiency retrofits or capital projects and need to prove savings against an adjusted baseline. That's a different query shape than a monitoring rollup.

### Use Smart Building Analytics' benchmarking layer instead if:

Your primary need is comparing buildings against each other or a portfolio average, or building anomaly-detection and KPI dashboards. That's the analytics layer covered in [<u>Smart Building Analytics</u>](https://www.tigerdata.com/learn/smart-building-analytics), not the capture and verification layer covered here.

### A single hourly continuous aggregate is probably still enough if:

You're managing one or two utility meters with no submetering program, no demand-charge tariff, and no M&V requirement today. Start there. The patterns in this piece are additive when you need them.

## What this looks like in production

[<u>ApexAnalytica</u>](https://www.tigerdata.com/blog/how-apexanalytica-runs-building-telemetry-transactional-data-rag-on-single-postgres-instance), an AI-powered building intelligence platform, states that it targets IPMVP-compliant measurement and verification. The platform runs on an energy_data hypertable and an energy_hourly materialized view, the same underlying substrate referenced from a storage angle in the [<u>BMS guide</u>](https://www.tigerdata.com/learn/building-management-system-database) and from an anomaly-detection angle in  [<u>Smart Building Analytics</u>](https://www.tigerdata.com/learn/smart-building-analytics). This piece's M&V and demand-monitoring patterns are the kind of query that substrate is built to support.

The real-world context matters for the submetering framing covered earlier: the platform serves buildings across care and social housing, hospitality, leisure, retail, commercial offices, veterinary, and energy-sector sites, genuine portfolio-scale variety, not a single building's worth of data.

Use cases to explore further are [<u>Soundsensing</u>](https://www.tigerdata.com/case-studies/soundsensing), which applies interval-data patterns to HVAC predictive maintenance, and [<u>Palas</u>](https://www.tigerdata.com/case-studies/palas), which applies such patterns to air-quality sensor monitoring. 

## Related resources

For general BMS storage and schema foundation, BACnet and Modbus protocol handling, and the narrow-row schema this piece extends, start with the [<u>building management system database</u>](https://www.tigerdata.com/learn/building-management-system-database) guide.

For portfolio energy benchmarking, anomaly detection, and KPI dashboards built on top of the same underlying data, see [<u>Smart Building Analytics</u>](https://www.tigerdata.com/learn/smart-building-analytics).

For the same interval-data patterns applied at the grid and utility scale rather than the building scale, see [<u>Postgres for Energy & Utilities</u>](https://www.tigerdata.com/energy-utilities) and [<u>IoT energy data at scale</u>](https://www.tigerdata.com/blog/iot-energy-data-at-scale-engineering-solutions-beyond-legacy-historians).

For the same high-cardinality, interval-data pattern applied to different infrastructure verticals, see [<u>Water Utilities Database</u>](https://www.tigerdata.com/learn/water-utilities-database-how-to-store-query-scada-ami-quality-data-at-scale) and [<u>Fleet Telemetry Database</u>](https://www.tigerdata.com/learn/fleet-telemetry-database).