Skip to content

Commit

Permalink
Initial release
Browse files Browse the repository at this point in the history
  • Loading branch information
slafi committed Oct 15, 2019
1 parent 8d48e55 commit 7261ce4
Show file tree
Hide file tree
Showing 4 changed files with 137 additions and 25 deletions.
69 changes: 46 additions & 23 deletions app.py
Original file line number Diff line number Diff line change
@@ -1,66 +1,89 @@
from multiprocessing import Process, Queue

import os
import sys
import threading
import time

# Import custom subpackages
from core import config, monitor
from common import utils, logger, recorder, database

import signal, sys, os
import threading, pkgutil
import time


## Initialize the logger
logger = logger.get_logger('voltazero_monitor')

## Define main thread stop flag
#StopFlag = threading.Event()


def signal_handler(signum, frame):
"""A signal handler which sets the stop flag if a termination signal is triggered
:signum: the signal number
:frame: the stack frame which triggered the signal
"""
logger.info('Stop flag raised. Main thread is stopping...')
#StopFlag.set()


import pkgutil
import os.path

if __name__ == '__main__':

## Clear console
utils.clear_console()

## Initialize the logger
logger = logger.get_logger('voltazero_monitor')

dirpath = os.getcwd()
#print(f"Current directory is: {dirpath}")
#print(f"Main ID: {os.getpid()}")
## Setup stop signal handler
#signal.signal(signal.SIGTERM, signal_handler)
#signal.signal(signal.SIGINT, signal_handler)
#signal.signal(signal.SIGABRT, signal_handler)
#signal.signal(signal.SIGQUIT, signal_handler)
print(f'Main: {os.getpid()}')

## Initialization
config_file = "./core/config.json"

## Setup telemetry queue
q = Queue()

## Read app config
## Read the application config
appConfig = config.AppConfig(config_file)
rc = appConfig.load_app_config()

if rc == -1:
print(f'The configuration file cannot be found!')
logger.error(f'The configuration file cannot be found!')
sys.exit()
elif rc == -2:
print(f'An exception has occured. Application will stop!')
logger.error(f'An exception has occured. Application will stop!')
sys.exit()
else:
logger.info(f'App configuration loaded and parsed successfully.')

## Establish connectivity to the MQTT broker
pmonitor = monitor.Monitor(appConfig, q, client_id="cp100")
pmonitor.start()

## Initialize and start database recorder
precorder = recorder.Recorder(q, appConfig, interval=60.0, batch_size=20)
precorder.start()
trecorder = recorder.Recorder(q, appConfig, interval=60.0, batch_size=20)
trecorder.start()

time.sleep(60)
#StopFlag.wait()

while True:
try:
time.sleep(1)
except KeyboardInterrupt:
print("KeyboardInterrupt has been caught.")
break

## Stop the monitor process
pmonitor.terminate()
pmonitor.stop()
pmonitor.join()

## Stop the recorder thread
precorder.stop()
precorder.join()
trecorder.stop()
trecorder.join()

## Load data from the queue
## For debug, check the data remaining in the queue
data = []

while not q.empty():
Expand Down
2 changes: 2 additions & 0 deletions core/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ def __init__(self, config_filename):
self.table_name = None
self.time_window = None
self.batch_size = None
self.db_query_interval = None


def load_app_config(self):
Expand Down Expand Up @@ -71,6 +72,7 @@ def parse_app_config(self, data):
self.table_name = data["table_name"]
self.time_window = data["time_window"]
self.batch_size = data["batch_size"]
self.db_query_interval = data["db_query_interval"]

return 0

Expand Down
14 changes: 12 additions & 2 deletions core/monitor.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,14 +39,16 @@ def __init__(self, appconfig, q, client_id):
:param appconfig: the application configuration object
:param client_id: the assigned client identifier
"""

print(f'Created1: {os.getpid()}')
super(Monitor, self).__init__()
print(f'Created2: {os.getpid()}')
self.appconfig = appconfig
self.q = q
self.subscribed = False
self.connected = False
self.client_id = client_id
self.Stopped = True
self.client = None


def init_connection(self):
Expand Down Expand Up @@ -80,6 +82,7 @@ def run(self):

try:
self.PID = os.getpid()
print(f'Created: {os.getpid()}')
self.Stopped = False
self.init_connection()

Expand All @@ -92,6 +95,10 @@ def run(self):
except Exception as e:
logger.error(f"Exception: {str(e)}")
return -1

"""except KeyboardInterrupt:
self.client.disconnect()
return 0"""


def stop(self):
Expand All @@ -104,12 +111,15 @@ def stop(self):
try:
self.Stopped = True

print(f'Created: {os.getpid()}')
if self.client != None and self.connected == True:
self.client.unsubscribe(self.appconfig.topic)
self.client.disconnect()
self.connected = False
self.subscribed = False


super(Monitor, self).terminate()

return 0

except Exception as e:
Expand Down
77 changes: 77 additions & 0 deletions core/viewer.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
from threading import Timer, Thread, Event, currentThread
#from common import logger, database

from matplotlib.figure import Figure
from platform import system

import matplotlib.pyplot as plt
import numpy as np
import datetime
import time
import logging

### Initialize logger for the module
logger = logging.getLogger('voltazero_monitor')


def plt_maximize():
# See discussion: https://stackoverflow.com/questions/12439588/how-to-maximize-a-plt-show-window-using-python
backend = plt.get_backend()
cfm = plt.get_current_fig_manager()

if backend == "wxAgg":
cfm.frame.Maximize(True)
elif backend == "TkAgg":
pos = str(system()).lower()
if pos == "win32" or pos == 'windows':
cfm.window.state('zoomed') # This is windows only
else:
cfm.resize(*cfm.window.maxsize())
elif backend == 'QT4Agg':
cfm.window.showMaximized()
elif callable(getattr(cfm, "full_screen_toggle", None)):
if not getattr(cfm, "flag_is_max", None):
cfm.full_screen_toggle()
cfm.flag_is_max = True
else:
raise RuntimeError("plt_maximize() is not implemented for current backend:", backend)


class Viewer(Thread):


def __init__(self):
self.sensors = ["Temp. (t0)", "Light Sensor", "Buzz. State", "Temp. (t1)", "Thermo. (th)", "Infrared Sensor"]


def init(self, window_title='Sensors data'):
# Creates just a figure and only one subplot
self.fig, self.axs = plt.subplots(6, sharex=True)

# Some example data to display
x = np.linspace(0, 2 * np.pi, 400)
y = np.sin(x ** 2)

for i in range(6):
self.axs[i].plot(x, y)
self.axs[i].grid(True)
self.axs[i].set_ylabel(self.sensors[i])

#set window title
self.fig.canvas.set_window_title(f"{window_title} - Last update: {datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')}")

try:
# Maximize window
plt_maximize()
except Exception as e:
print(f'Exception: {str(e)}')

# Show plot
plt.show()



if __name__ == "__main__":

viewer = Viewer()
viewer.init()

0 comments on commit 7261ce4

Please sign in to comment.