From 92cc9d5811194f950f31ce1ef3660a39dacbf51e Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Tue, 7 Jan 2020 14:20:22 +0100 Subject: [PATCH 1/5] forgot to save --- rowers/views/analysisviews.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rowers/views/analysisviews.py b/rowers/views/analysisviews.py index a7ea6a70..5f19f8c1 100644 --- a/rowers/views/analysisviews.py +++ b/rowers/views/analysisviews.py @@ -4453,7 +4453,7 @@ def alert_report_view(request,id=0,userid=0,nperiod=0): raise Http404("This alert doesn't exist") - if alert.manager != request.user: + if not checkalertowner(alert,request.user): raise PermissionDenied('You are not allowed to edit this Alert') stats = alert_get_stats(alert,nperiod=nperiod) From 07e9a5abf1d646e26498f276a0153457536b74f2 Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Tue, 7 Jan 2020 14:57:05 +0100 Subject: [PATCH 2/5] added impeller to Workout model and saving of this in dataprep need more work and testing --- rowers/dataprep.py | 28 ++++++++++++++++++++-------- rowers/models.py | 1 + 2 files changed, 21 insertions(+), 8 deletions(-) diff --git a/rowers/dataprep.py b/rowers/dataprep.py index 33f961be..747135e5 100644 --- a/rowers/dataprep.py +++ b/rowers/dataprep.py @@ -1081,7 +1081,8 @@ def save_workout_database(f2, r, dosmooth=True, workouttype='rower', makeprivate=False, oarlength=2.89, inboard=0.88, forceunit='lbs', - consistencychecks=False): + consistencychecks=False, + impeller=False): message = None powerperc = 100 * np.array([r.pw_ut2, @@ -1289,7 +1290,8 @@ def save_workout_database(f2, r, dosmooth=True, workouttype='rower', startdatetime=workoutstartdatetime, inboard=inboard, oarlength=oarlength, timezone=timezone_str, - privacy=privacy) + privacy=privacy, + impeller=impeller) try: w.save() except ValidationError: @@ -1421,24 +1423,32 @@ def handle_nonpainsled(f2, fileformat, summary=''): oarlength = 2.89 inboard = 0.88 hasrecognized = False + impeller = False row,hasrecognized,summary,fileformat = parsenonpainsled(fileformat,f2,summary) # Handle c2log if (fileformat == 'c2log' or fileformat == 'rowprolog'): - return (0,'',0,0,'') + return (0,'',0,0,'',impeller) if not hasrecognized: - return (0,'',0,0,'') + return (0,'',0,0,'',impeller) f_to_be_deleted = f2 # should delete file f2 = f2[:-4] + 'o.csv' try: row2 = rrdata(df = row.df) + if fileformat == 'speedcoach2': + # impeller consistency + impellerdata, consistent, ratio = row.impellerconsistent(threshold=0.3) + if impellerdata and consistent: + impeller = True + if impellerdata and not consistent: + row2.use_gps() row2.write_csv(f2, gzip=True) except: - return (0,'',0,0,'') + return (0,'',0,0,'',impeller) # os.remove(f2) try: @@ -1449,7 +1459,7 @@ def handle_nonpainsled(f2, fileformat, summary=''): except: pass - return (f2, summary, oarlength, inboard, fileformat) + return (f2, summary, oarlength, inboard, fileformat, impeller) # Create new workout from file and store it in the database # This routine should be used everywhere in views.py and mailprocessing.py @@ -1476,6 +1486,7 @@ def new_workout_from_file(r, f2, inboard = 0.88 if len(fileformat) == 3 and fileformat[0] == 'zip': f_to_be_deleted = f2 + impeller = False workoutsbox = Mailbox.objects.filter(name='workouts')[0] msg = Message(mailbox=workoutsbox, from_header=r.user.email, @@ -1543,7 +1554,7 @@ def new_workout_from_file(r, f2, # handle non-Painsled by converting it to painsled compatible CSV if (fileformat != 'csv'): - f2, summary, oarlength, inboard, fileformat = handle_nonpainsled( + f2, summary, oarlength, inboard, fileformat, impeller = handle_nonpainsled( f2, fileformat, summary=summary @@ -1571,7 +1582,8 @@ def new_workout_from_file(r, f2, summary=summary, inboard=inboard, oarlength=oarlength, title=title, - forceunit='N' + forceunit='N', + impeller=impeller, ) return (id, message, f2) diff --git a/rowers/models.py b/rowers/models.py index 47b6d629..fd830b37 100644 --- a/rowers/models.py +++ b/rowers/models.py @@ -2734,6 +2734,7 @@ class Workout(models.Model): choices=privacychoices) rankingpiece = models.BooleanField(default=False,verbose_name='Ranking Piece') duplicate = models.BooleanField(default=False,verbose_name='Duplicate Workout') + impeller = models.BooleanField(default=False,verbose_name='Impeller') def save(self, *args, **kwargs): user = self.user From d88a0f7aea6a0b5f7705cbf0167ff9e52f29a50e Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Tue, 7 Jan 2020 18:14:27 +0100 Subject: [PATCH 3/5] added menu items --- rowers/dataprep.py | 22 ++++++++++------------ rowers/templates/menu_workout.html | 12 ++++++++++++ templates/newbase.html | 1 + 3 files changed, 23 insertions(+), 12 deletions(-) diff --git a/rowers/dataprep.py b/rowers/dataprep.py index 747135e5..b0d015b9 100644 --- a/rowers/dataprep.py +++ b/rowers/dataprep.py @@ -1437,18 +1437,16 @@ def handle_nonpainsled(f2, fileformat, summary=''): f_to_be_deleted = f2 # should delete file f2 = f2[:-4] + 'o.csv' - try: - row2 = rrdata(df = row.df) - if fileformat == 'speedcoach2': - # impeller consistency - impellerdata, consistent, ratio = row.impellerconsistent(threshold=0.3) - if impellerdata and consistent: - impeller = True - if impellerdata and not consistent: - row2.use_gps() - row2.write_csv(f2, gzip=True) - except: - return (0,'',0,0,'',impeller) + row2 = rrdata(df = row.df) + if 'speedcoach2' in fileformat: + # impeller consistency + impellerdata, consistent, ratio = row.impellerconsistent(threshold=0.3) + if impellerdata and consistent: + impeller = True + if impellerdata and not consistent: + row2.use_gpsdata() + row2.write_csv(f2, gzip=True) + # os.remove(f2) try: diff --git a/rowers/templates/menu_workout.html b/rowers/templates/menu_workout.html index f6edffd0..f8d4ee7c 100644 --- a/rowers/templates/menu_workout.html +++ b/rowers/templates/menu_workout.html @@ -287,6 +287,18 @@  OTW Power + {% if 'speedcoach2' in workout.workoutsource %} +
  • + +  Use GPS data + +
  • +
  • + +  Use Impeller data + +
  • + {% endif %} {% endif %}
  • diff --git a/templates/newbase.html b/templates/newbase.html index 885e3f90..41486614 100644 --- a/templates/newbase.html +++ b/templates/newbase.html @@ -43,6 +43,7 @@ + From dfbae0b2db200950cdfff7cacb57c38bb915a20e Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Tue, 7 Jan 2020 18:21:00 +0100 Subject: [PATCH 4/5] added bullet --- rowers/templates/menu_workout.html | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/rowers/templates/menu_workout.html b/rowers/templates/menu_workout.html index f8d4ee7c..40cc7f00 100644 --- a/rowers/templates/menu_workout.html +++ b/rowers/templates/menu_workout.html @@ -290,19 +290,22 @@ {% if 'speedcoach2' in workout.workoutsource %}
  • -  Use GPS data + + {% if workout.impeller %}• {% else %} {% endif %}Use GPS data
  • -  Use Impeller data + + {% if workout.impeller %} {% else %}• {% endif %}Use Impeller data
  • {% endif %} {% endif %}
  • -  In-Stroke Metrics + + In-Stroke Metrics
  • From 498a06ef1df83ff1e6fbec52fe2e8eeb3472c9da Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Tue, 7 Jan 2020 22:14:57 +0100 Subject: [PATCH 5/5] gps/impeller switching implemented --- rowers/templates/menu_workout.html | 4 +- rowers/urls.py | 4 ++ rowers/views/workoutviews.py | 60 ++++++++++++++++++++++++------ 3 files changed, 54 insertions(+), 14 deletions(-) diff --git a/rowers/templates/menu_workout.html b/rowers/templates/menu_workout.html index 40cc7f00..5c06f2a4 100644 --- a/rowers/templates/menu_workout.html +++ b/rowers/templates/menu_workout.html @@ -291,13 +291,13 @@
  • - {% if workout.impeller %}• {% else %} {% endif %}Use GPS data + {% if workout.impeller %} {% else %}• {% endif %}Use GPS data
  • - {% if workout.impeller %} {% else %}• {% endif %}Use Impeller data + {% if workout.impeller %}• {% else %} {% endif %}Use Impeller data
  • {% endif %} diff --git a/rowers/urls.py b/rowers/urls.py index 5696c0d4..97a45af6 100644 --- a/rowers/urls.py +++ b/rowers/urls.py @@ -283,6 +283,10 @@ urlpatterns = [ re_path(r'^graph/(?P\d+)/delete/$',views.GraphDelete.as_view(),name='graph_delete'), re_path(r'^workout/(?P\b[0-9A-Fa-f]+\b)/get-thumbnails/$',views.get_thumbnails, name='get_thumbnails'), + re_path(r'^workout/(?P\b[0-9A-Fa-f]+\b)/otwuseimpeller/$',views.otw_use_impeller, + name='otw_use_impeller'), + re_path(r'^workout/(?P\b[0-9A-Fa-f]+\b)/otwusegps/$',views.otw_use_gps, + name='otw_use_gps'), re_path(r'^workout/(?P\b[0-9A-Fa-f]+\b)/toggle-ranking/$',views.workout_toggle_ranking, name='workout_toggle_ranking'), re_path(r'^workout/(?P\b[0-9A-Fa-f]+\b)/get-testscript/$',views.get_testscript, diff --git a/rowers/views/workoutviews.py b/rowers/views/workoutviews.py index 592cbc14..f72537f9 100644 --- a/rowers/views/workoutviews.py +++ b/rowers/views/workoutviews.py @@ -456,18 +456,54 @@ def workout_forcecurve_view(request,id=0,workstrokesonly=False): 'teams':get_my_teams(request.user), }) -# Test asynchronous tasking and messaging -#@login_required() -#def workout_test_task_view(request,id=0): -# row = Workout.objects.get(id=id) -# res = myqueue(queuehigh,addcomment2,request.user.id,row.id)# -# -# -# url = reverse('workout_edit_view', -# kwargs = { -# 'id':int(id), -# }) -# return HttpResponseRedirect(url) +# Switch from GPS to Impeller (only for SpeedCoach 2, if impeller data) +@login_required +def otw_use_impeller(request,id=0): + w = get_workout(id) + + if (checkworkoutuser(request.user,w)==False): + raise PermissionDenied("Access denied") + + row = rdata(w.csvfilename) + success = row.use_impellerdata() + if success: + row.write_csv(w.csvfilename) + dataprep.update_strokedata(w.id,row.df) + w.impeller = True + w.save() + messages.info(request,'The distance and speed data are now based on Impeller data') + else: + messages.error(request,'No impeller data found') + + url = reverse('workout_edit_view',kwargs={'id':encoder.encode_hex(w.id)}) + + return HttpResponseRedirect(url) + + +# Switch from Impeller to GPS (only for SpeedCoach 2, if impeller data) +@login_required +def otw_use_gps(request,id=0): + w = get_workout(id) + + if (checkworkoutuser(request.user,w)==False): + raise PermissionDenied("Access denied") + + row = rdata(w.csvfilename) + success = row.use_gpsdata() + if success: + row.write_csv(w.csvfilename) + dataprep.update_strokedata(w.id,row.df) + w.impeller = False + w.save() + messages.info(request,'The distance and speed data are now based on GPS data') + else: + messages.error(request,'No GPS data found') + + url = reverse('workout_edit_view',kwargs={'id':encoder.encode_hex(w.id)}) + + return HttpResponseRedirect(url) + + # Show Stroke power histogram for a workout @login_required()