Private
Public Access
1
0
This commit is contained in:
2024-07-26 16:31:29 +02:00
parent 4968ed5550
commit 2dea905b3c
5 changed files with 262 additions and 33 deletions

197
rowers/session_utils.py Normal file
View File

@@ -0,0 +1,197 @@
from django.utils import timezone
from rowers.models import Workout, VirtualRaceResult, CourseTestResult
def timefield_to_seconds_duration(t):
duration = t.hour*3600.
duration += t.minute * 60.
duration += t.second
duration += t.microsecond/1.e6
return duration
def is_session_complete_ws(ws, ps):
ws = ws.order_by("date")
if ws.count() == 0:
today = timezone.now()
if today.date() > ps.enddate:
verdict = 'missed'
ratio = 0
return ratio, verdict, None
else:
return 0, 'not done', None
value = ps.sessionvalue
if ps.sessionunit == 'min':
value *= 60.
elif ps.sessionunit == 'km': # pragma: no cover
value *= 1000.
cratiomin = 1
# cratiomax = 1
cratios = {
'better than nothing': 0,
'partial': 0.6,
'on target': 0.8,
'over target': 1.2,
'way over target': 1.5
}
if ps.criterium == 'none':
if ps.sessiontype == 'session':
cratiomin = 0.8
# cratiomax = 1.2
else:
cratios['on target'] = 0.9167
cratios['over target'] = 1.0833
cratiomin = 0.9167
# cratiomax = 1.0833
score = 0
completiondate = None
for w in ws:
if ps.sessionmode == 'distance':
score += w.distance
elif ps.sessionmode == 'time':
durationseconds = timefield_to_seconds_duration(w.duration)
score += durationseconds
elif ps.sessionmode == 'TRIMP':
score += w.trimp
elif ps.sessionmode == 'rScore':
score += wrscore
if not completiondate and score >= cratiomin*value:
completiondate = w.date
try:
ratio = score/float(int(value))
except ZeroDivisionError: # pragma: no cover
ratio = 0
verdict = 'better than nothing'
if ps.sessiontype in ['session', 'cycletarget']:
if ps.criterium == 'exact':
if ratio == 1.0:
return ratio, 'on target', completiondate
else:
if not completiondate: # pragma: no cover
completiondate = ws.reverse()[0].date
return ratio, 'partial', completiondate
elif ps.criterium == 'minimum': # pragma: no cover
if ratio >= 1.0:
return ratio, 'on target', completiondate
else:
if not completiondate:
completiondate = ws.reverse()[0].date
return ratio, 'partial', completiondate
else:
thevalue = 0
for key, value in cratios.items():
if ratio > value and value > thevalue:
verdict = key
thevalue = value
completiondate = ws.reverse()[0].date
return ratio, verdict, completiondate
elif ps.sessiontype == 'test':
if ratio == 1.0:
return ratio, 'on target', completiondate
else:
return ratio, 'partial', completiondate
elif ps.sessiontype == 'challenge':
if ps.criterium == 'exact':
if ratio == 1.0:
return ratio, 'on target', completiondate
else:
return ratio, 'partial', completiondate
elif ps.criterium == 'minimum': # pragma: no cover
if ratio > 1.0:
return ratio, 'on target', completiondate
else:
if not completiondate:
completiondate = ws.reverse()[0].date
return ratio, 'partial', completiondate
else:
if not completiondate: # pragma: no cover
completiondate = ws.reverse()[0].date
return ratio, 'partial', completiondate
elif ps.sessiontype == 'race': # pragma: no cover
vs = VirtualRaceResult.objects.filter(race=ps)
wids = [w.id for w in ws]
for record in vs:
if record.workoutid in wids:
if record.coursecompleted:
ratio = record.distance/ps.sessionvalue
return ratio, 'on target', completiondate
else:
ratio = record.distance/ps.sessionvalue
return ratio, 'partial', completiondate
return (0, 'partial', None)
elif ps.sessiontype in ['fastest_time', 'fastest_distance']: # pragma: no cover
vs = CourseTestResult.objects.filter(
plannedsession=ps, userid=ws[0].user.user.id)
completiondate = ws.reverse()[0].date
wids = [w.id for w in ws]
for record in vs:
if record.workoutid in wids:
if record.coursecompleted:
ratio = 1
return ratio, 'on target', completiondate
else:
return 0, 'partial', completiondate
if ws:
record = CourseTestResult(
userid=ws[0].user.id,
plannedsession=ps,
workoutid=ws[0].id,
duration=dt.time(0, 0),
coursecompleted=False
)
record.save()
return (0, 'not done', None)
elif ps.sessiontype == 'coursetest': # pragma: no cover
vs = CourseTestResult.objects.filter(plannedsession=ps)
wids = [w.id for w in ws]
for record in vs:
if record.workoutid in wids:
if record.coursecompleted:
ratio = record.distance/float(ps.sessionvalue)
return ratio, 'on target', completiondate
else:
ratio = record.distance/float(ps.sessionvalue)
return ratio, 'partial', completiondate
# we're still here - no record, need to create one
if ws:
record = CourseTestResult(
userid=ws[0].user.id,
plannedsession=ps,
workoutid=ws[0].id,
duration=dt.time(0, 0),
coursecompleted=False,
)
record.save()
_ = myqueue(queue, handle_check_race_course, ws[0].csvfilename,
ws[0].id, ps.course.id, record.id,
ws[0].user.user.email, ws[0].user.user.first_name,
mode='coursetest')
return (0, 'not done', None)
else: # pragma: no cover
if not completiondate:
completiondate = ws.reverse()[0].date
return ratio, verdict, completiondate
def is_session_complete(r, ps):
if r not in ps.rower.all(): # pragma: no cover
return 0, 'not assigned', None
ws = Workout.objects.filter(user=r, plannedsession=ps)
return is_session_complete_ws(ws, ps)