From 74e924a3c1d09ce9f4b2363d9a44c50964f20b37 Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Mon, 23 Oct 2017 08:56:10 +0200 Subject: [PATCH] send email to sender of unrecognized file The email processing sends a notification message to the person who sent a unrecognized file to the workouts@rowsandall.com email address. This way, people will know that their email has worked and perhaps stop sending 99 or more emails with the same unsupported file. --- rowers/mailprocessing.py | 16 +- rowers/tasks.py | 523 +++++++++++++++++++++------------------ 2 files changed, 296 insertions(+), 243 deletions(-) diff --git a/rowers/mailprocessing.py b/rowers/mailprocessing.py index 282fedbe..b6489e61 100644 --- a/rowers/mailprocessing.py +++ b/rowers/mailprocessing.py @@ -92,14 +92,22 @@ def make_new_workout_from_email(rower, datafile, name, cntr=0): # shutil.copyfileobj(f_in,f_out) fcopy = "media/"+datafilename if settings.DEBUG: - res = handle_sendemail_unrecognized.delay(fcopy, - rower.user.email) - + res = handle_sendemail_unrecognized.delay( + fcopy, + rower.user.email + ) + res = handle_sendemail_unrecognizedowner.delay( + rower.user.email, + rower.user.first_name + ) else: res = queuehigh.enqueue(handle_sendemail_unrecognized, fcopy, rower.user.email) - + res = queuehigh.enqueue(handle_sendemail_unrecognizedowner, + rower.user.email, + rower.user.first_name + ) return 0 summary = '' diff --git a/rowers/tasks.py b/rowers/tasks.py index 743e6af8..bea8eddf 100644 --- a/rowers/tasks.py +++ b/rowers/tasks.py @@ -1,4 +1,4 @@ -from celery import Celery,app +""" Background tasks done by Celery (develop) or QR (production) """ import os import time import gc @@ -7,67 +7,73 @@ import shutil import numpy as np import rowingdata -from rowingdata import main as rmain + from rowingdata import rowingdata as rdata -import rowingdata -from async_messages import message_user,messages + +from celery import app from matplotlib.backends.backend_agg import FigureCanvas #from matplotlib.backends.backend_cairo import FigureCanvasCairo as FigureCanvas import matplotlib.pyplot as plt -from matplotlib import figure -import stravalib + + import pandas as pd from django_rq import job -from utils import serialize_list,deserialize_list +from utils import deserialize_list from rowers.dataprepnodjango import ( update_strokedata, new_workout_from_file, - getsmallrowdata_db,read_df_sql,columndict, -) + getsmallrowdata_db, +) -from django.core.mail import send_mail, BadHeaderError,EmailMessage +from django.core.mail import send_mail, EmailMessage import datautils import utils # testing task + + @app.task def add(x, y): return x + y # create workout + + @app.task -def handle_new_workout_from_file(r,f2, - workouttype='rower', - title='Workout', - makeprivate=False, - notes=''): - return new_workout_from_file(r,f2,workouttype, - title,makeprivate,notes) +def handle_new_workout_from_file(r, f2, + workouttype='rower', + title='Workout', + makeprivate=False, + notes=''): + return new_workout_from_file(r, f2, workouttype, + title, makeprivate, notes) # process and update workouts + + @app.task -def handle_updatedps(useremail,workoutids,debug=False): - for wid,f1 in workoutids: +def handle_updatedps(useremail, workoutids, debug=False): + for wid, f1 in workoutids: havedata = 1 try: rowdata = rdata(f1) except IOError: try: - rowdata = rdata(f1+'.csv') + rowdata = rdata(f1 + '.csv') except IOError: try: - rowdata = rdata(f1+'.gz') + rowdata = rdata(f1 + '.gz') except IOError: havedata = 0 if havedata: - update_strokedata(wid,rowdata.df,debug=debug) + update_strokedata(wid, rowdata.df, debug=debug) subject = "Rowsandall.com Your Distance per Stroke metric has been updated" message = "All your workouts now have Distance per Stroke" @@ -77,18 +83,20 @@ def handle_updatedps(useremail,workoutids,debug=False): [useremail]) res = email.send() - + return 1 # send email when a breakthrough workout is uploaded + + @app.task -def handle_sendemail_breakthrough(workoutid,useremail, - userfirstname,userlastname, - btvalues = pd.DataFrame().to_json()): +def handle_sendemail_breakthrough(workoutid, useremail, + userfirstname, userlastname, + btvalues=pd.DataFrame().to_json()): # send email with attachment subject = "A breakthrough workout on rowsandall.com" - message = "Dear "+userfirstname+",\n" + message = "Dear " + userfirstname + ",\n" message += "Congratulations! Your recent workout has been analyzed" message += " by Rowsandall.com and it appears your fitness," message += " as measured by Critical Power, has improved!" @@ -98,17 +106,17 @@ def handle_sendemail_breakthrough(workoutid,useremail, message += " http://analytics.rowsandall.com/2017/06/17/how-do-we-calculate-critical-power/ \n\n" message += "Link to the workout http://rowsandall.com/rowers/workout/" message += str(workoutid) - message +="/edit\n\n" - message +="To add the workout to your Ranking workouts and see the updated CP plot, click the following link:\n" + message += "/edit\n\n" + message += "To add the workout to your Ranking workouts and see the updated CP plot, click the following link:\n" message += "http://rowsandall.com/rowers/workout/" message += str(workoutid) message += "/updatecp\n\n" btvalues = pd.read_json(btvalues) - btvalues.sort_values('delta',axis=0,inplace=True) - + btvalues.sort_values('delta', axis=0, inplace=True) + if not btvalues.empty: - message += "These were the breakthrough values:\n" + message += "These were the breakthrough values:\n" for t in btvalues.itertuples(): delta = t.delta cpvalue = t.cpvalues @@ -116,23 +124,21 @@ def handle_sendemail_breakthrough(workoutid,useremail, message += "Time: {delta} seconds\n".format( delta=delta - ) + ) message += "New: {cpvalue:.0f} Watt\n".format( cpvalue=cpvalue - ) + ) message += "Old: {pwr:.0f} Watt\n\n".format( pwr=pwr - ) + ) - message += "To opt out of these email notifications, deselect the checkbox on your Profile page under Account Information.\n\n" message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [useremail]) - + 'Rowsandall ', + [useremail]) res = email.send() @@ -140,14 +146,16 @@ def handle_sendemail_breakthrough(workoutid,useremail, return 1 # send email when a breakthrough workout is uploaded + + @app.task -def handle_sendemail_hard(workoutid,useremail, - userfirstname,userlastname, - btvalues = pd.DataFrame().to_json()): +def handle_sendemail_hard(workoutid, useremail, + userfirstname, userlastname, + btvalues=pd.DataFrame().to_json()): # send email with attachment subject = "That was a pretty hard workout on rowsandall.com" - message = "Dear "+userfirstname+",\n" + message = "Dear " + userfirstname + ",\n" message += "Congratulations! Your recent workout has been analyzed" message += " by Rowsandall.com and it appears that it was pretty hard work." message += " You were working pretty close to your Critical Power\n\n" @@ -157,16 +165,15 @@ def handle_sendemail_hard(workoutid,useremail, message += " http://analytics.rowsandall.com/2017/06/17/how-do-we-calculate-critical-power/ \n\n" message += "Link to the workout http://rowsandall.com/rowers/workout/" message += str(workoutid) - message +="/edit\n\n" + message += "/edit\n\n" message += "To opt out of these email notifications, deselect the checkbox on your Profile page under Account Information.\n\n" message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [useremail]) - + 'Rowsandall ', + [useremail]) res = email.send() @@ -176,25 +183,25 @@ def handle_sendemail_hard(workoutid,useremail, # send email to me when an unrecognized file is uploaded @app.task -def handle_sendemail_unrecognized(unrecognizedfile,useremail): +def handle_sendemail_unrecognized(unrecognizedfile, useremail): # send email with attachment fullemail = 'roosendaalsander@gmail.com' subject = "Unrecognized file from Rowsandall.com" message = "Dear Sander,\n\n" message += "Please find attached a file that someone tried to upload to rowsandall.com. The file was not recognized as a valid file type.\n\n" - message += "User Email "+useremail+"\n\n" + message += "User Email " + useremail + "\n\n" message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) + try: email.attach_file(unrecognizedfile) except IOError: pass - + res = email.send() # remove tcx file @@ -202,38 +209,69 @@ def handle_sendemail_unrecognized(unrecognizedfile,useremail): os.remove(unrecognizedfile) except: pass - + return 1 - + +# send email to owner when an unrecognized file is uploaded +@app.task +def handle_sendemail_unrecognizedowner(useremail, userfirstname): + + # send email with attachment + fullemail = useremail + subject = "Unrecognized file from Rowsandall.com" + message = "Dear " + userfirstname + ",\n\n" + message += """ + The file you tried to send to rowsandall.com was not recognized by + our email processing system. You may have sent a file in a format + that is not supported. Sometimes, rowing apps make file format changes. + When that happens, it takes some time for rowsandall.comm to make + the necessary changes on our side and support the app again. + + The file has been sent to the developer at rowsandall.com for evaluation. + + + """ + + message += "Best Regards, the Rowsandall Team" + + email = EmailMessage(subject, message, + 'Rowsandall ', + [fullemail]) + + res = email.send() + + return 1 + + # Send email with TCX attachment @app.task -def handle_sendemailtcx(first_name,last_name,email,tcxfile): +def handle_sendemailtcx(first_name, last_name, email, tcxfile): # send email with attachment fullemail = first_name + " " + last_name + " " + "<" + email + ">" subject = "File from Rowsandall.com" - message = "Dear "+first_name+",\n\n" + message = "Dear " + first_name + ",\n\n" message += "Please find attached the requested file for your workout.\n\n" message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) email.attach_file(tcxfile) - + res = email.send() # remove tcx file os.remove(tcxfile) return 1 + @app.task -def handle_zip_file(emailfrom,subject,file): +def handle_zip_file(emailfrom, subject, file): message = "... zip processing ... " - email = EmailMessage(subject,message, + email = EmailMessage(subject, message, emailfrom, ['workouts@rowsandall.com']) email.attach_file(file) @@ -242,64 +280,68 @@ def handle_zip_file(emailfrom,subject,file): return 1 # Send email with CSV attachment + + @app.task -def handle_sendemailcsv(first_name,last_name,email,csvfile): +def handle_sendemailcsv(first_name, last_name, email, csvfile): # send email with attachment fullemail = first_name + " " + last_name + " " + "<" + email + ">" subject = "File from Rowsandall.com" - message = "Dear "+first_name+",\n\n" + message = "Dear " + first_name + ",\n\n" message += "Please find attached the requested file for your workout.\n\n" message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) if os.path.isfile(csvfile): email.attach_file(csvfile) else: csvfile2 = csvfile - with gzip.open(csvfile+'.gz','rb') as f_in, open(csvfile2,'wb') as f_out: + with gzip.open(csvfile + '.gz', 'rb') as f_in, open(csvfile2, 'wb') as f_out: shutil.copyfileobj(f_in, f_out) - + email.attach_file(csvfile2) os.remove(csvfile2) - + res = email.send() return 1 # Calculate wind and stream corrections for OTW rowing + + @app.task -def handle_otwsetpower(f1,boattype,weightvalue, - first_name,last_name,email,workoutid,ps=[1,1,1,1], +def handle_otwsetpower(f1, boattype, weightvalue, + first_name, last_name, email, workoutid, ps=[ + 1, 1, 1, 1], ratio=1.0, debug=False): try: rowdata = rdata(f1) except IOError: try: - rowdata = rdata(f1+'.csv') + rowdata = rdata(f1 + '.csv') except IOError: - rowdata = rdata(f1+'.gz') - + rowdata = rdata(f1 + '.gz') + weightvalue = float(weightvalue) # do something with boat type boatfile = { - '1x':'static/rigging/1x.txt', - '2x':'static/rigging/2x.txt', - '2-':'static/rigging/2-.txt', - '4x':'static/rigging/4x.txt', - '4-':'static/rigging/4-.txt', - '8+':'static/rigging/8+.txt', - } + '1x': 'static/rigging/1x.txt', + '2x': 'static/rigging/2x.txt', + '2-': 'static/rigging/2-.txt', + '4x': 'static/rigging/4x.txt', + '4-': 'static/rigging/4-.txt', + '8+': 'static/rigging/8+.txt', + } try: - rg = rowingdata.getrigging(boatfile[boattype]) + rg = rowingdata.getrigging(boatfile[boattype]) except KeyError: - rg = rowingdata.getrigging('static/rigging/1x.txt') + rg = rowingdata.getrigging('static/rigging/1x.txt') # do calculation, but do not overwrite NK Empower Power data powermeasured = False @@ -310,117 +352,119 @@ def handle_otwsetpower(f1,boattype,weightvalue, except KeyError: pass - rowdata.otw_setpower_silent(skiprows=5,mc=weightvalue,rg=rg, + rowdata.otw_setpower_silent(skiprows=5, mc=weightvalue, rg=rg, powermeasured=powermeasured) # save data - rowdata.write_csv(f1,gzip=True) - update_strokedata(workoutid,rowdata.df,debug=debug) + rowdata.write_csv(f1, gzip=True) + update_strokedata(workoutid, rowdata.df, debug=debug) - totaltime = rowdata.df['TimeStamp (sec)'].max()-rowdata.df['TimeStamp (sec)'].min() + totaltime = rowdata.df['TimeStamp (sec)'].max( + ) - rowdata.df['TimeStamp (sec)'].min() try: - totaltime = totaltime+rowdata.df.ix[0,' ElapsedTime (sec)'] + totaltime = totaltime + rowdata.df.ix[0, ' ElapsedTime (sec)'] except KeyError: pass - df = getsmallrowdata_db(['power','workoutid','time'],ids=[workoutid]) + df = getsmallrowdata_db(['power', 'workoutid', 'time'], ids=[workoutid]) thesecs = totaltime - maxt = 1.05*thesecs + maxt = 1.05 * thesecs logarr = datautils.getlogarr(maxt) dfgrouped = df.groupby(['workoutid']) - delta,cpvalues,avgpower = datautils.getcp(dfgrouped,logarr) - - + delta, cpvalues, avgpower = datautils.getcp(dfgrouped, logarr) + #delta,cpvalues,avgpower = datautils.getsinglecp(rowdata.df) - res,btvalues,res2 = utils.isbreakthrough(delta,cpvalues,ps[0],ps[1],ps[2],ps[3],ratio) + res, btvalues, res2 = utils.isbreakthrough( + delta, cpvalues, ps[0], ps[1], ps[2], ps[3], ratio) if res: - handle_sendemail_breakthrough(workoutid,email, + handle_sendemail_breakthrough(workoutid, email, first_name, - last_name,btvalues=btvalues.to_json()) + last_name, btvalues=btvalues.to_json()) # send email fullemail = first_name + " " + last_name + " " + "<" + email + ">" subject = "Your Rowsandall OTW calculations are ready" - message = "Dear "+first_name+",\n\n" + message = "Dear " + first_name + ",\n\n" message += "Your Rowsandall OTW calculations are ready.\n" message += "Thank you for using rowsandall.com.\n\n" message += "Rowsandall OTW calculations have not been fully implemented yet.\n" message += "We are now running an experimental version for debugging purposes. \n" message += "Your wind/stream corrected plot is available here: http://rowsandall.com/rowers/workout/" message += str(workoutid) - message +="/interactiveotwplot\n\n" + message += "/interactiveotwplot\n\n" message += "Please report any bugs/inconsistencies/unexpected results at rowsandall.slack.com or by reply to this email.\n\n" message += "Best Regards, The Rowsandall Physics Department." send_mail(subject, message, - 'Rowsandall Physics Department ', - [fullemail]) + 'Rowsandall Physics Department ', + [fullemail]) return 1 # This function generates all the static (PNG image) plots -@app.task -def handle_makeplot(f1,f2,t,hrdata,plotnr,imagename): - hrmax = hrdata['hrmax'] - hrut2 = hrdata['hrut2'] - hrut1 = hrdata['hrut1'] - hrat = hrdata['hrat'] - hrtr = hrdata['hrtr'] - hran = hrdata['hran'] + +@app.task +def handle_makeplot(f1, f2, t, hrdata, plotnr, imagename): + + hrmax = hrdata['hrmax'] + hrut2 = hrdata['hrut2'] + hrut1 = hrdata['hrut1'] + hrat = hrdata['hrat'] + hrtr = hrdata['hrtr'] + hran = hrdata['hran'] ftp = hrdata['ftp'] powerzones = deserialize_list(hrdata['powerzones']) powerperc = np.array(deserialize_list(hrdata['powerperc'])).astype(int) - - rr = rowingdata.rower(hrmax=hrmax,hrut2=hrut2, - hrut1=hrut1,hrat=hrat, - hrtr=hrtr,hran=hran, - ftp=ftp,powerperc=powerperc, + + rr = rowingdata.rower(hrmax=hrmax, hrut2=hrut2, + hrut1=hrut1, hrat=hrat, + hrtr=hrtr, hran=hran, + ftp=ftp, powerperc=powerperc, powerzones=powerzones) try: - row = rdata(f2,rower=rr) + row = rdata(f2, rower=rr) except IOError: - row = rdata(f2+'.gz',rower=rr) - + row = rdata(f2 + '.gz', rower=rr) haspower = row.df[' Power (watts)'].mean() > 50 - + nr_rows = len(row.df) - if (plotnr in [1,2,4,5,8,11,9,12]) and (nr_rows > 1200): - bin = int(nr_rows/1200.) - df = row.df.groupby(lambda x:x/bin).mean() - row.df = df + if (plotnr in [1, 2, 4, 5, 8, 11, 9, 12]) and (nr_rows > 1200): + bin = int(nr_rows / 1200.) + df = row.df.groupby(lambda x: x / bin).mean() + row.df = df nr_rows = len(row.df) - if (plotnr==1): - fig1 = row.get_timeplot_erg(t) - elif (plotnr==2): - fig1 = row.get_metersplot_erg(t) - elif (plotnr==3): - fig1 = row.get_piechart(t) - elif (plotnr==4): + if (plotnr == 1): + fig1 = row.get_timeplot_erg(t) + elif (plotnr == 2): + fig1 = row.get_metersplot_erg(t) + elif (plotnr == 3): + fig1 = row.get_piechart(t) + elif (plotnr == 4): if haspower: fig1 = row.get_timeplot_otwempower(t) else: - fig1 = row.get_timeplot_otw(t) - elif (plotnr==5): + fig1 = row.get_timeplot_otw(t) + elif (plotnr == 5): if haspower: fig1 = row.get_metersplot_otwempower(t) else: - fig1 = row.get_metersplot_otw(t) - elif (plotnr==6): - fig1 = row.get_piechart(t) - elif (plotnr==7) or (plotnr==10): - fig1 = row.get_metersplot_erg2(t) - elif (plotnr==8) or (plotnr==11): - fig1 = row.get_timeplot_erg2(t) - elif (plotnr==9) or (plotnr==12): - fig1 = row.get_time_otwpower(t) - elif (plotnr==13) or (plotnr==16): - fig1 = row.get_power_piechart(t) + fig1 = row.get_metersplot_otw(t) + elif (plotnr == 6): + fig1 = row.get_piechart(t) + elif (plotnr == 7) or (plotnr == 10): + fig1 = row.get_metersplot_erg2(t) + elif (plotnr == 8) or (plotnr == 11): + fig1 = row.get_timeplot_erg2(t) + elif (plotnr == 9) or (plotnr == 12): + fig1 = row.get_time_otwpower(t) + elif (plotnr == 13) or (plotnr == 16): + fig1 = row.get_power_piechart(t) canvas = FigureCanvas(fig1) # plt.savefig('static/plots/'+imagename,format='png') - canvas.print_figure('static/plots/'+imagename) + canvas.print_figure('static/plots/' + imagename) # plt.imsave(fname='static/plots/'+imagename) plt.close(fig1) fig1.clf() @@ -430,12 +474,13 @@ def handle_makeplot(f1,f2,t,hrdata,plotnr,imagename): # Team related remote tasks + @app.task -def handle_sendemail_invite(email,name,code,teamname,manager): - fullemail = name+' <'+email+'>' - subject = 'Invitation to join team '+teamname - message = 'Dear '+name+',\n\n' - message += manager+' is inviting you to join his team '+teamname +def handle_sendemail_invite(email, name, code, teamname, manager): + fullemail = name + ' <' + email + '>' + subject = 'Invitation to join team ' + teamname + message = 'Dear ' + name + ',\n\n' + message += manager + ' is inviting you to join his team ' + teamname message += ' on rowsandall.com\n\n' message += 'By accepting the invite, you will have access to your' message += " team's workouts on rowsandall.com and your workouts will " @@ -444,117 +489,119 @@ def handle_sendemail_invite(email,name,code,teamname,manager): message += 'If you already have an account on rowsandall.com, you can login to the site and you will find the invitation here on the Teams page:\n' message += ' https://rowsandall.com/rowers/me/teams \n\n' message += 'You can also click the direct link: \n' - message += 'https://rowsandall.com/rowers/me/invitation/'+code+' \n\n' + message += 'https://rowsandall.com/rowers/me/invitation/' + code + ' \n\n' message += 'If you are not yet registered to rowsandall.com, ' message += 'you can register for free at https://rowsandall.com/rowers/register\n' message += 'After you set up your account, you can use the direct link: ' - message += 'https://rowsandall.com/rowers/me/invitation/'+code+' \n\n' + message += 'https://rowsandall.com/rowers/me/invitation/' + code + ' \n\n' message += 'You can also manually accept your team membership with the code.\n' message += 'You will need to do this if you registered under a different email address than this one.\n' - message += 'Code: '+code+'\n' + message += 'Code: ' + code + '\n' message += 'Link to manually accept your team membership: ' message += 'https://rowsandall.com/rowers/me/invitation\n\n' message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemailnewresponse(first_name,last_name, +def handle_sendemailnewresponse(first_name, last_name, email, commenter_first_name, commenter_last_name, comment, - workoutname,workoutid,commentid): - fullemail = first_name+' '+last_name+' <'+email+'>' - subject = 'New comment on workout '+workoutname - message = 'Dear '+first_name+',\n\n' - message += commenter_first_name+' '+commenter_last_name + workoutname, workoutid, commentid): + fullemail = first_name + ' ' + last_name + ' <' + email + '>' + subject = 'New comment on workout ' + workoutname + message = 'Dear ' + first_name + ',\n\n' + message += commenter_first_name + ' ' + commenter_last_name message += ' has written a new comment on the workout ' - message += workoutname+'\n\n' + message += workoutname + '\n\n' message += comment message += '\n\n' message += 'You can read the comment here:\n' - message += 'https://rowsandall.com/rowers/workout/'+str(workoutid)+'/comment' + message += 'https://rowsandall.com/rowers/workout/' + \ + str(workoutid) + '/comment' message += '\n\n' message += 'You are receiving this email because you are subscribed ' message += 'to comments on this workout. To unsubscribe, follow this link:\n' - message += 'https://rowsandall.com/rowers/workout/'+str(workoutid)+'/unsubscribe' + message += 'https://rowsandall.com/rowers/workout/' + \ + str(workoutid) + '/unsubscribe' email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 - + + @app.task def handle_sendemailnewcomment(first_name, - last_name, - email, + last_name, + email, commenter_first_name, commenter_last_name, - comment,workoutname, + comment, workoutname, workoutid): - fullemail = first_name+' '+last_name+' <'+email+'>' - subject = 'New comment on workout '+workoutname - message = 'Dear '+first_name+',\n\n' - message += commenter_first_name+' '+commenter_last_name + fullemail = first_name + ' ' + last_name + ' <' + email + '>' + subject = 'New comment on workout ' + workoutname + message = 'Dear ' + first_name + ',\n\n' + message += commenter_first_name + ' ' + commenter_last_name message += ' has written a new comment on your workout ' - message += workoutname+'\n\n' + message += workoutname + '\n\n' message += comment message += '\n\n' message += 'You can read the comment here:\n' - message += 'https://rowsandall.com/rowers/workout/'+str(workoutid)+'/comment' + message += 'https://rowsandall.com/rowers/workout/' + \ + str(workoutid) + '/comment' email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 - + @app.task -def handle_sendemail_request(email,name,code,teamname,requestor,id): - fullemail = name+' <'+email+'>' - subject = 'Request to join team '+teamname - message = 'Dear '+name+',\n\n' - message += requestor+' is requesting admission to your team '+teamname +def handle_sendemail_request(email, name, code, teamname, requestor, id): + fullemail = name + ' <' + email + '>' + subject = 'Request to join team ' + teamname + message = 'Dear ' + name + ',\n\n' + message += requestor + ' is requesting admission to your team ' + teamname message += ' on rowsandall.com\n\n' message += 'Click the direct link to accept: \n' - message += 'https://rowsandall.com/rowers/me/request/'+code+' \n\n' + message += 'https://rowsandall.com/rowers/me/request/' + code + ' \n\n' message += 'Click the following link to reject the request: \n' - message += 'https://rowsandall.com/rowers/me/request/'+str(id)+' \n\n' + message += 'https://rowsandall.com/rowers/me/request/' + str(id) + ' \n\n' message += 'You can find all pending requests on your team management page:\n' message += 'https://rowsandall.com/rowers/me/teams\n\n' message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemail_request_accept(email,name,teamname,managername): - fullemail = name+' <'+email+'>' - subject = 'Welcome to '+teamname - message = 'Dear '+name+',\n\n' +def handle_sendemail_request_accept(email, name, teamname, managername): + fullemail = name + ' <' + email + '>' + subject = 'Welcome to ' + teamname + message = 'Dear ' + name + ',\n\n' message += managername message += ' has accepted your request to be part of the team ' message += teamname @@ -562,19 +609,19 @@ def handle_sendemail_request_accept(email,name,teamname,managername): message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemail_request_reject(email,name,teamname,managername): - fullemail = name+' <'+email+'>' - subject = 'Your application to '+teamname+' was rejected' - message = 'Dear '+name+',\n\n' +def handle_sendemail_request_reject(email, name, teamname, managername): + fullemail = name + ' <' + email + '>' + subject = 'Your application to ' + teamname + ' was rejected' + message = 'Dear ' + name + ',\n\n' message += 'Unfortunately, ' message += managername message += ' has rejected your request to be part of the team ' @@ -583,19 +630,19 @@ def handle_sendemail_request_reject(email,name,teamname,managername): message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemail_member_dropped(email,name,teamname,managername): - fullemail = name+' <'+email+'>' - subject = 'You were removed from '+teamname - message = 'Dear '+name+',\n\n' +def handle_sendemail_member_dropped(email, name, teamname, managername): + fullemail = name + ' <' + email + '>' + subject = 'You were removed from ' + teamname + message = 'Dear ' + name + ',\n\n' message += 'Unfortunately, ' message += managername message += ' has removed you from the team ' @@ -604,42 +651,42 @@ def handle_sendemail_member_dropped(email,name,teamname,managername): message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemail_team_removed(email,name,teamname,managername): - fullemail = name+' <'+email+'>' - subject = 'Team '+teamname+' was deleted' - message = 'Dear '+name+',\n\n' +def handle_sendemail_team_removed(email, name, teamname, managername): + fullemail = name + ' <' + email + '>' + subject = 'Team ' + teamname + ' was deleted' + message = 'Dear ' + name + ',\n\n' message += managername message += ' has decided to delete the team ' message += teamname message += '\n\n' - message += 'The '+teamname+' tag has been removed from all your ' + message += 'The ' + teamname + ' tag has been removed from all your ' message += 'workouts on rowsandall.com.\n\n' message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemail_invite_reject(email,name,teamname,managername): - fullemail = managername+' <'+email+'>' - subject = 'Your invitation to '+name+' was rejected' - message = 'Dear '+managername+',\n\n' - message += 'Unfortunately, ' +def handle_sendemail_invite_reject(email, name, teamname, managername): + fullemail = managername + ' <' + email + '>' + subject = 'Your invitation to ' + name + ' was rejected' + message = 'Dear ' + managername + ',\n\n' + message += 'Unfortunately, ' message += name message += ' has rejected your invitation to be part of the team ' message += teamname @@ -647,33 +694,31 @@ def handle_sendemail_invite_reject(email,name,teamname,managername): message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 + @app.task -def handle_sendemail_invite_accept(email,name,teamname,managername): - fullemail = managername+' <'+email+'>' - subject = 'Your invitation to '+name+' was accepted' - message = 'Dear '+managername+',\n\n' - message += name+' has accepted your invitation to be part of the team '+teamname+'\n\n' +def handle_sendemail_invite_accept(email, name, teamname, managername): + fullemail = managername + ' <' + email + '>' + subject = 'Your invitation to ' + name + ' was accepted' + message = 'Dear ' + managername + ',\n\n' + message += name + ' has accepted your invitation to be part of the team ' + teamname + '\n\n' message += "Best Regards, the Rowsandall Team" email = EmailMessage(subject, message, - 'Rowsandall ', - [fullemail]) - + 'Rowsandall ', + [fullemail]) res = email.send() return 1 - # Another simple task for debugging purposes -def add2(x,y): - return x+y +def add2(x, y): + return x + y