Added database creation and updates
This commit is contained in:
parent
1c4e50d790
commit
fa600586ae
|
@ -1,3 +1,5 @@
|
||||||
*.pyc
|
*.pyc
|
||||||
__pycache__
|
__pycache__
|
||||||
virtenv
|
virtenv
|
||||||
|
*.rrd
|
||||||
|
*.png
|
||||||
|
|
43
config.py
43
config.py
|
@ -1,29 +1,52 @@
|
||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
import serial # for parity constants
|
|
||||||
|
from configutils import *
|
||||||
|
|
||||||
SERIAL = '/dev/ttyUSB0'
|
SERIAL = '/dev/ttyUSB0'
|
||||||
BAUD_RATE = 4800
|
BAUD_RATE = 4800
|
||||||
STOP_BITS = 1
|
STOP_BITS = 1
|
||||||
PARITY = None
|
PARITY = None
|
||||||
|
|
||||||
|
DATA_FILE = './test.rrd'
|
||||||
|
ARCHIVE_DATA_FILE = './test_archive.rrd'
|
||||||
DATA_INTERVAL = 60
|
DATA_INTERVAL = 60
|
||||||
ARCHIVE_INTERVAL = 60 * 60 # 1h
|
ARCHIVE_INTERVAL = 60 * 60 # 1h
|
||||||
KEEP_INTERVAL = 365 * 24 * 60 * 60 # 1 year
|
ARCHIVE_KEEP_INTERVAL = 365 * 24 * 60 * 60 # 1 year
|
||||||
|
MAX_MISSING = 0.5
|
||||||
|
|
||||||
# Manual claims poly should be 0x8404, internet says xmodem
|
# Manual claims poly should be 0x8404, internet says xmodem
|
||||||
CRC_TYPE = 'xmodem'
|
CRC_TYPE = 'xmodem'
|
||||||
|
|
||||||
|
|
||||||
STORED_VALUES = [
|
STORED_VALUES = [
|
||||||
'U_bat',
|
StoredValue('U_bat', 0.0, 20.0),
|
||||||
'U_mod1',
|
StoredValue('U_mod1', 0.0, 20.0),
|
||||||
'U_mod2',
|
StoredValue('U_mod2', 0.0, 20.0),
|
||||||
'I_pv_in',
|
StoredValue('I_pv_in', 0.0, 100.0),
|
||||||
'I_load_total',
|
StoredValue('I_load_total', 0.0, 100.0),
|
||||||
'load_switch',
|
StoredValue('load_switch', 0, 1),
|
||||||
'max_charge_bat_day',
|
StoredValue('max_charge_bat_day', 0.0, 1000.0),
|
||||||
'max_charge_load_day'
|
StoredValue('max_charge_load_day', 0.0, 1000.0),
|
||||||
]
|
]
|
||||||
|
|
||||||
|
GRAPHS = {
|
||||||
|
'voltages.png' : [
|
||||||
|
GraphLine('U_bat', 'Spannung Batterie [V]', '#ff0000'),
|
||||||
|
GraphLine('U_mod1', 'Spannung Modul 1 [V]', '#00ff00'),
|
||||||
|
GraphLine('U_mod2', 'Spannung Modul 2 [V]', '#0000ff'),
|
||||||
|
],
|
||||||
|
'currents.png' : [
|
||||||
|
GraphLine('I_pv_in', 'Strom PV [A]', '#ff0000'),
|
||||||
|
GraphLine('I_load_total', 'Strom Last [A]', '#00ff00'),
|
||||||
|
],
|
||||||
|
'realy.png' : [
|
||||||
|
GraphLine('load_switch', 'Relay', '#0000ff'),
|
||||||
|
],
|
||||||
|
'charges.png' : [
|
||||||
|
GraphLine('max_charge_bat_day', 'Max. Batterie Landung [Ah]', '#0000ff'),
|
||||||
|
GraphLine('max_charge_load_day', 'Max. Last Entladung [Ah]', '#ff0000'),
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
FORMAT = ['Version',
|
FORMAT = ['Version',
|
||||||
'Date',
|
'Date',
|
||||||
|
|
|
@ -0,0 +1,5 @@
|
||||||
|
#!/usr/bin/env python3
|
||||||
|
from collections import namedtuple
|
||||||
|
|
||||||
|
StoredValue = namedtuple('StoredValue', ['name', 'min', 'max'])
|
||||||
|
GraphLine = namedtuple('GraphLine', ['name', 'label', 'color'])
|
32
mockup.py
32
mockup.py
|
@ -1,15 +1,27 @@
|
||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
|
import os
|
||||||
import crcmod
|
import crcmod
|
||||||
from random import randint
|
from random import randint
|
||||||
|
from time import sleep
|
||||||
|
|
||||||
from config import *
|
from config import *
|
||||||
|
|
||||||
from update import parse_line
|
from update import parse_line, create_database, update_database, update_graphs
|
||||||
|
|
||||||
calc_crc = crcmod.predefined.mkCrcFun(CRC_TYPE)
|
calc_crc = crcmod.predefined.mkCrcFun(CRC_TYPE)
|
||||||
|
|
||||||
def gen_line():
|
def gen_line():
|
||||||
values = [str(randint(0,1000)) for _ in range(0,len(FORMAT))]
|
values = []
|
||||||
|
|
||||||
|
stored = {name : (minval, maxval) for name, minval, maxval in STORED_VALUES}
|
||||||
|
for name in FORMAT:
|
||||||
|
minval = 0
|
||||||
|
maxval = 1000
|
||||||
|
if name in stored.keys():
|
||||||
|
minval, maxval = stored[name]
|
||||||
|
|
||||||
|
values += [str(randint(minval, maxval))]
|
||||||
|
|
||||||
payload = ";".join(values) + ";"
|
payload = ";".join(values) + ";"
|
||||||
crc = calc_crc(payload.encode('ascii'))
|
crc = calc_crc(payload.encode('ascii'))
|
||||||
crc_str = chr((crc & 0xFF00) >> 8) + chr(crc & 0xFF)
|
crc_str = chr((crc & 0xFF00) >> 8) + chr(crc & 0xFF)
|
||||||
|
@ -19,13 +31,17 @@ def gen_line():
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
|
if not os.path.exists(DATA_FILE) or not os.path.exists(ARCHIVE_DATA_FILE):
|
||||||
|
create_database()
|
||||||
|
sleep(60)
|
||||||
|
|
||||||
|
while True:
|
||||||
|
print("Adding Line...")
|
||||||
line = gen_line()
|
line = gen_line()
|
||||||
result = parse_line(line)
|
parsed = parse_line(line)
|
||||||
|
update_database(parsed)
|
||||||
print(result)
|
update_graphs()
|
||||||
|
sleep(60)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
main()
|
main()
|
||||||
|
|
55
update.py
55
update.py
|
@ -1,6 +1,8 @@
|
||||||
#!/usr/bin/env python3
|
#!/usr/bin/env python3
|
||||||
|
import time
|
||||||
import serial
|
import serial
|
||||||
import crcmod
|
import crcmod
|
||||||
|
import rrdtool
|
||||||
|
|
||||||
from config import *
|
from config import *
|
||||||
|
|
||||||
|
@ -24,6 +26,59 @@ def parse_line(line):
|
||||||
|
|
||||||
return dict(data)
|
return dict(data)
|
||||||
|
|
||||||
|
def create_database():
|
||||||
|
sources = []
|
||||||
|
for name, minval, maxval in STORED_VALUES:
|
||||||
|
sources += ["DS:%s:GAUGE:%d:%f:%f" % (name, DATA_INTERVAL * 2, minval, maxval)]
|
||||||
|
|
||||||
|
now = time.time()
|
||||||
|
now = now - (now % DATA_INTERVAL)
|
||||||
|
|
||||||
|
rrd_params = [DATA_FILE,
|
||||||
|
"--start", "%d" % now,
|
||||||
|
"--step", str(DATA_INTERVAL)]
|
||||||
|
rrd_params += sources
|
||||||
|
rows = ARCHIVE_INTERVAL / DATA_INTERVAL
|
||||||
|
rrd_params += ["RRA:LAST:0.1:1:%d" % (rows,)]
|
||||||
|
rrdtool.create(*rrd_params)
|
||||||
|
|
||||||
|
|
||||||
|
rrd_archive_params = [ARCHIVE_DATA_FILE,
|
||||||
|
"--start", "now",
|
||||||
|
"--step", str(DATA_INTERVAL)]
|
||||||
|
steps = ARCHIVE_INTERVAL / DATA_INTERVAL
|
||||||
|
rows = ARCHIVE_KEEP_INTERVAL / ARCHIVE_INTERVAL
|
||||||
|
rrd_archive_params += sources
|
||||||
|
rrd_archive_params += ["RRA:AVERAGE:%f:%d:%d" % (MAX_MISSING, steps, rows)]
|
||||||
|
rrd_archive_params += ["RRA:MAX:%f:%d:%d" % (MAX_MISSING, steps, rows)]
|
||||||
|
rrd_archive_params += ["RRA:MIN:%f:%d:%d" % (MAX_MISSING, steps, rows)]
|
||||||
|
rrdtool.create(*rrd_archive_params)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def update_database(line):
|
||||||
|
update_values = []
|
||||||
|
for name, _, _ in STORED_VALUES:
|
||||||
|
update_values += ["%f" % float(line[name])]
|
||||||
|
|
||||||
|
now = time.time()
|
||||||
|
now = now - (now % DATA_INTERVAL)
|
||||||
|
line = ("%d:" % now) + ":".join(update_values)
|
||||||
|
print(line)
|
||||||
|
rrdtool.update(DATA_FILE, line)
|
||||||
|
rrdtool.update(ARCHIVE_DATA_FILE, line)
|
||||||
|
|
||||||
|
def update_graphs():
|
||||||
|
for name, lines in GRAPHS.items():
|
||||||
|
graph_params = [name, '-a', 'PNG', '-s', 'n-%d' % ARCHIVE_INTERVAL]
|
||||||
|
|
||||||
|
for name, lable, color in lines:
|
||||||
|
graph_params += ['DEF:%s=%s:%s:LAST' % (name, DATA_FILE, name)]
|
||||||
|
graph_params += ['LINE1:%s%s:%s' % (name, color, lable)]
|
||||||
|
|
||||||
|
rrdtool.graph(*graph_params)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
pass
|
pass
|
||||||
|
|
Loading…
Reference in New Issue