def addTask(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() if (authLib.checkAuthCode({ "username": username, "authCode": authCode }) != 1): return (0) if (dataDict["recurring"] not in [ "false", "daily", "weekly", "monthly", "quarterly", "yearly" ]): return (2) if (dataDict["recurring"] != "false" and authLib.checkIfPremium(username) != 1): return (3) createTime = str(time.time()) dataDict["createTime"] = createTime dueTime = dataDict["dueTime"] description = dataDict["description"].strip() done = "false" title = dataDict["title"].strip() tags = dataDict["tags"] hoursBefore = int(dataDict["hoursBefore"]) recurring = dataDict["recurring"] if (pushLib.checkPushSubscribed(username) == 1): pushable = dataDict["pushable"] else: pushable = "false" tagString = "" for tag in tags.split(","): if (tag == ""): continue tagString += tag.strip() + "," tagString = tagString[:-1] db = authLib.dbCon() c = db.cursor() command = "INSERT INTO tasks (username, createTime, dueTime, text, done, title, tags, pushScheduled, notificationHours, recurring) VALUES ( %s, %s, %s, %s, %s, %s, %s, %s, %s, %s)" c.execute(command, [ username, createTime, dueTime, description, done, title, tagString, pushable, hoursBefore, recurring ]) db.commit() db.close() db = authLib.dbCon() c = db.cursor() command = "SELECT id FROM tasks WHERE BINARY username = %s AND createTime = %s" c.execute(command, [username, createTime]) dataDict["id"] = c.fetchall()[0][0] if (pushable == "true" and pushLib.checkPushSubscribed(username) == 1): pushLib.schedulePush(dataDict) return (1)
def completePush(username, taskId): db = authLib.dbCon() c = db.cursor() command = "DELETE FROM duePushes WHERE username = %s AND taskId = %s" c.execute(command, [username, taskId]) db.commit() db.close() db = authLib.dbCon() c = db.cursor() command = "UPDATE tasks SET pushScheduled = %s WHERE BINARY username = %s AND id = %s" c.execute(command, ["false", username, taskId]) db.commit() db.close() return 0
def updatePushable(dataDict): username = dataDict["username"] taskId = dataDict["id"] pushable = "true" if (dataDict["pushable"] == "true"): pushable = "false" if (authLib.checkAuthCode(dataDict) != 1): return 0 if (pushLib.checkPushSubscribed(username) != 1): return 2 if (pushable == "true"): db = authLib.dbCon() c = db.cursor() command = "SELECT title, dueTime FROM tasks WHERE BINARY username = %s AND id = %s" c.execute(command, [username, taskId]) taskInfo = c.fetchall()[0] pushLib.schedulePush({ "username": username, "id": taskId, "title": taskInfo[0], "dueTime": taskInfo[1] }) return 1 else: pushLib.completePush(username, taskId) return 1
def doDuePushes(): # logFile = open("pushLog","a") db = authLib.dbCon() c = db.cursor() t = time.time() + 30.0 # logFile.write("Pushing tasks before " +str(t) + "\n") command = "SELECT * FROM duePushes WHERE pushTime < %s" c.execute(command, [ t, ]) duePushes = c.fetchall() if (len(duePushes) == 0): # logFile.write("No pushes found due before " + str(t) + "\n") # logFile.close() return 0 for duePush in duePushes: title = duePush[1] username = duePush[2] pushTime = float(duePush[3]) text = duePush[4] taskId = duePush[5] # logFile.write("Push due: " + title + " at " + str(pushTime) + " to " + username + "\n") returnCode = sendPush(username, title, text) if (returnCode == 0): # logFile.write("Failed to notifiy user " + username + " of task " + title + "\n") if (checkPushSubscribed(username) != 1): # logFile.write("Deleted task as user was not subscribed\n") completePush(username, taskId) else: completePush(username, taskId)
def sendPush(username, title, text): with open("pushKeys/private_key.pem", "r") as privKeyFile: privKey = privKeyFile.read().strip() db = authLib.dbCon() c = db.cursor() command = "SELECT subString FROM pushInfo WHERE BINARY username = %s" c.execute(command, [ username, ]) subs = c.fetchall() returnCode = 0 for sub in subs: subInfo = sub[0] aud = "https://" + subInfo.split("/")[2] claim = {"sub": "mailto:[email protected]", "aud": aud} data = text + ";" + text + ";" + "images/icon512-Rounded-Gray.png;" + title try: print( webpush(json.loads(subInfo), data, vapid_private_key=privKey, vapid_claims=claim)) updateSub(subInfo, "201") returnCode = 1 except: print("I'm sorry dave, I can't let you do that") updateSub(subInfo, "400") return (returnCode)
def completeTask(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() taskId = dataDict["id"] doneFlag = dataDict["done"] if (authLib.checkAuthCode({ "username": username, "authCode": authCode }) != 1): return (0) if (authLib.checkIfPremium(username) != 1): return (deleteTask(dataDict)) db = authLib.dbCon() c = db.cursor() recurring = getRecurring(taskId) if (recurring == 0): command = "UPDATE tasks SET done = %s, pushScheduled = 'false' WHERE BINARY username = %s AND id = %s" c.execute(command, [doneFlag, username, taskId]) else: recurringTime = recurring command = "UPDATE tasks SET dueTime = dueTime + %s, pushScheduled = 'false' WHERE BINARY username = %s AND id = %s" c.execute(command, [recurringTime, username, taskId]) db.commit() db.close() if (doneFlag == "true"): pushLib.completePush(username, taskId) return (1)
def getPushHours(taskId): db = authLib.dbCon() c = db.cursor() command = "SELECT notificationHours FROM tasks WHERE id = %s" c.execute(command, [ taskId, ]) pushHours = int(c.fetchall()[0][0]) return (pushHours)
def deleteSub(subString): db = authLib.dbCon() c = db.cursor() command = "DELETE FROM pushInfo WHERE BINARY subString = %s" c.execute(command, [ subString, ]) db.commit() db.close()
def getCustomers(): db = authLib.dbCon() c = db.cursor() command = "SELECT * FROM users WHERE premium = %s" c.execute(command, [ "true", ]) customers = c.fetchall() db.close() return (customers)
def deleteAllSubs(username): db = authLib.dbCon() c = db.cursor() command = "SELECT subString FROM pushInfo WHERE BINARY username = %s;" c.execute(command, [ username, ]) subs = c.fetchall() db.close() for sub in subs: subString = sub[0] deleteSub(subString) command = "UPDATE users SET sendPushes = %s WHERE BINARY username = %s" db = authLib.dbCon() c = db.cursor() c.execute(command, ["false", username]) db.commit() db.close() return (1)
def notifyUser(username, title, text): db = authLib.dbCon() c = db.cursor() command = "INSERT INTO tasks (username, createTime, dueTime, text, done, title, tags, pushScheduled, notificationHours, recurring) VALUES ( %s, %s, %s, %s, %s, %s, %s, %s, %s, %s)" c.execute(command, [ username, time.time(), 0, text, "false", title, "", "false", 2, "false" ]) db.commit() db.close() return (1)
def schedulePush(dataDict): username = dataDict["username"] title = dataDict["title"] text = "This task is due soon" dueTime = float(dataDict["dueTime"]) taskId = dataDict["id"] hoursBefore = getPushHours(taskId) pushTime = dueTime - hoursBefore * 60.0 * 60.0 completePush(username, taskId) db = authLib.dbCon() c = db.cursor() command = "INSERT INTO duePushes (title, username, pushTime, text, taskId) VALUES (%s, %s, %s, %s, %s)" c.execute(command, [title, username, pushTime, text, taskId]) db.commit() db.close() db = authLib.dbCon() c = db.cursor() command = "UPDATE tasks SET pushScheduled = %s WHERE BINARY username = %s AND id = %s" c.execute(command, ["true", username, taskId]) db.commit() db.close() return (1)
def getCustomerInfo(username): db = authLib.dbCon() c = db.cursor() command = "SELECT * FROM stripe WHERE BINARY username = %s" c.execute(command, [ username, ]) customerInfo = c.fetchall() if (len(customerInfo) == 0): return 0 customerInfo = customerInfo[0] db.close() return (customerInfo)
def checkPushSubscribed(username): db = authLib.dbCon() c = db.cursor() command = "SELECT * FROM pushInfo WHERE BINARY username = %s" c.execute(command, [ username, ]) subs = c.fetchall() if (len(subs) == 0): db.close() return 0 else: db.close() return 1
def deleteTask(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() taskId = dataDict["id"] if (authLib.checkAuthCode(dataDict) != 1): return (0) db = authLib.dbCon() c = db.cursor() command = "DELETE FROM tasks WHERE BINARY username = %s AND id = %s" c.execute(command, [username, taskId]) db.commit() db.close() pushLib.completePush(username, taskId) return (1)
def createCustomer(dataDict): username = dataDict["username"] if (authLib.checkAuthCode(dataDict) == 0): return (0) if (authLib.checkIfPremium(username) == 1): return (2) stripe.api_key = getKey() token = dataDict["token"] email = dataDict["email"] try: customer = stripe.Customer.create(description="New Customer", email=email, source=token) customerId = customer["id"] subscription = subscribeCustomer(customerId, username) except stripe.error.CardError as e: body = e.json_body err = body["error"] print(err) print("HTTP status is: " + str(e.http_status)) print("Type is: " + str(err["type"])) print("Code is: " + str(err["code"])) print("Message is: " + str(err["message"])) print("Param is: " + str(err["param"])) print("Attempting to delete unusable customer") try: customer.delete() print("Customer deleted successfully") except: print( "Customer delete failed, as customer creation failed earlier") return (err["message"]) except: return (4) db = authLib.dbCon() c = db.cursor() subId = subscription["id"] command = "INSERT INTO stripe (stripeId, email, username, subId) VALUES (%s, %s, %s, %s);" c.execute(command, [customerId, email, username, subId]) db.commit() db.close() authLib.upgradeToPremium(username) taskLib.notifyUser( username, "Thanks for Subscribing!", "Premium features like archive and push notifications are now available, look for them in the menu" ) return (1)
def editTask(dataDict): username = dataDict["username"] authCode = dataDict["authCode"] title = dataDict["title"].strip() dueTime = str(dataDict["dueTime"]) taskId = str(dataDict["id"]) text = dataDict["description"].strip() tags = dataDict["tags"] hoursBefore = int(dataDict["hoursBefore"]) recurring = dataDict["recurring"] if (pushLib.checkPushSubscribed(username)): pushable = dataDict["pushable"] else: pushable = "false" tagString = "" for tag in tags.split(","): if (tag == ""): continue tagString += tag.strip() + "," tagString = tagString[:-1] if (authLib.checkAuthCode({ "username": username, "authCode": authCode }) != 1): return (0) if (dataDict["recurring"] not in [ "false", "daily", "weekly", "monthly", "quarterly", "yearly" ]): return (2) if (dataDict["recurring"] != "false" and authLib.checkIfPremium(username) != 1): return (3) db = authLib.dbCon() c = db.cursor() command = "UPDATE tasks SET title = %s, text = %s, dueTime = %s, tags = %s, done = %s, pushScheduled = %s, notificationHours = %s, recurring = %s WHERE BINARY username = %s AND id = %s" c.execute(command, [ title, text, dueTime, tagString, "false", pushable, hoursBefore, recurring, username, taskId ]) db.commit() db.close() if (pushable == "true" and pushLib.checkPushSubscribed(username)): pushLib.schedulePush(dataDict) else: pushLib.completePush(username, taskId) return (1)
def addSub(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() if (authLib.checkAuthCode(dataDict) != 1): return (0) if (authLib.checkIfPremium(username) == 0): return (3) subInfo = dataDict["subInfo"] db = authLib.dbCon() c = db.cursor() command = "INSERT INTO pushInfo (username, subString, lastReturn) VALUES (%s, %s, %s);" c.execute(command, [username, subInfo, "201"]) command = "UPDATE users SET sendPushes = %s WHERE BINARY username = %s;" c.execute(command, ["true", username]) db.commit() db.close() return (1)
def updateSub(subString, returnCode): db = authLib.dbCon() c = db.cursor() command = "SELECT lastReturn FROM pushInfo WHERE BINARY subString = %s" c.execute(command, [ subString, ]) commandReturn = c.fetchall() lastReturn = commandReturn[0][0] if (lastReturn != "201" and lastReturn == returnCode): deleteSub(subString) return if (returnCode == "429"): #add to try-later list..... @FIXME add way of scheduling tasks for later return command = "UPDATE pushInfo SET lastReturn = %s WHERE BINARY subString = %s" c.execute(command, [returnCode, subString]) db.commit() db.close()
def deleteCustomer(username, stripeId, title, text): stripe.api_key = getKey() try: cu = stripe.Customer.retrieve(stripeId) cu.delete() db = authLib.dbCon() c = db.cursor() command = "DELETE FROM stripe WHERE BINARY username = %s" c.execute(command, [ username, ]) db.commit() db.close() authLib.downgradeFromPremium(username) pushLib.deleteAllSubs(username) taskLib.notifyUser(username, title, text) return (1) except: return (0)
def getTaskDates(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() sort = dataDict["sort"] month = int(dataDict["month"]) year = int(dataDict["year"]) auth = authLib.checkAuthCode(dataDict) if (auth != 1): return (0) db = authLib.dbCon() c = db.cursor() command = "SELECT dueTime FROM tasks WHERE BINARY username = %s AND BINARY done != %s" c.execute(command, [username, "true"]) tasks = c.fetchall() tasks = list(tasks) returnString = str(month) + ";" for task in tasks: dueTime = task[0] dueTimeString = time.strftime("%d/%m/%Y", time.gmtime(dueTime)) returnString += (dueTimeString + ",") db.close() returnString += ";" + str(year) return (returnString)
def getRecurring(taskId): db = authLib.dbCon() c = db.cursor() command = "SELECT recurring, dueTime FROM tasks WHERE id = %s" c.execute(command, [ taskId, ]) recurringString, dueTime = c.fetchall()[0] dueStruct = list(time.gmtime(dueTime)) if (recurringString == "false"): return (0) #daily if (recurringString == "daily"): dueStruct[2] += 1 #weekly if (recurringString == "weekly"): dueStruct[2] += 7 #monthly if (recurringString == "monthly"): dueStruct[1] += 1 #quarterly if (recurringString == "quarterly"): dueStruct[1] += 3 #yearly if (recurringString == "yearly"): dueStruct[0] += 1 #check days if (dueStruct[2] > 31): dueStruct[2] -= 31 dueStruct[1] += 1 #check months if (dueStruct[1] > 12): dueStruct[1] -= 12 dueStruct[0] += 1 dueTime = calendar.timegm(tuple(dueStruct)) - dueTime return (dueTime)
def getTagged(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() searchTag = dataDict["tag"].strip() sort = dataDict["sort"] auth = authLib.checkAuthCode(dataDict) timeOffset = float(dataDict["timeOffset"]) if (auth != 1): return (0) returnString = "" db = authLib.dbCon() c = db.cursor() command = "SELECT * FROM tasks WHERE BINARY username = %s AND BINARY done != %s" c.execute(command, [username, "true"]) tasks = c.fetchall() tasks = list(tasks) for task in tasks: for item in task: if (type(item) == StringType): item = item.decode("utf-8") if (len(tasks) == 0): return (2) if (sort == "default"): tasks.sort(key=lambda x: x[3]) infoString = "<div class='task' id='infoHeader' style='height:auto;width:auto;'><h2 class='taskTitle'>Tasks tagged with \"" + searchTag + "\" :</h2></div>" returnString += infoString for task in tasks: taskId = str(task[0]) username = task[1] createTime = float(task[2]) dueTime = float(task[3]) text = task[4] title = task[6] tags = task[7] pushable = task[8] recurring = task[10] if (recurring == "false"): recurringString = "" else: recurringString = " <i class='fa fa-repeat' aria-hidden='true'></i>(" + recurring.title( ) + ")" if ("'" in title): title = title.replace("'", "'") if ("'" in text): text = text.replace("'", "'") if (searchTag not in tags.split(",")): continue if (task[5] == "true"): continue timeString = time.strftime("%d/%m/%Y %H:%M", time.gmtime(dueTime - timeOffset)) dateSearchList = time.strftime( "%d/%m/%Y", time.gmtime(dueTime - float(timeOffset))).split("/") dateSearchList[1] = str(int(dateSearchList[1]) - 1) returnString += "<div class='task' id='" + taskId + "'><h2 class='taskTitle' onclick='openEdit(" + taskId + ");'>" + title + "</h2>" if (text != ""): returnString += "<div class='taskBody'>" + text + "</div>" else: returnString += "<div class='taskBody'><span class='italic'>No details</span></div>" returnString += "<div class='tagAndDueTimeWrapper'><div class='dueTime' onclick='dateSearch(" + dateSearchList[ 0] + "," + dateSearchList[1] + "," + dateSearchList[ 2] + ");'>" + timeString + recurringString returnString += "</div>" returnString += "<div class='taskTags'>" if (len(tags) < 1): returnString += "<span class='noTaskTag'><span class='italic'>No tags</span></span>" for tag in tags.split(","): if (tag == ""): continue returnString += "<span class='taskTag' onclick='getTagged(\"" + tag + "\");'>" + tag + "</span>" returnString += "</div></div>" if (pushable == "true"): returnString += "<button type='button' class='notificationToggle' onclick='updatePushable(" + taskId + ",\"true\");'><i class='fa fa-bell' aria-hidden='true'></i></button>" else: returnString += "<button type='button' class='notificationToggle' onclick='updatePushable(" + taskId + ",\"false\");'><i class='fa fa-bell-o' aria-hidden='true'></i></button>" returnString += "<button type='button' class='archiveButton' onclick='completeTaskPost(" + taskId + ");'><i class='fa fa-check-square-o' aria-hidden='true'></i></button>" returnString += "</div>" if (returnString == infoString): return (2) returnString += "<div class='task' id='infoFooter' style='height:auto;'><input type='button' id='archiveButton' onclick='getAll();' value='Go Back'></div>" return (returnString)
def getAll(dataDict): username = dataDict["username"].strip() authCode = dataDict["authCode"].strip() sort = dataDict["sort"] doneFlag = dataDict["archived"] timeOffset = dataDict["timeOffset"] if (doneFlag == "true" and authLib.checkIfPremium(username) == 0): return (3) if (doneFlag == "false"): buttonText = "<i class='fa fa-check-square-o' aria-hidden='true'></i>" buttonVal = "class='archiveButton'" onClick = "completeTaskPost" if (doneFlag == "true"): buttonText = "<i class='fa fa-reply' aria-hidden='true'></i>" buttonVal = "class='restoreButton'" onClick = "restoreTaskPost" auth = authLib.checkAuthCode(dataDict) if (auth != 1): return (0) returnString = "" db = authLib.dbCon() c = db.cursor() command = "SELECT * FROM tasks WHERE BINARY username = %s AND BINARY done = %s" c.execute(command, [username, doneFlag]) tasks = c.fetchall() tasks = list(tasks) if (len(tasks) == 0): return (2) if (sort == "default"): tasks.sort(key=lambda x: x[3]) if (sort == "createTime"): tasks.sort(key=lambda x: x[2], reverse=True) if (doneFlag == "true"): returnString += "<div class='task' style='height:auto;' id='infoHeader'><h2 style='margin:auto;'>Archived Tasks:</h2></div>" for task in tasks: # print(task) taskId = str(task[0]) username = task[1] createTime = float(task[2]) dueTime = float(task[3]) text = task[4] title = task[6] tags = task[7] pushable = task[8] recurring = task[10] if (recurring == "false"): recurringString = "" else: recurringString = " <i class='fa fa-repeat' aria-hidden='true'></i>(" + recurring.title( ) + ")" if ("'" in title): title = title.replace("'", "'") if ("'" in text): text = text.replace("'", "'") timeString = time.strftime("%d/%m/%Y %H:%M", time.gmtime(dueTime - float(timeOffset))) dateSearchList = time.strftime( "%d/%m/%Y", time.gmtime(dueTime - float(timeOffset))).split("/") dateSearchList[1] = str(int(dateSearchList[1]) - 1) returnString += "<div class='task' id='" + taskId + "'><h2 class='taskTitle' onclick='openEdit(" + taskId + ");'>" + title + "</h2>" if (text != ""): returnString += "<div class='taskBody'>" + text + "</div>" else: returnString += "<div class='taskBody'><span class='italic'>No details</span></div>" returnString += "<div class='tagAndDueTimeWrapper'><div class='dueTime' onclick='dateSearch(" + dateSearchList[ 0] + "," + dateSearchList[1] + "," + dateSearchList[ 2] + ");'>" + timeString + recurringString returnString += "</div>" returnString += "<div class='taskTags'>" if (len(tags) < 1): returnString += "<span class='noTaskTag'><span class='italic'>No tags</span></span>" for tag in tags.split(","): if (tag == ""): continue returnString += "<span class='taskTag' onclick='getTagged(\"" + tag + "\");'>" + tag + "</span>" returnString += "</div></div>" returnString += "<button type='button' " + buttonVal + " onclick='" + onClick + "(" + taskId + ");'>" + buttonText + "</button>" if (doneFlag == "true"): returnString += "<button type='button' class='deleteButton' onclick='deleteTask(" + taskId + ");'><i class='fa fa-times' aria-hidden='true'></i></button>" else: if (pushable == "true"): returnString += "<button type='button' class='notificationToggle' onclick='updatePushable(" + taskId + ",\"true\");'><i class='fa fa-bell' aria-hidden='true'></i></button>" else: returnString += "<button type='button' class='notificationToggle' onclick='updatePushable(" + taskId + ",\"false\");'><i class='fa fa-bell-o' aria-hidden='true'></i></button>" returnString += "</div>" if (doneFlag == "true"): returnString += "<div class='task' id='infoFooter' style='height:auto;'><input type='button' id='archiveButton' onclick='getAll();' value='Go Back'></div>" return (returnString)