def send_validation_fail_email(self, name, emails, error): """Notify the user via email about the tryjob error.""" html_content = [] html_content.append('<html><body>') body = """ Your tryjob with name '%(name)s' failed the validation step. This is most likely because <br>you are running an older version of cbuildbot. Please run <br><code>repo sync chromiumos/chromite</code> and try again. If you still see<br>this message please contact [email protected].<br> """ html_content.append(body % {'name': name}) html_content.append("Extra error information:") html_content.append(error.replace('\n', '<br>\n')) html_content.append(self.email_footer) m = Message() m.set_payload('<br><br>'.join(html_content), 'utf8') m.set_type("text/html") m['Date'] = formatdate(localtime=True) m['Subject'] = 'Tryjob failed validation' m['From'] = self.from_addr m['Reply-To'] = self.reply_to result = defer.Deferred() sender_factory = SMTPSenderFactory(self.from_addr, emails, StringIO(m.as_string()), result) reactor.connectTCP(self.smtp_host, 25, sender_factory)
def _send_signup_ai_email(request, username, profile): """Send email to user who has signed up to site. """ info = {} info['system_name'] = get_setting(profile, 'system_name', 'OpenCore') info['system_email_domain'] = get_setting(profile, 'system_email_domain') info['from_name'] = '%s invitation' % info['system_name'] info['from_email'] = 'invitation@%s' % info['system_email_domain'] info['c_title'] = info['system_name'] info['c_description'] = "" info['c_href'] = request.api.app_url info['mfrom'] = '%s <%s>' % (info['from_name'], info['from_email']) info['subject'] = 'Thank you for joining the %s community' % info['system_name'] body_template = get_template('templates/email_accept_signup_invitation.pt') mailer = getUtility(IMailDelivery) msg = Message() msg['From'] = info['mfrom'] msg['To'] = profile.email msg['Subject'] = info['subject'] body = body_template( system_name=info['system_name'], system_href=info['c_href'], username=username, ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send(info['mfrom'], [profile.email,], msg)
def _send_aeu_emails(community, community_href, profiles, text): # To make reading the add_existing_user_view easier, move the mail # delivery part here. info = _get_common_email_info(community, community_href) subject_fmt = 'You have been added to the %s community' subject = subject_fmt % info['c_title'] body_template = get_renderer( 'templates/email_add_existing.pt').implementation() html_body = text mailer = getUtility(IMailDelivery) for profile in profiles: to_email = profile.email msg = Message() msg['From'] = info['mfrom'] msg['To'] = to_email msg['Subject'] = subject body = body_template( system_name=info['system_name'], community_href=info['c_href'], community_name=info['c_title'], community_description=info['c_description'], personal_message=html_body, ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send([ to_email, ], msg)
def _send_ai_email(community, community_href, username, profile): """Send email to user who has accepted a community invitation. """ info = _get_common_email_info(community, community_href) subject_fmt = 'Thank you for joining the %s community' subject = subject_fmt % info['c_title'] body_template = get_renderer( 'templates/email_accept_invitation.pt').implementation() mailer = getUtility(IMailDelivery) msg = Message() msg['From'] = info['mfrom'] msg['To'] = profile.email msg['Subject'] = subject body = body_template( community_href=info['c_href'], community_name=info['c_title'], community_description=info['c_description'], username=username, ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send([ profile.email, ], msg)
def _send_signup_email(request, invitation): site = find_site(request.context) mailer = getUtility(IMailDelivery) info = {} info['system_name'] = get_setting(site, 'system_name', 'OpenCore') info['system_email_domain'] = get_setting(site, 'system_email_domain') info['from_name'] = '%s invitation' % info['system_name'] info['from_email'] = 'invitation@%s' % info['system_email_domain'] info['c_title'] = info['system_name'] info['c_description'] = "" info['c_href'] = model_url(site, request) info['mfrom'] = '%s <%s>' % (info['from_name'], info['from_email']) info['subject'] = 'Please join the %s community' % info['system_name'] body_template = get_template('templates/email_signup.pt') msg = Message() msg['From'] = info['mfrom'] msg['To'] = invitation.email msg['Subject'] = info['subject'] body = body_template( system_name=info['system_name'], personal_message=invitation.message, invitation_url=model_url(site, request, 'signup', invitation.__name__) ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send(info['mfrom'], [invitation.email,], msg)
def request_password_reset(user, profile, request): profile.password_reset_key = sha1( str(random.random())).hexdigest() profile.password_reset_time = datetime.datetime.now() context = find_site(profile) reset_url = model_url( context, request, "reset_confirm.html", query=dict(key=profile.password_reset_key)) # send email mail = Message() system_name = get_setting(context, 'system_name', 'OpenCore') admin_email = get_setting(context, 'admin_email') mail["From"] = "%s Administrator <%s>" % (system_name, admin_email) mail["To"] = "%s <%s>" % (profile.title, profile.email) mail["Subject"] = "%s Password Reset Request" % system_name body = render_template( "templates/email_reset_password.pt", login=user['login'], reset_url=reset_url, system_name=system_name, ) if isinstance(body, unicode): body = body.encode("UTF-8") mail.set_payload(body, "UTF-8") mail.set_type("text/html") recipients = [profile.email] mailer = getUtility(IMailDelivery) mailer.send(admin_email, recipients, mail)
def _send_aeu_emails(community, community_href, profiles, text): # To make reading the add_existing_user_view easier, move the mail # delivery part here. info = _get_common_email_info(community, community_href) subject_fmt = 'You have been added to the %s community' subject = subject_fmt % info['c_title'] body_template = get_renderer( 'templates/email_add_existing.pt').implementation() html_body = text mailer = getUtility(IMailDelivery) for profile in profiles: to_email = profile.email msg = Message() msg['From'] = info['mfrom'] msg['To'] = to_email msg['Subject'] = subject body = body_template( system_name=info['system_name'], community_href=info['c_href'], community_name=info['c_title'], community_description=info['c_description'], personal_message=html_body, ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send([to_email,], msg)
def _send_ai_email(community, community_href, username, profile): """Send email to user who has accepted a community invitation. """ info = _get_common_email_info(community, community_href) subject_fmt = 'Thank you for joining the %s community' subject = subject_fmt % info['c_title'] body_template = get_renderer( 'templates/email_accept_invitation.pt').implementation() mailer = getUtility(IMailDelivery) msg = Message() msg['From'] = info['mfrom'] msg['To'] = profile.email msg['Subject'] = subject body = body_template( community_href=info['c_href'], community_name=info['c_title'], community_description=info['c_description'], username=username, ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send([profile.email,], msg)
def _send_invitation_email(request, community, community_href, invitation): mailer = getUtility(IMailDelivery) info = _get_common_email_info(community, community_href) subject_fmt = 'Please join the %s community at %s' info['subject'] = subject_fmt % (info['c_title'], info['system_name']) body_template = get_renderer( 'templates/email_invite_new.pt').implementation() msg = Message() msg['From'] = info['mfrom'] msg['To'] = invitation.email msg['Subject'] = info['subject'] body = body_template( system_name=info['system_name'], community_href=info['c_href'], community_name=info['c_title'], community_description=info['c_description'], personal_message=invitation.message, invitation_url=resource_url(invitation.__parent__, request, invitation.__name__) ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send([invitation.email,], msg)
def _send_invitation_email(request, community, community_href, invitation): mailer = getUtility(IMailDelivery) info = _get_common_email_info(community, community_href) subject_fmt = 'Please join the %s community at %s' info['subject'] = subject_fmt % (info['c_title'], info['system_name']) body_template = get_renderer( 'templates/email_invite_new.pt').implementation() msg = Message() msg['From'] = info['mfrom'] msg['To'] = invitation.email msg['Subject'] = info['subject'] body = body_template(system_name=info['system_name'], community_href=info['c_href'], community_name=info['c_title'], community_description=info['c_description'], personal_message=invitation.message, invitation_url=resource_url(invitation.__parent__, request, invitation.__name__)) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send([ invitation.email, ], msg)
def _send_moderators_changed_email(community, community_href, new_moderators, old_moderators, cur_moderators, prev_moderators): info = _get_common_email_info(community, community_href) subject_fmt = 'Change in moderators for %s' subject = subject_fmt % info['c_title'] body_template = get_renderer( 'templates/email_moderators_changed.pt').implementation() profiles = find_profiles(community) all_moderators = cur_moderators | prev_moderators to_profiles = [profiles[name] for name in all_moderators] to_addrs = ["%s <%s>" % (p.title, p.email) for p in to_profiles] mailer = getUtility(IMailDelivery) msg = Message() msg['From'] = info['mfrom'] msg['To'] = ",".join(to_addrs) msg['Subject'] = subject body = body_template( system_name=info['system_name'], community_href=info['c_href'], community_name=info['c_title'], new_moderators=[profiles[name].title for name in new_moderators], old_moderators=[profiles[name].title for name in old_moderators], cur_moderators=[profiles[name].title for name in cur_moderators], prev_moderators=[profiles[name].title for name in prev_moderators]) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send(to_addrs, msg)
def addFile(self, paramName, fileName, data): """attaches the contents of fileName under the http parameter name paramName. """ msg = Message() msg.set_type("application/octet-stream") msg["Content-Disposition"] = "form-data" msg.set_param("name", paramName, "Content-Disposition") msg.set_param("filename", fileName, "Content-Disposition") msg.set_payload(data) self.attach(msg)
def create_msg(v, rcptlist=None, origmsg=None, template=None): """Create a DSN message from a template. Template must be '\n' separated. v - an object whose attributes are used for substitutions. Must have sender and receiver attributes at a minimum. rcptlist - used to set v.rcpt if given origmsg - used to set v.subject and v.spf_result if given template - a '\n' separated string with python '%(name)s' substitutions. """ if not template: return None if hasattr(v, 'perm_error'): # likely to be an spf.query, try translating for backward compatibility q = v v = Vars() try: v.heloname = q.h v.sender = q.s v.connectip = q.i v.receiver = q.r v.sender_domain = q.o v.result = q.result v.perm_error = q.perm_error except: v = q if rcptlist: v.rcpt = '\n\t'.join(rcptlist) if origmsg: try: v.subject = origmsg['Subject'] except: v.subject = '(none)' try: v.spf_result = origmsg['Received-SPF'] except: v.spf_result = None msg = Message() msg.add_header('X-Mailer', 'PyMilter-' + Milter.__version__) msg.set_type('text/plain') hdrs, body = template.split('\n\n', 1) for ln in hdrs.splitlines(): name, val = ln.split(':', 1) msg.add_header(name, (val % v.__dict__).strip()) msg.set_payload(body % v.__dict__) # add headers if missing from old template if 'to' not in msg: msg.add_header('To', v.sender) if 'from' not in msg: msg.add_header('From', 'postmaster@%s' % v.receiver) if 'auto-submitted' not in msg: msg.add_header('Auto-Submitted', 'auto-generated') return msg
def generateMessage(self, text): """generateMessageObject(text) This will create a headered, MIME-formatted message, with content type as text/plain,format=flowed and will flow the passed in text. Note an agent will still need to call the prepare function to space stfuf any sections which require it. You can take the return value, and just attach it, or turn it into a full message by adding the required headers.""" msg = Message() msg.set_type("text/plain") msg.set_param("format", "flowed") msg.set_payload(self.flow(text)) return msg
def create_msg(v,rcptlist=None,origmsg=None,template=None): """Create a DSN message from a template. Template must be '\n' separated. v - an object whose attributes are used for substitutions. Must have sender and receiver attributes at a minimum. rcptlist - used to set v.rcpt if given origmsg - used to set v.subject and v.spf_result if given template - a '\n' separated string with python '%(name)s' substitutions. """ if not template: return None if hasattr(v,'perm_error'): # likely to be an spf.query, try translating for backward compatibility q = v v = Vars() try: v.heloname = q.h v.sender = q.s v.connectip = q.i v.receiver = q.r v.sender_domain = q.o v.result = q.result v.perm_error = q.perm_error except: v = q if rcptlist: v.rcpt = '\n\t'.join(rcptlist) if origmsg: try: v.subject = origmsg['Subject'] except: v.subject = '(none)' try: v.spf_result = origmsg['Received-SPF'] except: v.spf_result = None msg = Message() msg.add_header('X-Mailer','PyMilter-'+Milter.__version__) msg.set_type('text/plain') hdrs,body = template.split('\n\n',1) for ln in hdrs.splitlines(): name,val = ln.split(':',1) msg.add_header(name,(val % v.__dict__).strip()) msg.set_payload(body % v.__dict__) # add headers if missing from old template if 'to' not in msg: msg.add_header('To',v.sender) if 'from' not in msg: msg.add_header('From','postmaster@%s'%v.receiver) if 'auto-submitted' not in msg: msg.add_header('Auto-Submitted','auto-generated') return msg
def handle_submit(self, validated): user = _get_user_by_email(self.context, validated['email']) # No such user, we're not letting anyone know about it though to protect # users from crooks trying to explore the users DB in hope of finding # out who has an account here. if not user: return self._redirect() request_id = uuid4().hex request = PasswordRequestRequest(request_id, user.email) site = find_site(self.context) if user.email in site['reset_password']: del site['reset_password'][user.email] site['reset_password'][user.email] = request reset_url = model_url(self.context, self.request, "reset.html", query=dict(key=request_id)) # send email mail = Message() system_name = get_setting(self.context, 'system_name', 'OpenCore') admin_email = get_setting(self.context, 'admin_email') mail["From"] = "%s Administrator <%s>" % (system_name, admin_email) mail["To"] = "%s <%s>" % (user.title, user.email) mail["Subject"] = "%s Password Reset Request" % system_name body = render_template( "templates/email_reset_password.pt", login=user.__name__, reset_url=reset_url, system_name=system_name, valid_hours=REQUEST_VALIDITY_HOURS, ) if isinstance(body, unicode): body = body.encode("UTF-8") mail.set_payload(body, "UTF-8") mail.set_type("text/html") recipients = [user.email] mailer = getUtility(IMailDelivery) mailer.send(admin_email, recipients, mail) return self._redirect()
def forum_post_as_email(self, forum, post): '''Convert a post to email''' topic = post.topic sre, subject = re.match(r'(Re: )?(.*)', post.subject).groups() if subject == '': if post.pid != topic.firstpost: sre = 'Re: ' subject = topic.title or 'topic %s' % topic.tid subject = (sre or '') + forum.subjectPrefix + subject if post.datetime is not None: pass zauthor,n = re.subn(r'[^-A-Za-z0-9]+','_', post.author) fromm = _subst(self.fromPattern, u=zauthor) msgid = _subst(self.messageIdPattern, p=post.pid) hbody = '<html><body>%s</body></html>' % post.body.encode('utf-8') try: from email.Message import Message from email.Header import Header from email.Utils import formatdate # Force quoted-printable for utf-8 instead of base64 (for Thunderbird "View source") import email.Charset as cs cs.add_charset('utf-8', cs.SHORTEST, cs.QP, 'utf-8') except ImportError: from email.message import Message from email.header import Header from email.utils import formatdate msg = Message() msg.add_header('From', fromm) msg.add_header('To', forum.recipient) hsubj = Header(subject) msg.add_header('Subject', str(hsubj)) msg.add_header('Message-ID', '<%s>' % msgid) if topic.firstpost: firstid = _subst(self.messageIdPattern, p=topic.firstpost) msg.add_header('In-Reply-To', '<%s>' % firstid) msg.add_header('References', '<%s>' % firstid) if post.datetime is not None: date = formatdate(post.datetime) msg.add_header('Date', date) msg.set_payload(hbody) msg.set_type('text/html') msg.set_charset('utf-8') return msg.as_string()
def _send_moderators_changed_email(community, community_href, new_moderators, old_moderators, cur_moderators, prev_moderators): info = _get_common_email_info(community, community_href) subject_fmt = 'Change in moderators for %s' subject = subject_fmt % info['c_title'] body_template = get_renderer( 'templates/email_moderators_changed.pt').implementation() profiles = find_profiles(community) all_moderators = cur_moderators | prev_moderators to_profiles = [profiles[name] for name in all_moderators] to_addrs = ["%s <%s>" % (p.title, p.email) for p in to_profiles] mailer = getUtility(IMailDelivery) msg = Message() msg['From'] = info['mfrom'] msg['To'] = ",".join(to_addrs) msg['Subject'] = subject body = body_template( system_name=info['system_name'], community_href=info['c_href'], community_name=info['c_title'], new_moderators=[profiles[name].title for name in new_moderators], old_moderators=[profiles[name].title for name in old_moderators], cur_moderators=[profiles[name].title for name in cur_moderators], prev_moderators=[profiles[name].title for name in prev_moderators] ) if isinstance(body, unicode): body = body.encode("UTF-8") msg.set_payload(body, "UTF-8") msg.set_type('text/html') mailer.send(to_addrs, msg)
def forgot_password_view(context, request): email = request.params.get('email', '') message = '' if 'form.submitted' in request.params: schema = ForgotPasswordSchema() try: schema.to_python(request.params) except formencode.validators.Invalid, why: message = str(why) else: profiles = find_profiles(context) found_profile = None for profile in profiles.values(): if profile.email == email: found_profile = profile break if found_profile is None: message = 'Email %s not found' % email else: login = profile.__name__ password = random_password() users = find_users(context) users.change_password(login, password) msg = Message() frm = 'bfg.repoze.org <*****@*****.**>' msg['From'] = frm msg['To'] = email msg['Subject'] = 'Account information' body = 'Your new password is "%s" for login name "%s"' % ( password, login) msg.set_payload(body) msg.set_type('text/html') message = msg.as_string() mailer = get_mailer() mailer.send(frm, [email], message) message = 'Mail sent to "%s" with new password' % email
marshaler = queryMultiAdapter(( context, field, ), IFieldMarshaler) if marshaler is None: continue payload = Message() attach = False contentType = marshaler.getContentType() payloadCharset = marshaler.getCharset(charset) if contentType is not None: payload.set_type(contentType) attach = True if payloadCharset is not None: # using set_charset() would also add transfer encoding, # which we don't want to do always payload.set_param('charset', payloadCharset) attach = True value = marshaler.marshal(charset, primary=True) if value is not None: payload.set_payload(value) attach = True if attach: marshaler.postProcessMessage(payload)
def constructMessage(context, fields, charset='utf-8'): msg = Message() primary = [] # First get all headers, storing primary fields for later for name, field in fields: if IPrimaryField.providedBy(field): primary.append((name, field,)) break # marshaler = queryMultiAdapter((context, field,), IFieldMarshaler) # if marshaler is None: # LOG.debug("No marshaler found for field %s of %s" % (name, repr(context))) # continue # # try: # value = marshaler.marshal(charset, primary=False) # except ValueError, e: # LOG.debug("Marshaling of %s for %s failed: %s" % (name, repr(context), str(e))) # continue # # if value is None: # value = '' # elif not isinstance(value, str): # raise ValueError("Marshaler for field %s did not return a string" % name) # # if marshaler.ascii and '\n' not in value: # msg[name] = value # else: # msg[name] = Header(value, charset) # Then deal with the primary field # If there's a single primary field, we have a non-multipart message with # a string payload if len(primary) == 1: name, field = primary[0] marshaler = queryMultiAdapter((context, field,), IFieldMarshaler) # import pdb # pdb.set_trace() if marshaler is not None: contentType = marshaler.getContentType() payloadCharset = marshaler.getCharset(charset) # if contentType is not None: # msg.set_type(contentType) # # if payloadCharset is not None: # # using set_charset() would also add transfer encoding, # # which we don't want to do always # msg.set_param('charset', payloadCharset) value = marshaler.marshal(charset, primary=True) # import pdb # pdb.set_trace() if value is not None: msg.set_payload(value) # marshaler.postProcessMessage(msg) # Otherwise, we return a multipart message elif len(primary) > 1: msg.set_type('multipart/mixed') for name, field in primary: marshaler = queryMultiAdapter((context, field,), IFieldMarshaler) if marshaler is None: continue payload = Message() attach = False contentType = marshaler.getContentType() payloadCharset = marshaler.getCharset(charset) if contentType is not None: payload.set_type(contentType) attach = True if payloadCharset is not None: # using set_charset() would also add transfer encoding, # which we don't want to do always payload.set_param('charset', payloadCharset) attach = True value = marshaler.marshal(charset, primary=True) if value is not None: payload.set_payload(value) attach = True if attach: marshaler.postProcessMessage(payload) msg.attach(payload) return msg
msg.set_type('multipart/mixed') for name, field in primary: marshaler = queryMultiAdapter((context, field,), IFieldMarshaler) if marshaler is None: continue payload = Message() attach = False contentType = marshaler.getContentType() payloadCharset = marshaler.getCharset(charset) if contentType is not None: payload.set_type(contentType) attach = True if payloadCharset is not None: # using set_charset() would also add transfer encoding, # which we don't want to do always payload.set_param('charset', payloadCharset) attach = True value = marshaler.marshal(charset, primary=True) if value is not None: payload.set_payload(value) attach = True if attach: marshaler.postProcessMessage(payload)