1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
import asyncdispatch, tables, times, options, tables
import ../types, ../vars, ../modbus, ../influx, ../utils
proc updatePowermeter (key: string, device: DeviceConfig) {.async.} =
let deviceAddress = device.address.get
let currentTimestamp = toUnix(getTime())
let voltage = (await mb.asyncReadFloat(deviceAddress, 0)).isaRound(3)
let current = (await mb.asyncReadFloat(deviceAddress, 6)).isaRound(3)
let frequency = (await mb.asyncReadFloat(deviceAddress, 70)).isaRound(3)
let `import` = (await mb.asyncReadFloat(deviceAddress, 72)).isaRound(3)
let cosphi = (await mb.asyncReadFloat(deviceAddress, 30)).isaRound(3)
let power = (await mb.asyncReadFloat(deviceAddress, 12)).isaRound(3)
if server.config.serverConfig.influx.isSome:
let config = server.config.serverConfig.influx.get
if config.powermetersDatabase.isSome:
if server.state[key].lastUpdated.isSome:
if (currentTimestamp - server.state[key].lastUpdated.get) < 30:
break
var tags, fields = initTable[string, string]()
tags["device"] = key
fields["voltage"] = $voltage
fields["current"] = $current
fields["frequency"] = $frequency
fields["import"] = $`import`
fields["cosphi"] = $cosphi
fields["power"] = $power
discard await config.insertDatabase(config.powermetersDatabase.get, key, tags, fields, currentTimestamp * 1000000000)
server.state[key].voltage = voltage
server.state[key].frequency = frequency
server.state[key].`import` = `import`
server.state[key].cosphi = cosphi
server.state[key].power = power
server.state[key].lastUpdated = some(currentTimestamp)
broadcastServerState()
proc updatePowermeters () {.async.} =
for key, device in server.config.devices.pairs():
if device.type != PowerMeter:
continue
try:
await updatePowermeter(key, device)
except:
echo "Error[updatePowermeters]:\n", getCurrentExceptionMsg()
proc powermetersLoop () {.async.} =
await sleepAsync(500)
while true:
await updatePowermeters()
await sleepAsync(int(server.config.serverConfig.powermeterUpdateIntervalSec * 1000))
proc initModbusPowermeters* () =
for key, device in server.config.devices.pairs():
if device.type != PowerMeter:
continue
server.state[key] = DeviceState(type: PowerMeter)
asyncCheck powermetersLoop()