Coverage for app/controllers/admin/volunteers.py: 26%

150 statements  

« prev     ^ index     » next       coverage.py v7.2.7, created at 2024-03-01 16:17 +0000

1from flask import request, render_template, redirect, url_for, flash, abort, g, json, jsonify 

2from peewee import DoesNotExist, JOIN 

3from playhouse.shortcuts import model_to_dict 

4from app.controllers.admin import admin_bp 

5from app.models.event import Event 

6from app.models.program import Program 

7from app.models.user import User 

8from app.models.eventParticipant import EventParticipant 

9from app.models.emergencyContact import EmergencyContact 

10from app.logic.searchUsers import searchUsers 

11from app.logic.volunteers import updateEventParticipants, getEventLengthInHours, addUserBackgroundCheck, setProgramManager 

12from app.logic.participants import trainedParticipants, addPersonToEvent, getParticipationStatusForTrainings, sortParticipantsByStatus 

13from app.logic.events import getPreviousRecurringEventData, getEventRsvpCount 

14from app.models.eventRsvp import EventRsvp 

15from app.models.backgroundCheck import BackgroundCheck 

16from app.logic.createLogs import createAdminLog, createRsvpLog 

17from app.logic.users import getBannedUsers, isBannedFromEvent 

18 

19 

20@admin_bp.route('/searchVolunteers/<query>', methods = ['GET']) 

21def getVolunteers(query): 

22 '''Accepts user input and queries the database returning results that matches user search''' 

23 

24 return json.dumps(searchUsers(query)) 

25 

26@admin_bp.route('/event/<eventID>/manage_volunteers', methods=['GET', 'POST']) 

27def manageVolunteersPage(eventID): 

28 """ 

29 Controller that handles POST and GET requests regarding the Manage Volunteers page. 

30 

31 POST: updates the event participants for a particular event by calling  

32 updateEventParticipants on the form. 

33 

34 GET: retrieves all necessary participant lists and dictionaries and categorizes 

35 the participants/volunteers into their respective participation statuses. Then  

36 renders the manageVolunteers.html template. 

37 """ 

38 try: 

39 event = Event.get_by_id(eventID) 

40 except DoesNotExist as e: 

41 print(f"No event found for {eventID}", e) 

42 abort(404) 

43 

44 # ------------ POST request ------------ 

45 if request.method == "POST": 

46 volunteerUpdated = updateEventParticipants(request.form) 

47 

48 # error handling depending on the boolean returned from updateEventParticipants 

49 if volunteerUpdated: 

50 flash("Volunteer table succesfully updated", "success") 

51 else: 

52 flash("Error adding volunteer", "danger") 

53 return redirect(url_for("admin.manageVolunteersPage", eventID=eventID)) 

54 

55 # ------------ GET request ------------ 

56 elif request.method == "GET": 

57 if not (g.current_user.isCeltsAdmin or (g.current_user.isCeltsStudentStaff and g.current_user.isProgramManagerForEvent(event))): 

58 abort(403) 

59 

60 # ------- Grab the different lists of participants ------- 

61 trainedParticipantsForProgramAndTerm = trainedParticipants(event.program, event.term) 

62 

63 bannedUsersForProgram = [bannedUser.user for bannedUser in getBannedUsers(event.program)] 

64 

65 eventNonAttendedData, eventWaitlistData, eventVolunteerData, eventParticipants = sortParticipantsByStatus(event) 

66 

67 allRelevantUsers = [participant.user for participant in (eventParticipants + eventNonAttendedData + eventWaitlistData)] 

68 

69 # ----------- Get miscellaneous data ----------- 

70 

71 participationStatusForTrainings = getParticipationStatusForTrainings(event.program, allRelevantUsers, event.term) 

72 

73 eventLengthInHours = getEventLengthInHours(event.timeStart, event.timeEnd, event.startDate) 

74 

75 recurringVolunteers = getPreviousRecurringEventData(event.recurringId) 

76 

77 currentRsvpAmount = getEventRsvpCount(event.id) 

78 

79 # ----------- Render template with all of the data ------------ 

80 return render_template("/events/manageVolunteers.html", 

81 eventVolunteerData = eventVolunteerData, 

82 eventNonAttendedData = eventNonAttendedData, 

83 eventWaitlistData = eventWaitlistData, 

84 eventLength = eventLengthInHours, 

85 event = event, 

86 recurringVolunteers = recurringVolunteers, 

87 bannedUsersForProgram = bannedUsersForProgram, 

88 trainedParticipantsForProgramAndTerm = trainedParticipantsForProgramAndTerm, 

89 participationStatusForTrainings = participationStatusForTrainings, 

90 currentRsvpAmount = currentRsvpAmount) 

91 

92@admin_bp.route('/event/<eventID>/volunteer_details', methods=['GET']) 

93def volunteerDetailsPage(eventID): 

94 try: 

95 event = Event.get_by_id(eventID) 

96 except DoesNotExist as e: 

97 print(f"No event found for {eventID}", e) 

98 abort(404) 

99 

100 if not (g.current_user.isCeltsAdmin or (g.current_user.isCeltsStudentStaff and g.current_user.isProgramManagerForEvent(event))): 

101 abort(403) 

102 

103 eventRsvpData = list(EventRsvp.select(EmergencyContact, EventRsvp) 

104 .join(EmergencyContact, JOIN.LEFT_OUTER, on=(EmergencyContact.user==EventRsvp.user)) 

105 .where(EventRsvp.event==event)) 

106 eventParticipantData = list(EventParticipant.select(EmergencyContact, EventParticipant) 

107 .join(EmergencyContact, JOIN.LEFT_OUTER, on=(EmergencyContact.user==EventParticipant.user)) 

108 .where(EventParticipant.event==event)) 

109 

110 waitlistUser = list(set([obj for obj in eventRsvpData if obj.rsvpWaitlist])) 

111 rsvpUser = list(set([obj for obj in eventRsvpData if not obj.rsvpWaitlist ])) 

112 

113 return render_template("/events/volunteerDetails.html", 

114 waitlistUser = waitlistUser, 

115 attendedUser= eventParticipantData, 

116 rsvpUser= rsvpUser, 

117 event = event) 

118 

119 

120@admin_bp.route('/addVolunteersToEvent/<eventId>', methods = ['POST']) 

121def addVolunteer(eventId): 

122 event = Event.get_by_id(eventId) 

123 successfullyAddedVolunteer = False 

124 usernameList = [] 

125 usernameList = request.form.getlist("volunteer[]") 

126 

127 successfullyAddedVolunteer = False 

128 alreadyAddedList = [] 

129 addedSuccessfullyList = [] 

130 errorList = [] 

131 

132 for user in usernameList: 

133 userObj = User.get_by_id(user) 

134 successfullyAddedVolunteer = addPersonToEvent(userObj, event) 

135 if successfullyAddedVolunteer == "already in": 

136 alreadyAddedList.append(userObj.fullName) 

137 else: 

138 if successfullyAddedVolunteer: 

139 addedSuccessfullyList.append(userObj.fullName) 

140 else: 

141 errorList.append(userObj.fullName) 

142 

143 volunteers = "" 

144 if alreadyAddedList: 

145 volunteers = ", ".join(vol for vol in alreadyAddedList) 

146 flash(f"{volunteers} already in table.", "warning") 

147 

148 if addedSuccessfullyList: 

149 volunteers = ", ".join(vol for vol in addedSuccessfullyList) 

150 flash(f"{volunteers} added successfully.", "success") 

151 

152 if errorList: 

153 volunteers = ", ".join(vol for vol in errorList) 

154 flash(f"Error when adding {volunteers} to event.", "danger") 

155 

156 if 'ajax' in request.form and request.form['ajax']: 

157 return '' 

158 

159 return redirect(url_for('admin.manageVolunteersPage', eventID = eventId)) 

160 

161@admin_bp.route('/rsvpFromWaitlist/<username>/<eventId>', methods = ['POST']) 

162def rsvpFromWaitlist(username, eventId): 

163 event = Event.get_by_id(eventId) 

164 isProgramManager = g.current_user.isProgramManagerFor(event.program) 

165 if g.current_user.isCeltsAdmin or (g.current_user.isCeltsStudentStaff and isProgramManager): 

166 waitlistUsers = EventRsvp.select(EventRsvp, User).join(User).where(EventRsvp.user == username, EventRsvp.event==eventId).execute() 

167 if (waitlistUsers): 

168 createRsvpLog(event.id, f"Moved {waitlistUsers[0].user.fullName} from waitlist to RSVP.") 

169 (EventRsvp.update(rsvpWaitlist = False).where(EventRsvp.event_id == eventId, EventRsvp.user_id == username)).execute() 

170 return "" 

171 

172@admin_bp.route('/addVolunteersToEvent/<username>/<eventId>/isBanned', methods = ['GET']) 

173def isVolunteerBanned(username, eventId): 

174 return {"banned":1} if isBannedFromEvent(username, eventId) else {"banned":0} 

175 

176@admin_bp.route('/removeVolunteerFromEvent', methods = ['POST']) 

177def removeVolunteerFromEvent(): 

178 user = request.form.get('username') 

179 eventID = request.form.get('eventId') 

180 if g.current_user.isAdmin: 

181 userInRsvpTable = EventRsvp.select(EventRsvp, User).join(User).where(EventRsvp.user == user, EventRsvp.event==eventID).execute() 

182 if (userInRsvpTable): 

183 rsvpUser = userInRsvpTable[0] 

184 if rsvpUser.rsvpWaitlist: 

185 createRsvpLog(eventID, f"Removed {rsvpUser.user.fullName} from waitlist.") 

186 else: 

187 createRsvpLog(eventID, f"Removed {rsvpUser.user.fullName} from RSVP list.") 

188 (EventParticipant.delete().where(EventParticipant.user==user, EventParticipant.event==eventID)).execute() 

189 (EventRsvp.delete().where(EventRsvp.user==user, EventRsvp.event==eventID)).execute() 

190 flash("Volunteer successfully removed", "success") 

191 return "" 

192 

193@admin_bp.route('/addBackgroundCheck', methods = ['POST']) 

194def addBackgroundCheck(): 

195 if g.current_user.isCeltsAdmin: 

196 eventData = request.form 

197 user = eventData['user'] 

198 bgStatus = eventData['bgStatus'] 

199 type = eventData['bgType'] 

200 dateCompleted = eventData['bgDate'] 

201 addUserBackgroundCheck(user, type, bgStatus, dateCompleted) 

202 return " " 

203 

204@admin_bp.route('/deleteBackgroundCheck', methods = ['POST']) 

205def deleteBackgroundCheck(): 

206 if g.current_user.isCeltsAdmin: 

207 eventData = request.form 

208 bgToDelete = BackgroundCheck.get_by_id(eventData['bgID']) 

209 BackgroundCheck.delete().where(BackgroundCheck.id == bgToDelete).execute() 

210 return "" 

211 

212@admin_bp.route('/updateProgramManager', methods=["POST"]) 

213def updateProgramManager(): 

214 if g.current_user.isCeltsAdmin: 

215 data =request.form 

216 username = User.get(User.username == data["user_name"]) 

217 program = Program.get_by_id(data['program_id']) 

218 setProgramManager(data["user_name"], data["program_id"], data["action"]) 

219 createAdminLog(f'{username.firstName} has been {data["action"]}ed as a Program Manager for {program.programName}') 

220 return "" 

221 else: 

222 abort(403) 

223 

224@admin_bp.route("/updatePhone", methods=["POST"]) 

225def updatePhone(): 

226 newinfo=request.form 

227 User.update(phoneNumber=newinfo["phoneNumber"]).where(User.username==newinfo["username"]).execute() 

228 return ""