def __call__(self): '''This script is to be run once every day and sends a reminder email to each and every student with a booking on the next day. So, if we run Monday, we should be sending for Wednesday's sessions.''' catalog = getToolByName(self.context, 'portal_catalog') #We want the date two days from now. target_date = DateTime().earliestTime()+2 days = catalog.unrestrictedSearchResults(path=self.context.getPath(), portal_type='Day', getDate=target_date) mail_counter = 0 mail_error_counter = 0 for day in days: the_day = day.getObject() for session in the_day.contentItems(): for person in session[1].contentItems(): try: mail.sendNotificationEmail(context=self.context, person=person[1], email_type=config.EHS_REMINDER_EMAIL) mail_counter += 1; except: mail_error_counter += 1; raise #Log how many emails were sent. self.context.plone_log("EHS Reminders Sent: We just spammed %s students and had %s errors when sending mail." % (mail_counter, mail_error_counter)) return
def cancelBooking(self): '''Processing that happens when a user is cancelling a given booking for a session.''' if self.request.form.get('form.submitted') == '1' and \ self.request.form.get('form.button.Submit') == \ 'Cancel selected session': self.authenticateForm() selectedSlots = self.request.get('selectedSlot', None) if type(selectedSlots) != list: selectedSlots = [selectedSlots] if selectedSlots != [None]: plone_utils = getToolByName(self.context, 'plone_utils') student_details = self.getStudentDetailsFromSdm() for slot in selectedSlots: try: booking_session = self.getBookingSessionByUid(slot) login_id = student_details['login_id'] person = booking_session[login_id] booking_session.manage_delObjects([login_id,]) try: #EMAIL: Send cancellation message to our user mail.sendNotificationEmail(context=self.context, person=person, email_type=config.EHS_CANCELLATION_EMAIL) notify(PersonCancelledEvent(person)) plone_utils.addPortalMessage(_(u'Your selected booking was cancelled successfully. You have been sent a confirmation email.'), 'info') except: raise plone_utils.addPortalMessage(_(u'Your selected booking was cancelled successfully but a confirmation email could not be sent.'), 'warning') self.has_cancelled = True except: raise plone_utils.addPortalMessage(_(u'Your booking could not be cancelled. Please contact Enrolment Help.'), 'error') view = ViewPageTemplateFile("show-bookings.pt") return view(self)
def handleSend(self, action): data, errors = self.extractData() if errors: self.status = self.formErrorsMessage return #Otherwise, if no errors on the form, then send our emails templating_errors = [] mail_counter = 0 for person in data['bookings']: for notification in data['notifications']: try: if action.value == 'Check Syntax': #Just do the templating, don't send mail mail.performTemplating(self.context, person, notification) else: #Actually send the mail and run the whole process mail.sendNotificationEmail( context=self.context, person=person, email_type=notification, log=True, ) mail_counter += 1 except mail.EmailTemplatingException as exception: messages = [] for err in exception.error: wrapped = err.getException()[1] #Some errors mightn't have line numbers. pretty_line_output = '' if hasattr(wrapped, 'lineno'): pretty_line_output = ', Line %d' % wrapped.lineno #Produce our nicely formatted template error output pretty_output = "%s error (%s%s): %s" % ( exception.type, notification, pretty_line_output, repr(wrapped), ) templating_errors += [pretty_output,] #Display the errors for the user to peruse if templating_errors: visual_error = Invalid('<br />\n'.join(templating_errors)) error = getMultiAdapter((visual_error, self.request, None, None, self, self.context), IErrorViewSnippet) error.render = lambda: util.render_html(error) error.update() self.widgets.errors += (error,) self.status = self.formErrorsMessage else: if action.value == 'Check Syntax': self.successMessage = u'No errors detected in templates!' else: self.successMessage = \ u'Successfully sent %d mail messages.' % \ mail_counter self.status = self.successMessage
def __call__(self, *args, **kwargs): #Recall our user's course selection from their session. plone_utils = getToolByName(self.context, 'plone_utils') self.student_details = self.getStudentDetailsFromSdm() self.booked_session_uid = None member = self.getAuthenticatedMember() #If a user hasn't selected a course yet, then get them to. #Administrators are special -- they don't get bumped. if self.student_details is None and not self.showEditLinks() and not self.isBookingStaff(): self.request.response.redirect(self.context.absolute_url()+'/@@select-course') return #When submitting our form, do the following for validation/processing if self.request.form.get('form.submitted') == '1' and \ self.request.form.get('form.button.Submit') == 'Submit Form': self.authenticateForm() #Validate our fields from the page for field in ExposedPersonSchema.fields(): field_validation = field.validate(self.request.form.get(field.getName()), self.context) if field_validation: self.errors[field.getName()] = field_validation #Special case for personal email address if "confirmPersonalEmail" not in self.errors and self.request.form.get('pers_email') != self.request.form.get('confirmPersonalEmail'): self.errors['confirmPersonalEmail'] = "Confirmation email address does not match. Please check your input." #Special case for advanced standing if self.request.form.get('intendToApplyForAdvancedStanding') is '1' and self.request.form.get('submittedApplicationForAdvancedStanding') is None: self.errors['submittedApplicationForAdvancedStanding'] = "This field is required." #Special checks for our slotSelection; it's not a real field timeSlotUid = self.request.form.get('slotSelection') timeSlotUid = isinstance(timeSlotUid, basestring) and [timeSlotUid,] or timeSlotUid timeSlot = None if not timeSlotUid or len(timeSlotUid) != 1: self.errors['slotSelection'] = "Please select one enrolment session to book into." else: timeSlot = self.getBookingSessionByUid(timeSlotUid[0]) existing = timeSlot.get(self.student_details['login_id']) #XXX Need more checks here to make sure the student #can sign up for the given slot... if not timeSlot \ or timeSlot.isClosed() \ or timeSlot.isFull() \ or timeSlot.isInThePast() \ or timeSlot.getFaculty() != self.student_details['faculty_code'] \ or self.context.isUserSignedUpForAnySlot(self.student_details): self.errors['slotSelection'] = "Your could not be signed up for your selected session. It may have been cancelled, closed or become full. Please select a different session." elif existing: self.errors['slotSelection'] = "You are already attending this enrolment session for %s. Please choose another session." % existing.crs_full_nm #If we don't have any errors, we're good. Otherwise, we just fall through to displaying the form. if len(self.errors) == 0: try: #need to add/merge request details with student details here #They might have changed phone/email/etc and we need their #responses included. self.student_details.update(self.request.form) person = timeSlot.invokeFactory('Person', self.student_details['login_id'], **self.student_details) try: #EMAIL: Send confirmation email to our user mail.sendNotificationEmail(context=self.context, person=timeSlot[person], email_type=config.EHS_CONFIRMATION_EMAIL) plone_utils.addPortalMessage(_(u'Your booking was processed successfully. Your selected session is highlighted below.'), 'success') except: raise plone_utils.addPortalMessage(_(u'Your booking was processed successfully but a confirmation email could not be sent.'), 'warning') self.booked_session_uid = timeSlot.UID() except: raise self.errors['slotSelection'] = "Your could not be signed up for your selected session. The session may have been cancelled or become full. Please select a different session." #We're just loading the form, not submitting else: #Copy selected exposed schema attributes into the request.form #object to inject them onto the page. if self.student_details is not None: for field_key in ExposedPersonSchema.keys(): self.request.form.setdefault(field_key, self.student_details.get(field_key)) #Data reconfiguration before our page loads if self.student_details is not None: self.faculty_code = self.student_details['faculty_code'] self.faculty_name = config.FACULTY_LIST.getValue(self.faculty_code) else: self.faculty_code = '' self.faculty_name = "Administrative overview (all sessions)" #Inject our friendly error message if there's errors on the page if self.errors: plone_utils.addPortalMessage(_(u'Please correct the indicated errors before attempting to book a session.'), 'error') #print self.request.form return super(ChooseTimeSlot,self).__call__(args, kwargs)