From d987ecf5c42141002984725b50a052d045d3236a Mon Sep 17 00:00:00 2001 From: rxf Date: Thu, 8 Jun 2023 17:08:03 +0200 Subject: [PATCH] getiing data from mongoseries AND from influx possible databases/mongo.js - fetchNoiseAVGData added sensorspecials/noise.js - read also from mongo --- databases/mongo.js | 133 ++++++++++++++++++++++++++++++++++------ sensorspecials/noise.js | 1 + 2 files changed, 115 insertions(+), 19 deletions(-) diff --git a/databases/mongo.js b/databases/mongo.js index 3bb7566..6c5b4eb 100644 --- a/databases/mongo.js +++ b/databases/mongo.js @@ -176,25 +176,120 @@ export const fetchActData = async (opts) => { ).toArray(); */ - -export const fetchActDataxx = async (opts) => { +export const fetchNoiseAVGData = async (opts) => { + let docs = [] let ret = {err: null, values: []} - let sorting = '' - if(opts.sort) { - if (opts.sort === 1) { - sorting = '|> sort(columns: ["_time"], desc: false)' - } else if (opts.sort === -1) { - sorting = '|> sort(columns: ["_time"], desc: true)' - } + let start = opts.start.slice(7) + let end = opts.stop.slice(6) + start = DateTime.fromISO(start).toJSDate() + end = DateTime.fromISO(end).toJSDate() + let peak = opts.peak; // threshold for peak count + let datRange = {sensorid: opts.sensorid, datetime: {$gte: start, $lt: end}} + let sorting = {datetime: opts.sort}; + let grpId = {$dateToString: {format: '%Y-%m-%dT%H:00:00Z', date: '$datetime'}} + let client = await connectMongo() + try { + docs = await client.db(MONGOBASE).collection('sensors').aggregate([ + {$sort: sorting}, // sort by date + {$match: datRange}, // select only values in give data range + { + $group: { + _id: grpId, + n_average: {$avg: "$values.E10tel_eq"}, // calculate the average + n_sum: {$sum: "$values.E10tel_eq"}, // calculate the sum + peakcount: {$sum: {$cond: [{$gte: ["$values.noise_LA_max", peak]}, 1, 0]}}, // count peaks + count: {$sum: 1}, // count entries + } + }, + {$sort: {_id: 1}}, // sort by result dates + { $addFields: { datetime: "$_id"}}, // change '_id' to 'date' + {$project: opts.long ? { _id:0, n_AVG: { $multiply: [10, {$log10: "$n_average"}]}, datetime:1, peakcount:1, count:1, n_sum:1} : + {_id:0, n_AVG: { $multiply: [10, {$log10: "$n_average"}]}, datetime:1, peakcount:1}} + ]).toArray(); // return not all fields, depending on 'long' + } catch(e) { // if there was an error + ret.err = e // log it to console } - // build the flux query - let query = ` - from(bucket: "sensor_data") -|> range(${opts.start}, ${opts.stop}) -|> filter(fn: (r) => r.sid == "${opts.sensorid}") -${sorting} -|> keep(columns: ["_time","_field","_value"]) -|> pivot(rowKey:["_time"], columnKey: ["_field"], valueColumn: "_value") -` - return await fetchFromInflux(ret, query) + finally { + client.close() + } + ret.values = docs + return ret } + +/* +// ********************************************* +// getAverageData +// +// Calculate different values per hour +// average of E10tel_eq ( E10tel_eq => 10 ^(LAeq/10) ) +// sum of E10tel_eq, to calculate day, night and eveniung averages +// count, how many values are used for average/sum +// paeakcount, how many values of LAmax are over defined peak value in every hour +// +// params: +// db: Database +// opt: different options (see further down) +// +// return +// depending an calling parameter 'what', not all values will be sent in 'values' +// JSON +// {[ +// { datetime: "2019-10-23T00:00:00Z" , n_AVG: 67.22, n_sum: 32783, count: 24, peakcount: 6 }. +// { datetime: "2019-10-23T01:00:00Z" , n_AVG: 52.89, n_sum: 23561, count: 26, peakcount: 5 }. +// ......... +// ]} +// +// ********************************************* +async function getAverageData(db,opt) { + let start = opt.start; + let end = opt.end; // start and ent time for aggregation + let docs = []; // collect data here + const collection = db.collection('data_' + opt.sid);; + let span = opt.span // date range in days + let peak = opt.peak; // threshold for peak count + let long = opt.long; // true => give extra output + let nbrOfHours = opt.end.diff(opt.start,'hours') + 24; + let datRange = {datetime: {$gte: opt.start.toDate(), $lt: opt.end.toDate()}}; + let sorting = {datetime: opt.sort}; + let grpId = {$dateToString: {format: '%Y-%m-%dT%H:00:00Z', date: '$datetime'}}; + try { + docs = await collection.aggregate([ + {$sort: sorting}, // sort by date + {$match: datRange}, // select only values in give data range + { + $group: { + _id: grpId, + n_average: {$avg: '$E10tel_eq'}, // calculate the average + n_sum: {$sum: '$E10tel_eq'}, // calculate the sum + peakcount: {$sum: {$cond: [{$gte: ["$noise_LA_max", peak]}, 1, 0]}}, // count peaks + count: {$sum: 1}, // count entries + } + }, + {$sort: {_id: 1}}, // sort by result dates + { $addFields: { datetime: "$_id"}}, // change '_id' to 'date' + {$project: opt.long ? { _id:0, n_AVG: { $multiply: [10, {$log10: "$n_average"}]}, datetime:1, peakcount:1, count:1, n_sum:1} : + {_id:0, n_AVG: { $multiply: [10, {$log10: "$n_average"}]}, datetime:1, peakcount:1}} + ]).toArray(); // return not all fields, depending on 'long' + } catch(e) { // if there was an error + console.log(e); // log it to console + } + // To easily extract the values, we copy the data from docs into a new array, so that the + // hour in an element in docs becomes the index into the new array (for every new day this + // index will be incremented by 24). Missing values are marked by: {n_sum=-1, n_AVG=-1}. + let hoursArr = new Array(nbrOfHours); // generate new array + let emptyValues = opt.long ? {n_sum: -1, n_AVG:-1} : {n_AVG:-1}; + hoursArr.fill(emptyValues); // fill with 'empty' value + let startDay = moment.utc(docs[0].datetime).date(); // calc first day + let k = 0; + for (let i=0; i { const getNoiseAVGData = async (opts) => { let ret = await influx.fetchNoiseAVGData(opts) + let retM = await mongo.fetchNoiseAVGData(opts) if(ret.err) { return returnOnError(ret, ret.err, getNoiseAVGData.name)