191 lines
6.0 KiB
JavaScript
191 lines
6.0 KiB
JavaScript
// Fetch the actual (= newest) data out of the dbase to show it on the map
|
|
import {DateTime} from "luxon"
|
|
import * as mongo from "../databases/mongo.js"
|
|
import { returnOnError } from "../utilities/reporterror.js"
|
|
|
|
|
|
// Default distance for center search ( in km)
|
|
const DEFAULT_DISTANCE = 10
|
|
|
|
// Value to use fpr map
|
|
const value4map = [
|
|
{ typ: 'noise', value: 'LA_max'},
|
|
{ typ: 'pm', value: 'P1'},
|
|
{ typ: 'thp', value: 'temperature'},
|
|
{ typ: 'radioactivity', value: 'counts_per_minute'},
|
|
]
|
|
|
|
// get value for map from tabel
|
|
const getValue4Map = (t) => {
|
|
for(let x of value4map) {
|
|
if(x.typ == t) {
|
|
return x.value
|
|
}
|
|
}
|
|
return ''
|
|
}
|
|
|
|
// Relations between types and value type
|
|
const vtype2measurement = {
|
|
P1: 'pm', P2: 'pm', P0: 'pm',
|
|
temperature: 'thp', humidity: 'thp', pressure: 'thp',
|
|
LAeq: 'noise',
|
|
counts_per_minute: 'radioactivity'
|
|
};
|
|
|
|
|
|
|
|
// find first value type from measurement
|
|
const getfieldfromtype = (typ) => {
|
|
for (const [key, value] of Object.entries(vtype2measurement)) {
|
|
if (value === typ) {
|
|
return key
|
|
}
|
|
}
|
|
return ' '
|
|
}
|
|
|
|
|
|
// read the last entries from the influx database
|
|
const readLastDates = async (typ) => {
|
|
let ret = {values: [], err: null}
|
|
let query = `
|
|
from(bucket: "sensor_data")
|
|
|> range(start: -2h)
|
|
|> filter(fn: (r) => r._measurement == "${typ}" and r._field == "${getValue4Map(typ)}")
|
|
|> last()
|
|
|> group()
|
|
|> map(fn: (r) => ({r with sid: int(v: r.sid)}))
|
|
|> sort(columns: ["sid"])
|
|
|> keep(columns: ["_time","sid","_value"])
|
|
`
|
|
return await fetchFromInflux(ret, query)
|
|
}
|
|
|
|
export var getData4map = async (params) => {
|
|
let start = DateTime.now()
|
|
let ret = {err: null}
|
|
|
|
// ***** This function will (at the moment) only be called by internal routines, so there is no need to check the parameters !
|
|
|
|
const typ = params.type
|
|
let poly = []
|
|
let south = null, north = null, east = null, west = null, center = null
|
|
let distance = DEFAULT_DISTANCE
|
|
if(params.box !== undefined) {
|
|
let val = params.box.split(',')
|
|
for (let i = 0; i < val.length; i++) {
|
|
val[i] = parseFloat(val[i])
|
|
}
|
|
south = parseFloat(val[1])
|
|
north = parseFloat(val[3])
|
|
east = parseFloat(val[2])
|
|
west = parseFloat(val[0])
|
|
// logit(`getData4map: S=${south} N=${north} E=${east} W=${west}`)
|
|
}
|
|
if (!((params.poly === undefined) || (params.poly === ' '))){
|
|
poly = JSON.parse(params.poly)
|
|
}
|
|
if (params.center !== undefined) {
|
|
center = params.center
|
|
if ((params.distance !== undefined) &&
|
|
(params.distance >= 1) && (params.distance <= 1000)) {
|
|
distance = params.distance
|
|
}
|
|
}
|
|
const aktData = []
|
|
let lastDate = 0
|
|
let query = {type: typ}
|
|
|
|
// if polyline or box were given, set query
|
|
if (poly.length !== 0) { // polyline given
|
|
query.location = {
|
|
$geoWithin: {
|
|
$geometry: {
|
|
type: "Polygon",
|
|
coordinates: [poly],
|
|
}
|
|
}
|
|
}
|
|
} else if (south !== null) { // box given
|
|
query["location.loc"] = {
|
|
$geoWithin: {
|
|
$box: [
|
|
[west, south],
|
|
[east, north]
|
|
]
|
|
}
|
|
}
|
|
} else if (center !== null) { // center point given
|
|
query["location.loc"] = {
|
|
$nearSphere: {
|
|
$geometry: {
|
|
type: "Point",
|
|
coordinates: center
|
|
},
|
|
$maxDistance: distance * 1000
|
|
}
|
|
}
|
|
}
|
|
try {
|
|
// fetch mapdata from mongodb
|
|
let { properties, err } = await mongo.getallProperties(mongo.properties_collection, query)
|
|
if(err) {
|
|
return returnOnError(ret, 'NOPROPSFOUND', getData4map.name)
|
|
}
|
|
let v4map = getValue4Map(typ)
|
|
for (let sensor of properties) {
|
|
let oneAktData = {}
|
|
if (sensor.values !== undefined) {
|
|
oneAktData = {
|
|
location: sensor.location[0].loc.coordinates,
|
|
id: sensor._id,
|
|
name: sensor.name[0].name,
|
|
indoor: sensor.location[0].indoor,
|
|
lastseen: sensor.values.timestamp
|
|
}
|
|
let now = new Date().getTime()
|
|
if(oneAktData.lastseen !== '') {
|
|
let diff = now - oneAktData.lastseen.getTime()
|
|
if (diff >= 365 * 24 * 3600 * 1000) {
|
|
oneAktData.value = -4
|
|
} else if (diff >= 30 * 24 * 3600 * 1000) {
|
|
oneAktData.value = -3
|
|
} else if (diff >= 7 * 24 * 3600 * 1000) {
|
|
oneAktData.value = -2
|
|
} else if (diff >= 2 * 3600 * 1000) {
|
|
oneAktData.value = -1
|
|
} else {
|
|
if (sensor.values !== undefined) {
|
|
oneAktData.value = Math.round(sensor.values[v4map] * 100) / 100
|
|
}
|
|
}
|
|
let weeks = Math.round(diff / (7 * 24 * 3600 * 1000))
|
|
oneAktData.weeks = weeks
|
|
}
|
|
if (sensor.values.timestamp > lastDate) {
|
|
lastDate = sensor.values.timestamp
|
|
}
|
|
} else {
|
|
oneAktData.value = -5
|
|
oneAktData.weeks = 0
|
|
oneAktData.lastseen = ''
|
|
}
|
|
aktData.push(oneAktData)
|
|
}
|
|
ret = {
|
|
err: null,
|
|
options: {
|
|
lastdate: lastDate,
|
|
count: aktData.length,
|
|
data: 'map'
|
|
},
|
|
values: aktData
|
|
}
|
|
return ret
|
|
}
|
|
catch(e) {
|
|
return returnOnError(ret, `catch\n${e}`, getData4map.name)
|
|
}
|
|
}
|