changed the folder and added index.js
This commit is contained in:
200
src/measurements/MeasurementContainer.js
Normal file
200
src/measurements/MeasurementContainer.js
Normal file
@@ -0,0 +1,200 @@
|
||||
const MeasurementBuilder = require('./MeasurementBuilder');
|
||||
|
||||
class MeasurementContainer {
|
||||
constructor(options = {}, logger) {
|
||||
this.logger = logger;
|
||||
this.measurements = {};
|
||||
this.windowSize = options.windowSize || 10; // Default window size
|
||||
|
||||
// For chaining context
|
||||
this._currentType = null;
|
||||
this._currentVariant = null;
|
||||
this._currentPosition = null;
|
||||
}
|
||||
|
||||
// Chainable methods
|
||||
type(typeName) {
|
||||
this._currentType = typeName;
|
||||
this._currentVariant = null;
|
||||
this._currentPosition = null;
|
||||
return this;
|
||||
}
|
||||
|
||||
variant(variantName) {
|
||||
if (!this._currentType) {
|
||||
throw new Error('Type must be specified before variant');
|
||||
}
|
||||
this._currentVariant = variantName;
|
||||
this._currentPosition = null;
|
||||
return this;
|
||||
}
|
||||
|
||||
position(positionName) {
|
||||
if (!this._currentVariant) {
|
||||
throw new Error('Variant must be specified before position');
|
||||
}
|
||||
this._currentPosition = positionName;
|
||||
return this;
|
||||
}
|
||||
|
||||
// Core methods that complete the chain
|
||||
value(val, timestamp = Date.now()) {
|
||||
if (!this._ensureChainIsValid()) return this;
|
||||
|
||||
const measurement = this._getOrCreateMeasurement();
|
||||
measurement.setValue(val, timestamp);
|
||||
return this;
|
||||
}
|
||||
|
||||
unit(unitName) {
|
||||
if (!this._ensureChainIsValid()) return this;
|
||||
|
||||
const measurement = this._getOrCreateMeasurement();
|
||||
measurement.setUnit(unitName);
|
||||
return this;
|
||||
}
|
||||
|
||||
// Terminal operations - get data out
|
||||
get() {
|
||||
if (!this._ensureChainIsValid()) return null;
|
||||
return this._getOrCreateMeasurement();
|
||||
}
|
||||
|
||||
getCurrentValue() {
|
||||
const measurement = this.get();
|
||||
return measurement ? measurement.getCurrentValue() : null;
|
||||
}
|
||||
|
||||
getAverage() {
|
||||
const measurement = this.get();
|
||||
return measurement ? measurement.getAverage() : null;
|
||||
}
|
||||
|
||||
getMin() {
|
||||
const measurement = this.get();
|
||||
return measurement ? measurement.getMin() : null;
|
||||
}
|
||||
|
||||
getMax() {
|
||||
const measurement = this.get();
|
||||
return measurement ? measurement.getMax() : null;
|
||||
}
|
||||
|
||||
getAllValues() {
|
||||
const measurement = this.get();
|
||||
return measurement ? measurement.getAllValues() : null;
|
||||
}
|
||||
|
||||
// Difference calculations between positions
|
||||
difference() {
|
||||
if (!this._currentType || !this._currentVariant) {
|
||||
throw new Error('Type and variant must be specified for difference calculation');
|
||||
}
|
||||
|
||||
// Save position to restore chain state after operation
|
||||
const savedPosition = this._currentPosition;
|
||||
|
||||
// Get upstream measurement
|
||||
this._currentPosition = 'upstream';
|
||||
const upstream = this.get();
|
||||
|
||||
// Get downstream measurement
|
||||
this._currentPosition = 'downstream';
|
||||
const downstream = this.get();
|
||||
|
||||
// Restore chain state
|
||||
this._currentPosition = savedPosition;
|
||||
|
||||
if (!upstream || !downstream || upstream.values.length === 0 || downstream.values.length === 0) {
|
||||
return null;
|
||||
}
|
||||
|
||||
// Ensure units match
|
||||
let downstreamForCalc = downstream;
|
||||
if (upstream.unit && downstream.unit && upstream.unit !== downstream.unit) {
|
||||
try {
|
||||
downstreamForCalc = downstream.convertTo(upstream.unit);
|
||||
} catch (error) {
|
||||
if (this.logger) {
|
||||
this.logger.error(`Unit conversion failed: ${error.message}`);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
value: downstreamForCalc.getCurrentValue() - upstream.getCurrentValue() ,
|
||||
avgDiff: downstreamForCalc.getAverage() - upstream.getAverage() ,
|
||||
unit: upstream.unit
|
||||
};
|
||||
}
|
||||
|
||||
// Helper methods
|
||||
_ensureChainIsValid() {
|
||||
if (!this._currentType || !this._currentVariant || !this._currentPosition) {
|
||||
if (this.logger) {
|
||||
this.logger.error('Incomplete measurement chain, required: type, variant, and position');
|
||||
}
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
_getOrCreateMeasurement() {
|
||||
// Initialize nested structure if needed
|
||||
if (!this.measurements[this._currentType]) {
|
||||
this.measurements[this._currentType] = {};
|
||||
}
|
||||
|
||||
if (!this.measurements[this._currentType][this._currentVariant]) {
|
||||
this.measurements[this._currentType][this._currentVariant] = {};
|
||||
}
|
||||
|
||||
if (!this.measurements[this._currentType][this._currentVariant][this._currentPosition]) {
|
||||
this.measurements[this._currentType][this._currentVariant][this._currentPosition] =
|
||||
new MeasurementBuilder()
|
||||
.setType(this._currentType)
|
||||
.setVariant(this._currentVariant)
|
||||
.setPosition(this._currentPosition)
|
||||
.setWindowSize(this.windowSize)
|
||||
.build();
|
||||
}
|
||||
|
||||
return this.measurements[this._currentType][this._currentVariant][this._currentPosition];
|
||||
}
|
||||
|
||||
// Additional utility methods
|
||||
getTypes() {
|
||||
return Object.keys(this.measurements);
|
||||
}
|
||||
|
||||
getVariants() {
|
||||
if (!this._currentType) {
|
||||
throw new Error('Type must be specified before listing variants');
|
||||
}
|
||||
return this.measurements[this._currentType] ?
|
||||
Object.keys(this.measurements[this._currentType]) : [];
|
||||
}
|
||||
|
||||
getPositions() {
|
||||
if (!this._currentType || !this._currentVariant) {
|
||||
throw new Error('Type and variant must be specified before listing positions');
|
||||
}
|
||||
|
||||
if (!this.measurements[this._currentType] ||
|
||||
!this.measurements[this._currentType][this._currentVariant]) {
|
||||
return [];
|
||||
}
|
||||
|
||||
return Object.keys(this.measurements[this._currentType][this._currentVariant]);
|
||||
}
|
||||
|
||||
clear() {
|
||||
this.measurements = {};
|
||||
this._currentType = null;
|
||||
this._currentVariant = null;
|
||||
this._currentPosition = null;
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = MeasurementContainer;
|
||||
Reference in New Issue
Block a user