from rowers.models import Workout, User, Rower from rowingdata import rowingdata as rrdata from rowingdata import rower as rrower from rowingdata import main as rmain from pandas import DataFrame,Series import pandas as pd import numpy as np import itertools from django.conf import settings from sqlalchemy import create_engine import sqlalchemy as sa user = settings.DATABASES['default']['USER'] password = settings.DATABASES['default']['PASSWORD'] database_name = settings.DATABASES['default']['NAME'] host = settings.DATABASES['default']['HOST'] port = settings.DATABASES['default']['PORT'] database_url = 'mysql://{user}:{password}@{host}:{port}/{database_name}'.format( user=user, password=password, database_name=database_name, host=host, port=port, ) if settings.DEBUG or user=='': # database_url = 'sqlite:///db.sqlite3' database_url = 'sqlite:///'+database_name engine = create_engine(database_url, echo=False) from scipy.signal import savgol_filter import datetime def niceformat(values): out = [] for v in values: formattedv = strfdelta(v) out.append(formattedv) return out def strfdelta(tdelta): try: minutes,seconds = divmod(tdelta.seconds,60) tenths = int(tdelta.microseconds/1e5) except AttributeError: minutes,seconds = divmod(tdelta.view(np.int64),60e9) seconds,rest = divmod(seconds,1e9) tenths = int(rest/1e8) res = "{minutes:0>2}:{seconds:0>2}.{tenths:0>1}".format( minutes=minutes, seconds=seconds, tenths=tenths, ) return res def nicepaceformat(values): out = [] for v in values: formattedv = strfdelta(v) out.append(formattedv) return out def timedeltaconv(x): dt = datetime.timedelta(seconds=x) return dt def rdata(file,rower=rrower()): try: res = rrdata(file,rower=rower) except IOError: res = 0 return res def getrowdata_db(id=0): data = read_df_sql(id) data['pace'] = data['pace']/1.0e6 data['ergpace'] = data['ergpace']/1.0e6 data['nowindpace'] = data['nowindpace']/1.0e6 data['time'] = data['time']/1.0e6 data['x_right'] = data['x_right']/1.0e6 if data.empty: rowdata,row = getrowdata(id=id) if rowdata: data = dataprep(rowdata.df,id=id,bands=True,barchart=True,otwpower=True) else: data = pd.DataFrame() # returning empty dataframe else: row = Workout.objects.get(id=id) return data,row def getsmallrowdata_db(xparam,yparam1,yparam2,ids=[]): if yparam2 == 'None': yparam2 = yparam1 prepmultipledata(ids) data = read_cols_df_sql(ids,xparam,yparam1,yparam2) if xparam == 'time': data['time'] = data['time']/1.0e6 if yparam1 == 'pace': data['pace'] = data['pace']/1.0e6 if yparam2 == 'pace': data['pace'] = data['pace']/1.0e6 return data def getrowdata(id=0): # check if valid ID exists (workout exists) row = Workout.objects.get(id=id) f1 = row.csvfilename # get user r = row.user u = r.user rr = rrower(hrmax=r.max,hrut2=r.ut2, hrut1=r.ut1,hrat=r.at, hrtr=r.tr,hran=r.an,ftp=r.ftp) rowdata = rdata(f1,rower=rr) return rowdata,row def prepmultipledata(ids): query = sa.text('SELECT DISTINCT workoutid FROM strokedata') with engine.connect() as conn, conn.begin(): res = conn.execute(query) res = list(itertools.chain.from_iterable(res.fetchall())) res = list(set(ids)-set(res)) for id in res: rowdata,row = getrowdata(id=id) if rowdata: data = dataprep(rowdata.df,id=id,bands=True,barchart=True,otwpower=True) return res def read_cols_df_sql(ids,col1,col2,col3): columns = list(set((col1,col2,col3,'distance','spm'))) cls = '' for column in columns: cls += column+', ' cls = cls[:-2] if len(ids) == 0: query = sa.text('SELECT {columns} FROM strokedata WHERE workoutid=0'.format( columns = cls, )) elif len(ids) == 1: query = sa.text('SELECT {columns} FROM strokedata WHERE workoutid={id}'.format( id = ids[0], columns = cls, )) else: query = sa.text('SELECT {columns} FROM strokedata WHERE workoutid IN {ids}'.format( columns = cls, ids = tuple(ids), )) df = pd.read_sql_query(query,engine) return df def read_df_sql(id): df = pd.read_sql_query(sa.text('SELECT * FROM strokedata WHERE workoutid={id}'.format( id=id)), engine) return df def smalldataprep(therows,xparam,yparam1,yparam2): df = pd.DataFrame() if yparam2 == 'None': yparam2 = 'power' df[xparam] = [] df[yparam1] = [] df[yparam2] = [] df['distance'] = [] df['spm'] = [] for workout in therows: f1 = workout.csvfilename try: rowdata = dataprep(rrdata(f1).df) rowdata = pd.DataFrame({xparam: rowdata[xparam], yparam1: rowdata[yparam1], yparam2: rowdata[yparam2], 'distance': rowdata['distance'], 'spm': rowdata['spm'], } ) df = pd.concat([df,rowdata],ignore_index=True) except IOError: pass return df def dataprep(rowdatadf,id=0,bands=False,barchart=False,otwpower=False): rowdatadf.set_index([range(len(rowdatadf))],inplace=True) t = rowdatadf.ix[:,'TimeStamp (sec)'] t = pd.Series(t-rowdatadf.ix[0,'TimeStamp (sec)']) row_index = rowdatadf.ix[:,' Stroke500mPace (sec/500m)'] > 3000 rowdatadf.loc[row_index,' Stroke500mPace (sec/500m)'] = 3000. p = rowdatadf.ix[:,' Stroke500mPace (sec/500m)'] hr = rowdatadf.ix[:,' HRCur (bpm)'] spm = rowdatadf.ix[:,' Cadence (stokes/min)'] cumdist = rowdatadf.ix[:,'cum_dist'] power = rowdatadf.ix[:,' Power (watts)'] averageforce = rowdatadf.ix[:,' AverageDriveForce (lbs)'] drivelength = rowdatadf.ix[:,' DriveLength (meters)'] try: workoutstate = rowdatadf.ix[:,' WorkoutState'] except KeyError: workoutstate = 0*hr peakforce = rowdatadf.ix[:,' PeakDriveForce (lbs)'] forceratio = averageforce/peakforce forceratio = forceratio.fillna(value=0) f = rowdatadf['TimeStamp (sec)'].diff().mean() windowsize = 2*(int(10./(f)))+1 if windowsize <= 3: windowsize = 5 if windowsize > 3: spm = savgol_filter(spm,windowsize,3) hr = savgol_filter(hr,windowsize,3) drivelength = savgol_filter(drivelength,windowsize,3) forceratio = savgol_filter(forceratio,windowsize,3) try: t2 = t.fillna(method='ffill').apply(lambda x: timedeltaconv(x)) except TypeError: t2 = 0*t p2 = p.fillna(method='ffill').apply(lambda x: timedeltaconv(x)) drivespeed = drivelength/rowdatadf[' DriveTime (ms)']*1.0e3 drivespeed = drivespeed.fillna(value=0) driveenergy = drivelength*averageforce*4.44822 distance = rowdatadf.ix[:,'cum_dist'] data = DataFrame( dict( time = t2, timesecs = t, hr = hr, pace = p2, pseconds=p, spm = spm, cumdist = cumdist, ftime = niceformat(t2), fpace = nicepaceformat(p2), driveenergy=driveenergy, power=power, workoutstate=workoutstate, averageforce=averageforce, drivelength=drivelength, peakforce=peakforce, forceratio=forceratio, distance=distance, drivespeed=drivespeed, ) ) if bands: # HR bands data['hr_ut2'] = rowdatadf.ix[:,'hr_ut2'] data['hr_ut1'] = rowdatadf.ix[:,'hr_ut1'] data['hr_at'] = rowdatadf.ix[:,'hr_at'] data['hr_tr'] = rowdatadf.ix[:,'hr_tr'] data['hr_an'] = rowdatadf.ix[:,'hr_an'] data['hr_max'] = rowdatadf.ix[:,'hr_max'] data['hr_bottom'] = 0.0*data['hr'] if barchart: # time increments for bar chart time_increments = rowdatadf.ix[:,' ElapsedTime (sec)'].diff() time_increments[0] = time_increments[1] time_increments = 0.5*time_increments+0.5*np.abs(time_increments) x_right = (t2+time_increments.apply(lambda x:timedeltaconv(x))) data['x_right'] = x_right if otwpower: try: nowindpace = rowdatadf.ix[:,'nowindpace'] except KeyError: nowindpace = p try: equivergpower = rowdatadf.ix[:,'equivergpower'] except KeyError: equivergpower = 0*p+50. nowindpace = nowindpace.apply(lambda x: timedeltaconv(x)) ergvelo = (equivergpower/2.8)**(1./3.) ergpace = 500./ergvelo ergpace[ergpace == np.inf] = 240. ergpace = ergpace.apply(lambda x: timedeltaconv(x)) data['ergpace'] = ergpace data['nowindpace'] = nowindpace data['equivergpower'] = equivergpower data['fergpace'] = nicepaceformat(ergpace) data['fnowindpace'] = nicepaceformat(nowindpace) data = data.replace([-np.inf,np.inf],np.nan) data = data.fillna(method='ffill') # write data if id given if id != 0: data['workoutid'] = id with engine.connect() as conn, conn.begin(): data.to_sql('strokedata',engine,if_exists='append',index=False) return data