X-Git-Url: https://git.openstreetmap.org./osqa.git/blobdiff_plain/0f2d00f9d7d5d28149707f66c719b28edfe51aed..2c3ba81e19fd6d84ab208ad90a48fd81e4780c29:/forum/subscriptions.py
diff --git a/forum/subscriptions.py b/forum/subscriptions.py
index 4c57256..fad24a5 100644
--- a/forum/subscriptions.py
+++ b/forum/subscriptions.py
@@ -1,227 +1,198 @@
-import os
-import re
-import datetime
-from forum.models import User, Question, Comment, QuestionSubscription, SubscriptionSettings, Answer
-from forum.models.user import activity_record
-from forum.utils.mail import send_email
-from forum.views.readers import question_view
-from django.utils.translation import ugettext as _
-from django.conf import settings
-from django.db.models import Q, F
-from django.db.models.signals import post_save
-from django.contrib.contenttypes.models import ContentType
-import const
-
-def create_subscription_if_not_exists(question, user):
- try:
- subscription = QuestionSubscription.objects.get(question=question, user=user)
- except:
- subscription = QuestionSubscription(question=question, user=user)
- subscription.save()
-
-def apply_default_filters(queryset, excluded_id):
- return queryset.values('email', 'username').exclude(id=excluded_id)
-
-def create_recipients_dict(usr_list):
- return [(s['username'], s['email'], {'username': s['username']}) for s in usr_list]
-
-def question_posted(instance, created, **kwargs):
- if not created: return
-
- question = instance
-
- subscribers = User.objects.values('email', 'username').filter(
- Q(subscription_settings__enable_notifications=True, subscription_settings__new_question='i') |
- (Q(subscription_settings__new_question_watched_tags='i') &
- Q(marked_tags__name__in=question.tagnames.split(' ')) &
- Q(tag_selections__reason='good'))
- ).exclude(id=question.author.id).distinct()
-
- recipients = create_recipients_dict(subscribers)
-
- send_email(settings.EMAIL_SUBJECT_PREFIX + _("New question on %(app_name)s") % dict(app_name=settings.APP_SHORT_NAME),
- recipients, "notifications/newquestion.html", {
- 'question': question,
- })
-
- if question.author.subscription_settings.questions_asked:
- subscription = QuestionSubscription(question=question, user=question.author)
- subscription.save()
-
- new_subscribers = User.objects.filter(
- Q(subscription_settings__all_questions=True) |
- Q(subscription_settings__all_questions_watched_tags=True,
- marked_tags__name__in=question.tagnames.split(' '),
- tag_selections__reason='good'))
-
- for user in new_subscribers:
- create_subscription_if_not_exists(question, user)
-
-#post_save.connect(question_posted, sender=Question)
-
-
-def answer_posted(instance, created, **kwargs):
- if not created: return
-
- answer = instance
- question = answer.question
-
- subscribers = question.subscribers.values('email', 'username').filter(
- subscription_settings__enable_notifications=True,
- subscription_settings__notify_answers=True,
- subscription_settings__subscribed_questions='i'
- ).exclude(id=answer.author.id).distinct()
- recipients = create_recipients_dict(subscribers)
-
- send_email(settings.EMAIL_SUBJECT_PREFIX + _("New answer to '%(question_title)s'") % dict(question_title=question.title),
- recipients, "notifications/newanswer.html", {
- 'question': question,
- 'answer': answer
- })
-
- if answer.author.subscription_settings.questions_answered:
- create_subscription_if_not_exists(question, answer.author)
-
-post_save.connect(answer_posted, sender=Answer)
-
-
-def comment_posted(sender, instance, **kwargs):
- comment = instance.content_object
- post = comment.content_object
-
- if post.__class__ == Question:
- question = post
- else:
- question = post.question
-
- subscribers = question.subscribers.values('email', 'username')
-
- q_filter = Q(subscription_settings__notify_comments=True) | Q(subscription_settings__notify_comments_own_post=True, id=post.author.id)
-
- inreply = re.search('@\w+', comment.comment)
- if inreply is not None:
- q_filter = q_filter | Q(subscription_settings__notify_reply_to_comments=True,
- username__istartswith=inreply.group(0)[1:],
- comments__object_id=post.id,
- comments__content_type=ContentType.objects.get_for_model(post.__class__)
- )
-
- subscribers = subscribers.filter(
- q_filter, subscription_settings__subscribed_questions='i', subscription_settings__enable_notifications=True
- ).exclude(id=comment.user.id).distinct()
-
- recipients = create_recipients_dict(subscribers)
-
- send_email(settings.EMAIL_SUBJECT_PREFIX + _("New comment on %(question_title)s") % dict(question_title=question.title),
- recipients, "notifications/newcomment.html", {
- 'comment': comment,
- 'post': post,
- 'question': question,
- })
-
- if comment.user.subscription_settings.questions_commented:
- create_subscription_if_not_exists(question, comment.user)
-
-activity_record.connect(comment_posted, sender=const.TYPE_ACTIVITY_COMMENT_QUESTION, weak=False)
-activity_record.connect(comment_posted, sender=const.TYPE_ACTIVITY_COMMENT_ANSWER, weak=False)
-
-
-def answer_accepted(instance, created, **kwargs):
- if not created and 'accepted' in instance.get_dirty_fields() and instance.accepted:
- question = instance.question
-
- subscribers = question.subscribers.values('email', 'username').filter(
- subscription_settings__enable_notifications=True,
- subscription_settings__notify_accepted=True,
- subscription_settings__subscribed_questions='i'
- ).exclude(id=instance.accepted_by.id).distinct()
- recipients = create_recipients_dict(subscribers)
-
- send_email(settings.EMAIL_SUBJECT_PREFIX + _("An answer to '%(question_title)s' was accepted") % dict(question_title=question.title),
- recipients, "notifications/answeraccepted.html", {
- 'question': question,
- 'answer': instance
- })
-
-post_save.connect(answer_accepted, sender=Answer)
-
-
-def member_joined(sender, instance, created, **kwargs):
- if not created:
- return
-
- subscribers = User.objects.values('email', 'username').filter(
- subscription_settings__enable_notifications=True,
- subscription_settings__member_joins='i'
- ).exclude(id=instance.id).distinct()
-
- recipients = create_recipients_dict(subscribers)
-
- send_email(settings.EMAIL_SUBJECT_PREFIX + _("%(username)s is a new member on %(app_name)s") % dict(username=instance.username, app_name=settings.APP_SHORT_NAME),
- recipients, "notifications/newmember.html", {
- 'newmember': instance,
- })
-
- sub_settings = SubscriptionSettings(user=instance)
- sub_settings.save()
-
-post_save.connect(member_joined, sender=User, weak=False)
-
-def question_viewed(instance, user, **kwargs):
- if not user.is_authenticated():
- return
-
- try:
- subscription = QuestionSubscription.objects.get(question=instance, user=user)
- subscription.last_view = datetime.datetime.now()
- subscription.save()
- except:
- if user.subscription_settings.questions_viewed:
- subscription = QuestionSubscription(question=instance, user=user)
- subscription.save()
-
-question_view.connect(question_viewed)
-
-#todo: this stuff goes temporarily here
-from forum.models import Award, Answer
-
-def notify_award_message(instance, created, **kwargs):
- if created:
- user = instance.user
-
- msg = (u"Congratulations, you have received a badge '%s'. " \
- + u"Check out your profile.") \
- % (instance.badge.name, user.get_profile_url())
-
- user.message_set.create(message=msg)
-
-post_save.connect(notify_award_message, sender=Award)
-
-#todo: translate this
-record_answer_event_re = re.compile("You have received (a|\d+) .*new response.*")
-def record_answer_event(instance, created, **kwargs):
- if created:
- q_author = instance.question.author
- found_match = False
- #print 'going through %d messages' % q_author.message_set.all().count()
- for m in q_author.message_set.all():
- #print m.message
- match = record_answer_event_re.search(m.message)
- if match:
- found_match = True
- try:
- cnt = int(match.group(1))
- except:
- cnt = 1
- m.message = u"You have received %d new responses."\
- % (cnt+1, q_author.get_profile_url())
-
- m.save()
- break
- if not found_match:
- msg = u"You have received a new response."\
- % q_author.get_profile_url()
-
- q_author.message_set.create(message=msg)
-
-post_save.connect(record_answer_event, sender=Answer)
\ No newline at end of file
+import os
+import re
+import datetime
+import logging
+from forum.models import User, Question, Comment, QuestionSubscription, SubscriptionSettings, Answer
+from forum.utils.mail import send_template_email
+from django.utils.translation import ugettext as _
+from forum.actions import AskAction, AnswerAction, CommentAction, AcceptAnswerAction, UserJoinsAction, QuestionViewAction
+from forum import settings
+from django.db.models import Q, F
+
+def create_subscription_if_not_exists(question, user):
+ try:
+ subscription = QuestionSubscription.objects.get(question=question, user=user)
+ return subscription
+ except QuestionSubscription.MultipleObjectsReturned:
+ pass
+ except QuestionSubscription.DoesNotExist:
+ subscription = QuestionSubscription(question=question, user=user)
+ subscription.save()
+ return subscription
+ except Exception, e:
+ logging.error(e)
+
+ return False
+
+def filter_subscribers(subscribers):
+ subscribers = subscribers.exclude(is_active=False)
+
+ if settings.DONT_NOTIFY_UNVALIDATED:
+ return subscribers.exclude(email_isvalid=False)
+ else:
+ return subscribers
+
+def question_posted(action, new):
+ question = action.node
+
+ if not question.is_notifiable:
+ return
+
+ subscribers = User.objects.filter(
+ Q(subscription_settings__enable_notifications=True, subscription_settings__new_question='i') |
+ (Q(subscription_settings__new_question_watched_tags='i') &
+ Q(marked_tags__name__in=question.tagnames.split(' ')) &
+ Q(tag_selections__reason='good'))
+ ).exclude(id=question.author.id).distinct()
+
+ subscribers = filter_subscribers(subscribers)
+
+ send_template_email(subscribers, "notifications/newquestion.html", {'question': question})
+
+ subscription = QuestionSubscription(question=question, user=question.author)
+ subscription.save()
+
+ new_subscribers = User.objects.filter(
+ Q(subscription_settings__all_questions=True) |
+ Q(subscription_settings__all_questions_watched_tags=True,
+ marked_tags__name__in=question.tagnames.split(' '),
+ tag_selections__reason='good'))
+
+ for user in new_subscribers:
+ create_subscription_if_not_exists(question, user)
+
+AskAction.hook(question_posted)
+
+
+def answer_posted(action, new):
+ answer = action.node
+ question = answer.question
+
+ logging.error("Answer posted: %s" % str(answer.is_notifiable))
+
+ if not answer.is_notifiable or not question.is_notifiable:
+ return
+
+ subscribers = question.subscribers.filter(
+ subscription_settings__enable_notifications=True,
+ subscription_settings__notify_answers=True,
+ subscription_settings__subscribed_questions='i'
+ ).exclude(id=answer.author.id).distinct()
+
+ subscribers = filter_subscribers(subscribers)
+
+ send_template_email(subscribers, "notifications/newanswer.html", {'answer': answer})
+
+ create_subscription_if_not_exists(question, answer.author)
+
+AnswerAction.hook(answer_posted)
+
+
+def comment_posted(action, new):
+ comment = action.node
+ post = comment.parent
+
+ if not comment.is_notifiable or not post.is_notifiable:
+ return
+
+ if post.__class__ == Question:
+ question = post
+ else:
+ question = post.question
+
+ q_filter = Q(subscription_settings__notify_comments=True) | Q(subscription_settings__notify_comments_own_post=True, id=post.author.id)
+
+ inreply = re.search('@\w+', comment.comment)
+ if inreply is not None:
+ q_filter = q_filter | Q(subscription_settings__notify_reply_to_comments=True,
+ username__istartswith=inreply.group(0)[1:],
+ nodes__parent=post, nodes__node_type="comment")
+
+ subscribers = question.subscribers.filter(
+ q_filter, subscription_settings__subscribed_questions='i', subscription_settings__enable_notifications=True
+ ).exclude(id=comment.user.id).distinct()
+
+ subscribers = filter_subscribers(subscribers)
+
+
+ send_template_email(subscribers, "notifications/newcomment.html", {'comment': comment})
+
+ create_subscription_if_not_exists(question, comment.user)
+
+CommentAction.hook(comment_posted)
+
+
+def answer_accepted(action, new):
+ question = action.node.question
+
+ if not question.is_notifiable:
+ return
+
+ subscribers = question.subscribers.filter(
+ subscription_settings__enable_notifications=True,
+ subscription_settings__subscribed_questions='i'
+ ).exclude(id=action.node.nstate.accepted.by.id).distinct()
+
+ subscribers = filter_subscribers(subscribers)
+
+ send_template_email(subscribers, "notifications/answeraccepted.html", {'answer': action.node})
+
+AcceptAnswerAction.hook(answer_accepted)
+
+
+def member_joined(action, new):
+ subscribers = User.objects.filter(
+ subscription_settings__enable_notifications=True,
+ subscription_settings__member_joins='i'
+ ).exclude(id=action.user.id).distinct()
+
+ subscribers = filter_subscribers(subscribers)
+
+ send_template_email(subscribers, "notifications/newmember.html", {'newmember': action.user})
+
+UserJoinsAction.hook(member_joined)
+
+def question_viewed(action, new):
+ if not action.viewuser.is_authenticated():
+ return
+
+ try:
+ subscription = QuestionSubscription.objects.get(question=action.node, user=action.viewuser)
+ subscription.last_view = datetime.datetime.now()
+ subscription.save()
+ except:
+ if action.viewuser.subscription_settings.questions_viewed:
+ subscription = QuestionSubscription(question=action.node, user=action.viewuser)
+ subscription.save()
+
+QuestionViewAction.hook(question_viewed)
+
+
+#todo: translate this
+#record_answer_event_re = re.compile("You have received (a|\d+) .*new response.*")
+#def record_answer_event(instance, created, **kwargs):
+# if created:
+# q_author = instance.question.author
+# found_match = False
+# #print 'going through %d messages' % q_author.message_set.all().count()
+# for m in q_author.message_set.all():
+## #print m.message
+# # match = record_answer_event_re.search(m.message)
+# if match:
+# found_match = True
+# try:
+# cnt = int(match.group(1))
+# except:
+# cnt = 1
+## m.message = u"You have received %d new responses."\
+# # % (cnt+1, q_author.get_profile_url())
+#
+# m.save()
+# break
+# if not found_match:
+# msg = u"You have received a new response."\
+# % q_author.get_profile_url()
+#
+# q_author.message_set.create(message=msg)
+#
+#post_save.connect(record_answer_event, sender=Answer)