Added database creation and updates
This commit is contained in:
parent
1c4e50d790
commit
fa600586ae
|
@ -1,3 +1,5 @@
|
|||
*.pyc
|
||||
__pycache__
|
||||
virtenv
|
||||
*.rrd
|
||||
*.png
|
||||
|
|
43
config.py
43
config.py
|
@ -1,29 +1,52 @@
|
|||
#!/usr/bin/env python3
|
||||
import serial # for parity constants
|
||||
|
||||
from configutils import *
|
||||
|
||||
SERIAL = '/dev/ttyUSB0'
|
||||
BAUD_RATE = 4800
|
||||
STOP_BITS = 1
|
||||
PARITY = None
|
||||
|
||||
DATA_FILE = './test.rrd'
|
||||
ARCHIVE_DATA_FILE = './test_archive.rrd'
|
||||
DATA_INTERVAL = 60
|
||||
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
|
||||
CRC_TYPE = 'xmodem'
|
||||
|
||||
|
||||
STORED_VALUES = [
|
||||
'U_bat',
|
||||
'U_mod1',
|
||||
'U_mod2',
|
||||
'I_pv_in',
|
||||
'I_load_total',
|
||||
'load_switch',
|
||||
'max_charge_bat_day',
|
||||
'max_charge_load_day'
|
||||
StoredValue('U_bat', 0.0, 20.0),
|
||||
StoredValue('U_mod1', 0.0, 20.0),
|
||||
StoredValue('U_mod2', 0.0, 20.0),
|
||||
StoredValue('I_pv_in', 0.0, 100.0),
|
||||
StoredValue('I_load_total', 0.0, 100.0),
|
||||
StoredValue('load_switch', 0, 1),
|
||||
StoredValue('max_charge_bat_day', 0.0, 1000.0),
|
||||
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',
|
||||
'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
|
||||
import os
|
||||
import crcmod
|
||||
from random import randint
|
||||
from time import sleep
|
||||
|
||||
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)
|
||||
|
||||
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) + ";"
|
||||
crc = calc_crc(payload.encode('ascii'))
|
||||
crc_str = chr((crc & 0xFF00) >> 8) + chr(crc & 0xFF)
|
||||
|
@ -19,13 +31,17 @@ def gen_line():
|
|||
|
||||
|
||||
def main():
|
||||
line = gen_line()
|
||||
result = parse_line(line)
|
||||
if not os.path.exists(DATA_FILE) or not os.path.exists(ARCHIVE_DATA_FILE):
|
||||
create_database()
|
||||
sleep(60)
|
||||
|
||||
print(result)
|
||||
|
||||
|
||||
|
||||
while True:
|
||||
print("Adding Line...")
|
||||
line = gen_line()
|
||||
parsed = parse_line(line)
|
||||
update_database(parsed)
|
||||
update_graphs()
|
||||
sleep(60)
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
||||
|
|
55
update.py
55
update.py
|
@ -1,6 +1,8 @@
|
|||
#!/usr/bin/env python3
|
||||
import time
|
||||
import serial
|
||||
import crcmod
|
||||
import rrdtool
|
||||
|
||||
from config import *
|
||||
|
||||
|
@ -24,6 +26,59 @@ def parse_line(line):
|
|||
|
||||
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():
|
||||
pass
|
||||
|
|
Loading…
Reference in New Issue