fix: added energy-management
This commit is contained in:
54
energy-management/backend/src/control/quarterHour.ts
Normal file
54
energy-management/backend/src/control/quarterHour.ts
Normal file
@@ -0,0 +1,54 @@
|
||||
import type { PowerSample, QuarterHourStatus } from "../types.js";
|
||||
|
||||
export const BLOCK_DURATION_MS = 15 * 60 * 1000;
|
||||
|
||||
export function blockStartFor(timestampMs: number): number {
|
||||
return Math.floor(timestampMs / BLOCK_DURATION_MS) * BLOCK_DURATION_MS;
|
||||
}
|
||||
|
||||
/**
|
||||
* Computes the running and projected average power for the current 15-minute
|
||||
* billing block, given a step-function reading of power samples (each sample
|
||||
* holds until the next one arrives). Samples outside the current block are
|
||||
* ignored; if the block has no samples yet, power is assumed to be 0 so far.
|
||||
*/
|
||||
export function computeQuarterHourStatus(
|
||||
samples: PowerSample[],
|
||||
nowMs: number,
|
||||
targetW: number,
|
||||
): QuarterHourStatus {
|
||||
const blockStartMs = blockStartFor(nowMs);
|
||||
const blockEndMs = blockStartMs + BLOCK_DURATION_MS;
|
||||
|
||||
const relevant = samples
|
||||
.filter((s) => s.timestampMs >= blockStartMs && s.timestampMs <= nowMs)
|
||||
.sort((a, b) => a.timestampMs - b.timestampMs);
|
||||
|
||||
let energyWms = 0;
|
||||
let cursorMs = blockStartMs;
|
||||
let cursorWatts = relevant.length > 0 ? relevant[0].watts : 0;
|
||||
|
||||
for (const sample of relevant) {
|
||||
energyWms += cursorWatts * (sample.timestampMs - cursorMs);
|
||||
cursorMs = sample.timestampMs;
|
||||
cursorWatts = sample.watts;
|
||||
}
|
||||
energyWms += cursorWatts * (nowMs - cursorMs);
|
||||
|
||||
const elapsedMs = nowMs - blockStartMs;
|
||||
const runningAverageW = elapsedMs > 0 ? energyWms / elapsedMs : 0;
|
||||
|
||||
const remainingMs = blockEndMs - nowMs;
|
||||
const projectedEnergyWms = energyWms + cursorWatts * remainingMs;
|
||||
const projectedAverageW = projectedEnergyWms / BLOCK_DURATION_MS;
|
||||
|
||||
return {
|
||||
blockStartMs,
|
||||
blockEndMs,
|
||||
elapsedFractionOfBlock: elapsedMs / BLOCK_DURATION_MS,
|
||||
runningAverageW,
|
||||
projectedAverageW,
|
||||
targetW,
|
||||
overTarget: projectedAverageW > targetW,
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user