|
@@ -0,0 +1,56 @@
|
|
|
+#
|
|
|
+# Copyright (c) Daniel Sheffield 2023
|
|
|
+# All rights reserved
|
|
|
+#
|
|
|
+# THIS SOFTWARE IS PROVIDED AS IS WITHOUT WARRANTY
|
|
|
+from bottle import route, request, run, response, abort
|
|
|
+from psycopg import sql, Cursor, connect
|
|
|
+from datetime import date, datetime
|
|
|
+import os
|
|
|
+import matplotlib.pyplot as plt
|
|
|
+import seaborn as sns
|
|
|
+from ..activities.Plot import (
|
|
|
+ get_data,
|
|
|
+)
|
|
|
+from ..data.QueryManager import QueryManager, display_mapper
|
|
|
+def line(pivot, ylabel=None, xlabel=None):
|
|
|
+ ax = sns.lineplot(data=pivot, markers=True)
|
|
|
+ ax.set_xlabel(xlabel)
|
|
|
+ ax.set_ylabel(ylabel)
|
|
|
+
|
|
|
+ALL_UNITS = {'g','kg','mL','L','Pieces','Bunches','Bags'}
|
|
|
+PARAMS ={ 'group', 'category', 'product', 'unit' }
|
|
|
+host = f"host={os.getenv('HOST')}"
|
|
|
+db = f"dbname={os.getenv('DB', 'grocery')}"
|
|
|
+user = f"user={os.getenv('USER', 'das')}"
|
|
|
+password = f"password={os.getenv('PASSWORD','')}"
|
|
|
+if not password.split('=',1)[1]:
|
|
|
+ password = ''
|
|
|
+conn = connect(f"{host} {db} {user} {password}")
|
|
|
+from io import StringIO
|
|
|
+@route('/grocery/trend')
|
|
|
+def trend():
|
|
|
+ try:
|
|
|
+ with conn.cursor() as cur:
|
|
|
+ query_manager = QueryManager(cur, display_mapper)
|
|
|
+ fields = { k: request.query[k] for k in request.query.keys() if k in PARAMS }
|
|
|
+ unit = fields['unit'] = fields['unit'] if 'unit' in fields else None or 'kg'
|
|
|
+ if unit not in ALL_UNITS:
|
|
|
+ raise abort(400, f"Unsupported unit {unit}")
|
|
|
+
|
|
|
+ data = get_data(query_manager, **fields)
|
|
|
+ if data.empty:
|
|
|
+ raise abort(404, f"No data for {fields}")
|
|
|
+ pivot = data.pivot_table(index=['ts_raw',], columns=['product',], values=['$/unit'], aggfunc='mean')
|
|
|
+ pivot.columns = pivot.columns.droplevel()
|
|
|
+ plt.figure(figsize=[16, 9])
|
|
|
+ line(pivot, xlabel='Time', ylabel=f'$ / {unit}')
|
|
|
+ f = StringIO()
|
|
|
+ plt.savefig(f, format='svg')
|
|
|
+ finally:
|
|
|
+ conn.commit()
|
|
|
+
|
|
|
+ response.content_type = 'image/svg+xml; charset=utf-8'
|
|
|
+ return f.getvalue()
|
|
|
+
|
|
|
+run(host='127.0.0.1', port=6772)
|