feat: update session handling and add session history endpoint

This commit is contained in:
Giuseppe Raffa
2026-04-16 15:37:10 +02:00
parent 5912c00a82
commit 981f498eb7
5 changed files with 354 additions and 92 deletions

View File

@@ -15,11 +15,10 @@ const writeApi = client.getWriteApi(org, bucket, 'ms', {
/**
* Scrive dati generici su InfluxDB senza mapping.
* I campi vengono scritti con il nome originale.
* @param {string} measurement - nome della measurement (es. 'logs', 'weather')
* @param {Object} fields - campi { key: value }
* @param {string} sensor - nome del sensore
* @param {string} session - id sessione
* @param {string} session - id sessione (tag immutabile)
* @param {number} timestamp - timestamp unix ms
*/
function writeGenericData(measurement, fields, sensor, session, timestamp) {
@@ -52,6 +51,24 @@ function writeForecastBatch(points, sensor, session) {
}
}
/**
* Forza il flush del buffer di scrittura.
*/
async function flush() {
try {
await writeApi.flush();
} catch (err) {
console.error('[INFLUX] Flush error:', err.message);
}
}
/**
* Query storica per una sessione: ritorna righe pivotate con tutti i campi.
* @param {string} sensor - nome sensore
* @param {string} session - session_id (tag InfluxDB)
* @param {string} since - ISO timestamp o duration (es. "-30d")
* @returns {Array<Object>}
*/
async function queryHistory(sensor, session, since) {
const queryApi = client.getQueryApi(org);
const fluxQuery = `
@@ -61,6 +78,7 @@ async function queryHistory(sensor, session, since) {
|> filter(fn: (r) => r.sensor == "${sensor}")
|> filter(fn: (r) => r.session == "${session}")
|> pivot(rowKey:["_time"], columnKey: ["_field"], valueColumn: "_value")
|> sort(columns: ["_time"])
`;
const rows = [];
@@ -75,4 +93,44 @@ async function queryHistory(sensor, session, since) {
});
}
module.exports = { writeGenericData, writeForecastBatch, queryHistory };
/**
* Esporta tutti i dati di una sessione come CSV.
* @param {string} sensor - nome sensore
* @param {string} session - session_id
* @param {string} since - ISO timestamp inizio (opzionale, default -30d)
* @returns {string} CSV content
*/
async function exportSessionCSV(sensor, session, since) {
const start = since || '-30d';
const rows = await queryHistory(sensor, session, start);
if (rows.length === 0) return '';
// Raccogli tutti i field names (esclusi meta InfluxDB)
const metaKeys = new Set(['result', 'table', '_start', '_stop', '_measurement', 'sensor', 'session', '']);
const fieldNames = new Set();
for (const row of rows) {
for (const key of Object.keys(row)) {
if (!metaKeys.has(key) && key !== '_time') {
fieldNames.add(key);
}
}
}
const fields = Array.from(fieldNames).sort();
const header = ['timestamp', ...fields].join(',');
const csvRows = rows.map(row => {
const ts = row._time || '';
const values = fields.map(f => {
const v = row[f];
if (v === null || v === undefined) return '';
return v;
});
return [ts, ...values].join(',');
});
return header + '\n' + csvRows.join('\n') + '\n';
}
module.exports = { writeGenericData, writeForecastBatch, flush, queryHistory, exportSessionCSV };