def send_instant_notifications_about_activity_in_post(update_activity=None, post=None, recipients=None): # reload object from the database post = Post.objects.get(id=post.id) if post.is_approved() is False: return if recipients is None: return acceptable_types = const.RESPONSE_ACTIVITY_TYPES_FOR_INSTANT_NOTIFICATIONS if update_activity.activity_type not in acceptable_types: return # calculate some variables used in the loop below update_type_map = const.RESPONSE_ACTIVITY_TYPE_MAP_FOR_TEMPLATES update_type = update_type_map[update_activity.activity_type] origin_post = post.get_origin_post() headers = mail.thread_headers(post, origin_post, update_activity.activity_type) logger = logging.getLogger() if logger.getEffectiveLevel() <= logging.DEBUG: log_id = uuid.uuid1() message = "email-alert %s, logId=%s" % (post.get_absolute_url(), log_id) logger.debug(message) else: log_id = None for user in recipients: if user.is_blocked(): continue reply_address, alt_reply_address = get_reply_to_addresses(user, post) subject_line, body_text = format_instant_notification_email( to_user=user, from_user=update_activity.user, post=post, reply_address=reply_address, alt_reply_address=alt_reply_address, update_type=update_type, template=get_template("email/instant_notification.html"), ) headers["Reply-To"] = reply_address try: mail.send_mail( subject_line=subject_line, body_text=body_text, recipient_list=[user.email], related_object=origin_post, activity_type=const.TYPE_ACTIVITY_EMAIL_UPDATE_SENT, headers=headers, raise_on_failure=True, ) except askbot_exceptions.EmailNotSent, error: logger.debug("%s, error=%s, logId=%s" % (user.email, error, log_id)) else: logger.debug("success %s, logId=%s" % (user.email, log_id))
def process_context(self, context): to_user = context.get('to_user') from_user = context.get('from_user') post = context.get('post') update_activity = context.get('update_activity') update_type = self.get_update_type(update_activity) #unhandled update_type 'post_shared' #user_action = _('%(user)s shared a %(post_link)s.') origin_post = post.get_origin_post() post_url = site_url(post.get_absolute_url()) can_reply = to_user.can_post_by_email() from askbot.models import get_reply_to_addresses reply_address, alt_reply_address = get_reply_to_addresses( to_user, post) alt_reply_subject = urllib.quote( ('Re: ' + post.thread.title).encode('utf-8')) return { 'admin_email': askbot_settings.ADMIN_EMAIL, 'recipient_user': to_user, 'update_author_name': from_user.username, 'receiving_user_name': to_user.username, 'receiving_user_karma': to_user.reputation, 'reply_by_email_karma_threshold': askbot_settings.MIN_REP_TO_POST_BY_EMAIL, 'can_reply': can_reply, 'update_type': update_type, 'update_activity': update_activity, 'post': post, 'post_url': post_url, 'origin_post': origin_post, 'thread_title': origin_post.thread.title, 'reply_address': reply_address, 'alt_reply_address': alt_reply_address, 'alt_reply_subject': alt_reply_subject, 'is_multilingual': getattr(django_settings, 'ASKBOT_MULTILINGUAL', False), 'reply_sep_tpl': const.SIMPLE_REPLY_SEPARATOR_TEMPLATE }
def process_context(self, context): to_user = context.get("to_user") from_user = context.get("from_user") post = context.get("post") update_activity = context.get("update_activity") update_type = self.get_update_type(update_activity) # unhandled update_type 'post_shared' # user_action = _('%(user)s shared a %(post_link)s.') origin_post = post.get_origin_post() post_url = site_url(post.get_absolute_url()) can_reply = to_user.can_post_by_email() from askbot.models import get_reply_to_addresses reply_address, alt_reply_address = get_reply_to_addresses(to_user, post) alt_reply_subject = urllib.quote(("Re: " + post.thread.title).encode("utf-8")) return { "admin_email": askbot_settings.ADMIN_EMAIL, "recipient_user": to_user, "update_author_name": from_user.username, "receiving_user_name": to_user.username, "receiving_user_karma": to_user.reputation, "reply_by_email_karma_threshold": askbot_settings.MIN_REP_TO_POST_BY_EMAIL, "can_reply": can_reply, "update_type": update_type, "update_activity": update_activity, "post": post, "post_url": post_url, "origin_post": origin_post, "thread_title": origin_post.thread.title, "reply_address": reply_address, "alt_reply_address": alt_reply_address, "alt_reply_subject": alt_reply_subject, "is_multilingual": askbot.is_multilingual(), "reply_sep_tpl": const.SIMPLE_REPLY_SEPARATOR_TEMPLATE, }
def process_context(self, context): to_user = context.get('to_user') from_user = context.get('from_user') post = context.get('post') update_activity = context.get('update_activity') update_type = self.get_update_type(update_activity) #unhandled update_type 'post_shared' #user_action = _('%(user)s shared a %(post_link)s.') origin_post = post.get_origin_post() post_url = site_url(post.get_absolute_url()) can_reply = to_user.can_post_by_email() from askbot.models import get_reply_to_addresses reply_address, alt_reply_address = get_reply_to_addresses(to_user, post) alt_reply_subject = urllib.quote(('Re: ' + post.thread.title).encode('utf-8')) return { 'admin_email': askbot_settings.ADMIN_EMAIL, 'recipient_user': to_user, 'update_author_name': from_user.username, 'receiving_user_name': to_user.username, 'receiving_user_karma': to_user.reputation, 'reply_by_email_karma_threshold': askbot_settings.MIN_REP_TO_POST_BY_EMAIL, 'can_reply': can_reply, 'update_type': update_type, 'update_activity': update_activity, 'post': post, 'post_url': post_url, 'origin_post': origin_post, 'thread_title': origin_post.thread.title, 'reply_address': reply_address, 'alt_reply_address': alt_reply_address, 'alt_reply_subject': alt_reply_subject, 'is_multilingual': askbot.is_multilingual(), 'reply_sep_tpl': const.SIMPLE_REPLY_SEPARATOR_TEMPLATE }
def send_instant_notifications_about_activity_in_post( activity_id=None, post_id=None, recipients=None, ): if recipients is None: return acceptable_types = const.RESPONSE_ACTIVITY_TYPES_FOR_INSTANT_NOTIFICATIONS try: update_activity = Activity.objects.filter( activity_type__in=acceptable_types).get(id=activity_id) except Activity.DoesNotExist: logger.error("Unable to fetch activity with id %s" % post_id) return try: post = Post.objects.get(id=post_id) except Post.DoesNotExist: logger.error("Unable to fetch post with id %s" % post_id) return if post.is_approved() is False: return #calculate some variables used in the loop below update_type_map = const.RESPONSE_ACTIVITY_TYPE_MAP_FOR_TEMPLATES update_type = update_type_map[update_activity.activity_type] origin_post = post.get_origin_post() headers = mail.thread_headers(post, origin_post, update_activity.activity_type) if logger.getEffectiveLevel() <= logging.DEBUG: log_id = uuid.uuid1() message = 'email-alert %s, logId=%s' % (post.get_absolute_url(), log_id) logger.debug(message) else: log_id = None for user in recipients: if user.is_blocked(): continue reply_address, alt_reply_address = get_reply_to_addresses(user, post) activate_language(post.language_code) subject_line, body_text = format_instant_notification_email( to_user=user, from_user=update_activity.user, post=post, reply_address=reply_address, alt_reply_address=alt_reply_address, update_type=update_type, template=get_template('email/instant_notification.html')) headers['Reply-To'] = reply_address try: mail.send_mail(subject_line=subject_line, body_text=body_text, recipient_list=[user.email], related_object=origin_post, activity_type=const.TYPE_ACTIVITY_EMAIL_UPDATE_SENT, headers=headers, raise_on_failure=True) except askbot_exceptions.EmailNotSent, error: logger.debug('%s, error=%s, logId=%s' % (user.email, error, log_id)) else: logger.debug('success %s, logId=%s' % (user.email, log_id))
def process_context(self, context): to_user = context.get('to_user') from_user = context.get('from_user') post = context.get('post') update_activity = context.get('update_activity') update_type = self.get_update_type(update_activity) origin_post = post.get_origin_post() from askbot.models import Post if update_type == 'question_comment': assert(isinstance(post, Post) and post.is_comment()) assert(post.parent and post.parent.is_question()) elif update_type == 'answer_comment': assert(isinstance(post, Post) and post.is_comment()) assert(post.parent and post.parent.is_answer()) elif update_type == 'answer_update': assert(isinstance(post, Post) and post.is_answer()) elif update_type == 'new_answer': assert(isinstance(post, Post) and post.is_answer()) elif update_type == 'question_update': assert(isinstance(post, Post) and post.is_question()) elif update_type == 'new_question': assert(isinstance(post, Post) and post.is_question()) elif update_type == 'post_shared': pass else: raise ValueError('unexpected update_type %s' % update_type) if update_type.endswith('update'): assert('comment' not in update_type) revisions = post.revisions.all()[:2] assert(len(revisions) == 2) content_preview = htmldiff( sanitize_html(revisions[1].html), sanitize_html(revisions[0].html), ins_start = '<b><u style="background-color:#cfc">', ins_end = '</u></b>', del_start = '<del style="color:#600;background-color:#fcc">', del_end = '</del>' ) #todo: remove hardcoded style else: content_preview = post.format_for_email(is_leaf_post=True, recipient=to_user) #add indented summaries for the parent posts content_preview += post.format_for_email_as_parent_thread_summary(recipient=to_user) #content_preview += '<p>======= Full thread summary =======</p>' #content_preview += post.thread.format_for_email(recipient=to_user) if update_type == 'post_shared': user_action = _('%(user)s shared a %(post_link)s.') elif post.is_comment(): if update_type.endswith('update'): user_action = _('%(user)s edited a %(post_link)s.') else: user_action = _('%(user)s posted a %(post_link)s') elif post.is_answer(): if update_type.endswith('update'): user_action = _('%(user)s edited an %(post_link)s.') else: user_action = _('%(user)s posted an %(post_link)s.') elif post.is_question(): if update_type.endswith('update'): user_action = _('%(user)s edited a %(post_link)s.') else: user_action = _('%(user)s posted a %(post_link)s.') else: raise ValueError('unrecognized post type') post_url = site_url(post.get_absolute_url()) user_url = site_url(from_user.get_absolute_url()) if to_user.is_administrator_or_moderator() and askbot_settings.SHOW_ADMINS_PRIVATE_USER_DATA: user_link_fmt = '<a href="%(profile_url)s">%(username)s</a> (<a href="mailto:%(email)s">%(email)s</a>)' user_link = user_link_fmt % { 'profile_url': user_url, 'username': from_user.username, 'email': from_user.email } elif post.is_anonymous: user_link = from_user.get_name_of_anonymous_user() else: user_link = '<a href="%s">%s</a>' % (user_url, from_user.username) user_action = user_action % { 'user': user_link, 'post_link': '<a href="%s">%s</a>' % (post_url, _(post.post_type)) } can_reply = to_user.can_post_by_email() from askbot.models import get_reply_to_addresses reply_address, alt_reply_address = get_reply_to_addresses(to_user, post) if can_reply: reply_separator = const.SIMPLE_REPLY_SEPARATOR_TEMPLATE % \ _('To reply, PLEASE WRITE ABOVE THIS LINE.') if post.post_type == 'question' and alt_reply_address: data = { 'addr': alt_reply_address, 'subject': urllib.quote( ('Re: ' + post.thread.title).encode('utf-8') ) } reply_separator += '<p>' + const.REPLY_WITH_COMMENT_TEMPLATE % data reply_separator += '</p>' else: reply_separator = '<p>%s</p>' % reply_separator reply_separator += user_action else: reply_separator = user_action return { 'admin_email': askbot_settings.ADMIN_EMAIL, 'recipient_user': to_user, 'update_author_name': from_user.username, 'receiving_user_name': to_user.username, 'receiving_user_karma': to_user.reputation, 'reply_by_email_karma_threshold': askbot_settings.MIN_REP_TO_POST_BY_EMAIL, 'can_reply': can_reply, 'content_preview': content_preview, 'update_type': update_type, 'update_activity': update_activity, 'post': post, 'post_url': post_url, 'origin_post': origin_post, 'thread_title': origin_post.thread.title, 'reply_separator': reply_separator, 'reply_address': reply_address, 'is_multilingual': getattr(django_settings, 'ASKBOT_MULTILINGUAL', False) }
def process_context(self, context): to_user = context.get('to_user') from_user = context.get('from_user') post = context.get('post') update_activity = context.get('update_activity') update_type = self.get_update_type(update_activity) origin_post = post.get_origin_post() from askbot.models import Post if update_type == 'question_comment': assert (isinstance(post, Post) and post.is_comment()) assert (post.parent and post.parent.is_question()) elif update_type == 'answer_comment': assert (isinstance(post, Post) and post.is_comment()) assert (post.parent and post.parent.is_answer()) elif update_type == 'answer_update': assert (isinstance(post, Post) and post.is_answer()) elif update_type == 'new_answer': assert (isinstance(post, Post) and post.is_answer()) elif update_type == 'question_update': assert (isinstance(post, Post) and post.is_question()) elif update_type == 'new_question': assert (isinstance(post, Post) and post.is_question()) elif update_type == 'post_shared': pass else: raise ValueError('unexpected update_type %s' % update_type) if update_type.endswith('update'): assert ('comment' not in update_type) revisions = post.revisions.all()[:2] assert (len(revisions) == 2) content_preview = htmldiff( sanitize_html(revisions[1].html), sanitize_html(revisions[0].html), ins_start='<b><u style="background-color:#cfc">', ins_end='</u></b>', del_start='<del style="color:#600;background-color:#fcc">', del_end='</del>') #todo: remove hardcoded style else: content_preview = post.format_for_email(is_leaf_post=True, recipient=to_user) #add indented summaries for the parent posts content_preview += post.format_for_email_as_parent_thread_summary( recipient=to_user) #content_preview += '<p>======= Full thread summary =======</p>' #content_preview += post.thread.format_for_email(recipient=to_user) if update_type == 'post_shared': user_action = _('%(user)s shared a %(post_link)s.') elif post.is_comment(): if update_type.endswith('update'): user_action = _('%(user)s edited a %(post_link)s.') else: user_action = _('%(user)s posted a %(post_link)s') elif post.is_answer(): if update_type.endswith('update'): user_action = _('%(user)s edited an %(post_link)s.') else: user_action = _('%(user)s posted an %(post_link)s.') elif post.is_question(): if update_type.endswith('update'): user_action = _('%(user)s edited a %(post_link)s.') else: user_action = _('%(user)s posted a %(post_link)s.') else: raise ValueError('unrecognized post type') post_url = site_url(post.get_absolute_url()) user_url = site_url(from_user.get_absolute_url()) if to_user.is_administrator_or_moderator( ) and askbot_settings.SHOW_ADMINS_PRIVATE_USER_DATA: user_link_fmt = '<a href="%(profile_url)s">%(username)s</a> (<a href="mailto:%(email)s">%(email)s</a>)' user_link = user_link_fmt % { 'profile_url': user_url, 'username': from_user.username, 'email': from_user.email } elif post.is_anonymous: user_link = from_user.get_name_of_anonymous_user() else: user_link = '<a href="%s">%s</a>' % (user_url, from_user.username) user_action = user_action % { 'user': user_link, 'post_link': '<a href="%s">%s</a>' % (post_url, _(post.post_type)) } can_reply = to_user.can_post_by_email() from askbot.models import get_reply_to_addresses reply_address, alt_reply_address = get_reply_to_addresses( to_user, post) if can_reply: reply_separator = const.SIMPLE_REPLY_SEPARATOR_TEMPLATE % \ _('To reply, PLEASE WRITE ABOVE THIS LINE.') if post.post_type == 'question' and alt_reply_address: data = { 'addr': alt_reply_address, 'subject': urllib.quote(('Re: ' + post.thread.title).encode('utf-8')) } reply_separator += '<p>' + const.REPLY_WITH_COMMENT_TEMPLATE % data reply_separator += '</p>' else: reply_separator = '<p>%s</p>' % reply_separator reply_separator += user_action else: reply_separator = user_action return { 'admin_email': askbot_settings.ADMIN_EMAIL, 'recipient_user': to_user, 'update_author_name': from_user.username, 'receiving_user_name': to_user.username, 'receiving_user_karma': to_user.reputation, 'reply_by_email_karma_threshold': askbot_settings.MIN_REP_TO_POST_BY_EMAIL, 'can_reply': can_reply, 'content_preview': content_preview, 'update_type': update_type, 'update_activity': update_activity, 'post': post, 'post_url': post_url, 'origin_post': origin_post, 'thread_title': origin_post.thread.title, 'reply_separator': reply_separator, 'reply_address': reply_address, 'is_multilingual': getattr(django_settings, 'ASKBOT_MULTILINGUAL', False) }