def form_valid(self, form): from django.conf import settings from django.core.mail import send_mail from extinctionr.circles import get_circle outreach_circle = get_circle('outreach') address = self.request.META.get('HTTP_X_FORWARDED_FOR', self.request.META.get('REMOTE_ADDR', 'unknown address')) subject = '[XR] Website Contact from {}'.format(address) message = form.cleaned_data['message'] send_mail(subject, message, settings.DEFAULT_FROM_EMAIL, outreach_circle.get_notification_addresses()) messages.success(self.request, "Thanks for your feedback") return super().form_valid(form)
def action_to_ical_event(action): from icalendar import Event, vText, vCalAddress, vDatetime from pytz import timezone evt = Event() evt["uid"] = f"{action.id}@{base_url()}" evt.add("summary", action.html_title) evt["url"] = action.full_url outreach_circle = get_circle("outreach") if outreach_circle: organizer = vCalAddress(f"MAILTO:{outreach_circle.public_email}") organizer.params["cn"] = "Extinction Rebellion Boston" evt["organizer"] = organizer start = action.when # TODO: event listings don't have a duration so making one up. end = action.when + timedelta(hours=2) evt.add("dtstart", vDatetime(start)) evt.add("dtend", vDatetime(end)) evt.add("dtstamp", vDatetime(now())) # Attempt to put video conferencing information into the ics. # TODO: this doesn't work entirely but it doesn't hurt. Revisit # when we have more time and patience to work on it. if action.virtual: dlines = [ f"Join online: <a href=\"{action.location}\">{action.location}</a>\n", f"Event details: <a href=\"{action.full_url}\">{action.full_url}</a>\n", f"{action.description}\n", ICS_VIDEO_CONFERENCE_SEP, "Do not edit this section of the description.\n", "This event has a video call.", f"Join: {action.location}\n", f"View your event at {action.full_url}", ICS_VIDEO_CONFERENCE_SEP, ] evt["location"] = "Online event" else: dlines = [ f"Event details: {action.full_url}\n", f"{action.description}", ] evt["location"] = action.location description = "\n".join(dlines) evt.add("description", description) evt["last-modified"] = vDatetime(action.modified) evt["created"] = vDatetime(now()) return evt
def notify_new_volunteer(volunteer): contact = volunteer.contact outreach_circle = get_circle('outreach') subject = '[XR] New Volunteer Request: {}'.format(contact) message = '''{who} <{email}> has signed up to volunteer. View all new requests at: {baseurl}/admin/circles/volunteerrequest/?status__exact=n Edit this request at: {baseurl}/admin/circles/volunteerrequest/edit/{pk}/ '''.format(who=contact, email=contact.email, baseurl=base_url(), pk=volunteer.id) send_mail(subject, message, settings.DEFAULT_FROM_EMAIL, outreach_circle.get_notification_addresses())
def confirm_rsvp(action, attendee, ics_data): """ Send notification email to attendee when they register. Will not send notifications for actions which have already happened. Will not notify attendees twice. """ if now() > (action.when - timedelta(hours=2)): return if not _check_attendee_whitelist(attendee): return # Prevents getting a reminder too soon. attendee.notified = now() outreach = get_circle("outreach") if not outreach: logger.warning( "Outreach circle not found. App is misconfigured and will not send mail." ) return 0 from_email = settings.NOREPLY_FROM_EMAIL subject = "[XR Boston] RSVP confirmation for {}".format(action.text_title) msg_body_html = _render_action_email(action, attendee, outreach.public_email, "action_email_rsvp.html") msg_body_plain = _render_action_email(action, attendee, outreach.public_email, "action_email_rsvp.txt") msg = EmailMultiAlternatives(subject, msg_body_plain, from_email, [attendee.contact.email]) msg.attach_alternative(msg_body_html, "text/html") msg.attach(f"{action.slug}.ics", ics_data, "text/calendar") msg.send() attendee.save()
def send_action_reminder(action, attendees, reminder): engine = Engine.get_default() if reminder is EventReminder.NEXT_DAY: template_html = engine.get_template("action_email_reminder_day.html") template_plain = engine.get_template("action_email_reminder_day.txt") subject = "[XR Boston] Event reminder: {} is coming up".format( action.text_title) elif reminder is EventReminder.SOON: template_html = engine.get_template("action_email_reminder_soon.html") template_plain = engine.get_template("action_email_reminder_soon.txt") subject = "[XR Boston] Event reminder: {} is starting soon".format( action.text_title) else: raise ValueError("Unknown reminder type") from_email = settings.NOREPLY_FROM_EMAIL outreach = get_circle("outreach") if not outreach: logger.warning( "Outreach circle not found. App is misconfigured and will not send mail." ) return 0 notified = set() messages = [] # Can't use send_mass_mail because it doesn't work with html mail_connection = get_connection() time_now = now() for attendee in attendees: if attendee in notified: continue if not _check_attendee_whitelist(attendee): continue # If they got a reminder less than one day ago, skip this one. if attendee.notified and (time_now - attendee.notified) < timedelta(days=1): continue notified.add(attendee) msg_body_plain = _render_action_email(action, attendee, outreach.public_email, template_plain) msg_body_html = _render_action_email(action, attendee, outreach.public_email, template_html) msg = EmailMultiAlternatives(subject, msg_body_plain, from_email, [attendee.contact.email], connection=mail_connection) msg.attach_alternative(msg_body_html, "text/html") messages.append(msg) # Record when they were notified so that we don't do it again right away. attendee.notified = time_now for attendee in notified: attendee.save() mail_connection.send_messages(messages) return len(notified)