1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
|
from django.core.management.base import NoArgsCommand
from django.db import connection
from django.db.models import Q, F
from forum.models import *
from django.core.mail import EmailMessage
from django.utils.translation import ugettext as _
from django.utils.translation import ungettext
import datetime
import settings
class Command(NoArgsCommand):
def handle_noargs(self,**options):
try:
self.send_email_alerts()
except Exception, e:
print e
finally:
connection.close()
def get_updated_questions_for_user(self,user):
q_sel = []
q_ask = []
q_ans = []
q_all = []
now = datetime.datetime.now()
Q_set1 = Question.objects.exclude(
last_activity_by=user,
).exclude(
last_activity_at__lt=user.date_joined
).filter(
Q(viewed__who=user,viewed__when__lt=F('last_activity_at')) | \
~Q(viewed__who=user)
).exclude(
deleted=True
).exclude(
closed=True
)
user_feeds = EmailFeedSetting.objects.filter(subscriber=user).exclude(frequency='n')
for feed in user_feeds:
cutoff_time = now - EmailFeedSetting.DELTA_TABLE[feed.frequency]
if feed.reported_at == None or feed.reported_at <= cutoff_time:
Q_set = Q_set1.exclude(last_activity_at__gt=cutoff_time)
feed.reported_at = now
feed.save()#may not actually report anything, depending on filters below
if feed.feed_type == 'q_sel':
q_sel = Q_set.filter(followed_by=user)
q_sel.cutoff_time = cutoff_time
elif feed.feed_type == 'q_ask':
q_ask = Q_set.filter(author=user)
q_ask.cutoff_time = cutoff_time
elif feed.feed_type == 'q_ans':
q_ans = Q_set.filter(answers__author=user)
q_ans.cutoff_time = cutoff_time
elif feed.feed_type == 'q_all':
q_all = Q_set
q_all.cutoff_time = cutoff_time
#build list in this order
q_tbl = {}
def extend_question_list(src, dst):
if isinstance(src,list):
return
cutoff_time = src.cutoff_time
for q in src:
if q in dst:
if cutoff_time < dst[q]:
dst[q] = cutoff_time
else:
dst[q] = cutoff_time
extend_question_list(q_sel, q_tbl)
extend_question_list(q_ask, q_tbl)
extend_question_list(q_ans, q_tbl)
extend_question_list(q_all, q_tbl)
ctype = ContentType.objects.get_for_model(Question)
out = {}
for q, cutoff_time in q_tbl.items():
#todo use Activity, but first start keeping more Activity records
#act = Activity.objects.filter(content_type=ctype, object_id=q.id)
#get info on question edits, answer edits, comments
out[q] = {}
q_rev = QuestionRevision.objects.filter(question=q,revised_at__lt=cutoff_time)
q_rev = q_rev.exclude(author=user)
out[q]['q_rev'] = len(q_rev)
if len(q_rev) > 0 and q.added_at == q_rev[0].revised_at:
out[q]['q_rev'] = 0
out[q]['new_q'] = True
else:
out[q]['new_q'] = False
new_ans = Answer.objects.filter(question=q,added_at__lt=cutoff_time)
new_ans = new_ans.exclude(author=user)
out[q]['new_ans'] = len(new_ans)
ans_rev = AnswerRevision.objects.filter(answer__question=q,revised_at__lt=cutoff_time)
ans_rev = ans_rev.exclude(author=user)
out[q]['ans_rev'] = len(ans_rev)
return out
def __act_count(self,string,number,output):
if number > 0:
output.append(_(string) % {'num':number})
def send_email_alerts(self):
for user in User.objects.all():
q_list = self.get_updated_questions_for_user(user)
num_q = len(q_list)
if num_q > 0:
url_prefix = settings.APP_URL
subject = _('email update message subject')
text = ungettext('%(name)s, this is an update message header for a question',
'%(name)s, this is an update message header for %(num)d questions',num_q) \
% {'num':num_q, 'name':user.username}
text += '<ul>'
for q, act in q_list.items():
act_list = []
if act['new_q']:
act_list.append(_('new question'))
self.__act_count('%(num)d rev', act['q_rev'],act_list)
self.__act_count('%(num)d ans', act['new_ans'],act_list)
self.__act_count('%(num)d ans rev',act['ans_rev'],act_list)
act_token = ', '.join(act_list)
text += '<li><a href="%s?sort=latest">%s</a> <font color="#777777">(%s)</font></li>' \
% (url_prefix + q.get_absolute_url(), q.title, act_token)
text += '</ul>'
link = url_prefix + user.get_profile_url() + '?sort=email_subscriptions'
text += _('go to %(link)s to change frequency of email updates or %(email)s administrator') \
% {'link':link, 'email':settings.ADMINS[0][1]}
msg = EmailMessage(subject, text, settings.DEFAULT_FROM_EMAIL, [user.email])
msg.content_subtype = 'html'
msg.send()
|