1 from question import Question ,QuestionRevision, QuestionView, AnonymousQuestion, FavoriteQuestion
\r
2 from answer import Answer, AnonymousAnswer, AnswerRevision
\r
3 from tag import Tag, MarkedTag
\r
4 from meta import Vote, Comment, FlaggedItem
\r
5 from user import Activity, AnonymousEmail, EmailFeedSetting, AuthKeyUserAssociation
\r
6 from repute import Badge, Award, Repute
\r
10 # User extend properties
\r
11 QUESTIONS_PER_PAGE_CHOICES = (
\r
17 def user_is_username_taken(cls,username):
\r
19 cls.objects.get(username=username)
\r
21 except cls.MultipleObjectsReturned:
\r
23 except cls.DoesNotExist:
\r
26 def user_get_q_sel_email_feed_frequency(self):
\r
27 #print 'looking for frequency for user %s' % self
\r
29 feed_setting = EmailFeedSetting.objects.get(subscriber=self,feed_type='q_sel')
\r
30 except Exception, e:
\r
31 #print 'have error %s' % e.message
\r
33 #print 'have freq=%s' % feed_setting.frequency
\r
34 return feed_setting.frequency
\r
36 User.add_to_class('is_approved', models.BooleanField(default=False))
\r
37 User.add_to_class('email_isvalid', models.BooleanField(default=False))
\r
38 User.add_to_class('email_key', models.CharField(max_length=32, null=True))
\r
39 User.add_to_class('reputation', models.PositiveIntegerField(default=1))
\r
40 User.add_to_class('gravatar', models.CharField(max_length=32))
\r
42 #User.add_to_class('favorite_questions',
\r
43 # models.ManyToManyField(Question, through=FavoriteQuestion,
\r
44 # related_name='favorited_by'))
\r
46 #User.add_to_class('badges', models.ManyToManyField(Badge, through=Award,
\r
47 # related_name='awarded_to'))
\r
48 User.add_to_class('gold', models.SmallIntegerField(default=0))
\r
49 User.add_to_class('silver', models.SmallIntegerField(default=0))
\r
50 User.add_to_class('bronze', models.SmallIntegerField(default=0))
\r
51 User.add_to_class('questions_per_page',
\r
52 models.SmallIntegerField(choices=QUESTIONS_PER_PAGE_CHOICES, default=10))
\r
53 User.add_to_class('last_seen',
\r
54 models.DateTimeField(default=datetime.datetime.now))
\r
55 User.add_to_class('real_name', models.CharField(max_length=100, blank=True))
\r
56 User.add_to_class('website', models.URLField(max_length=200, blank=True))
\r
57 User.add_to_class('location', models.CharField(max_length=100, blank=True))
\r
58 User.add_to_class('date_of_birth', models.DateField(null=True, blank=True))
\r
59 User.add_to_class('about', models.TextField(blank=True))
\r
60 User.add_to_class('is_username_taken',classmethod(user_is_username_taken))
\r
61 User.add_to_class('get_q_sel_email_feed_frequency',user_get_q_sel_email_feed_frequency)
\r
62 User.add_to_class('hide_ignored_questions', models.BooleanField(default=False))
\r
63 User.add_to_class('tag_filter_setting',
\r
66 choices=TAG_EMAIL_FILTER_CHOICES,
\r
72 tags_updated = django.dispatch.Signal(providing_args=["question"])
\r
73 edit_question_or_answer = django.dispatch.Signal(providing_args=["instance", "modified_by"])
\r
74 delete_post_or_answer = django.dispatch.Signal(providing_args=["instance", "deleted_by"])
\r
75 mark_offensive = django.dispatch.Signal(providing_args=["instance", "mark_by"])
\r
76 user_updated = django.dispatch.Signal(providing_args=["instance", "updated_by"])
\r
77 user_logged_in = django.dispatch.Signal(providing_args=["session"])
\r
80 def get_messages(self):
\r
82 for m in self.message_set.all():
\r
83 messages.append(m.message)
\r
86 def delete_messages(self):
\r
87 self.message_set.all().delete()
\r
89 def get_profile_url(self):
\r
90 """Returns the URL for this User's profile."""
\r
91 return '%s%s/' % (reverse('user', args=[self.id]), slugify(self.username))
\r
93 def get_profile_link(self):
\r
94 profile_link = u'<a href="%s">%s</a>' % (self.get_profile_url(),self.username)
\r
95 logging.debug('in get profile link %s' % profile_link)
\r
96 return mark_safe(profile_link)
\r
98 User.add_to_class('get_profile_url', get_profile_url)
\r
99 User.add_to_class('get_profile_link', get_profile_link)
\r
100 User.add_to_class('get_messages', get_messages)
\r
101 User.add_to_class('delete_messages', delete_messages)
\r
103 def calculate_gravatar_hash(instance, **kwargs):
\r
104 """Calculates a User's gravatar hash from their email address."""
\r
105 if kwargs.get('raw', False):
\r
107 instance.gravatar = hashlib.md5(instance.email).hexdigest()
\r
109 def record_ask_event(instance, created, **kwargs):
\r
111 activity = Activity(user=instance.author, active_at=instance.added_at, content_object=instance, activity_type=TYPE_ACTIVITY_ASK_QUESTION)
\r
114 def record_answer_event(instance, created, **kwargs):
\r
116 activity = Activity(user=instance.author, active_at=instance.added_at, content_object=instance, activity_type=TYPE_ACTIVITY_ANSWER)
\r
119 def record_comment_event(instance, created, **kwargs):
\r
121 from django.contrib.contenttypes.models import ContentType
\r
122 question_type = ContentType.objects.get_for_model(Question)
\r
123 question_type_id = question_type.id
\r
124 if (instance.content_type_id == question_type_id):
\r
125 type = TYPE_ACTIVITY_COMMENT_QUESTION
\r
127 type = TYPE_ACTIVITY_COMMENT_ANSWER
\r
128 activity = Activity(user=instance.user, active_at=instance.added_at, content_object=instance, activity_type=type)
\r
131 def record_revision_question_event(instance, created, **kwargs):
\r
132 if created and instance.revision <> 1:
\r
133 activity = Activity(user=instance.author, active_at=instance.revised_at, content_object=instance, activity_type=TYPE_ACTIVITY_UPDATE_QUESTION)
\r
136 def record_revision_answer_event(instance, created, **kwargs):
\r
137 if created and instance.revision <> 1:
\r
138 activity = Activity(user=instance.author, active_at=instance.revised_at, content_object=instance, activity_type=TYPE_ACTIVITY_UPDATE_ANSWER)
\r
141 def record_award_event(instance, created, **kwargs):
\r
143 After we awarded a badge to user, we need to record this activity and notify user.
\r
144 We also recaculate awarded_count of this badge and user information.
\r
147 activity = Activity(user=instance.user, active_at=instance.awarded_at, content_object=instance,
\r
148 activity_type=TYPE_ACTIVITY_PRIZE)
\r
151 instance.badge.awarded_count += 1
\r
152 instance.badge.save()
\r
154 if instance.badge.type == Badge.GOLD:
\r
155 instance.user.gold += 1
\r
156 if instance.badge.type == Badge.SILVER:
\r
157 instance.user.silver += 1
\r
158 if instance.badge.type == Badge.BRONZE:
\r
159 instance.user.bronze += 1
\r
160 instance.user.save()
\r
162 def notify_award_message(instance, created, **kwargs):
\r
164 Notify users when they have been awarded badges by using Django message.
\r
167 user = instance.user
\r
168 user.message_set.create(message=u"Congratulations, you have received a badge '%s'" % instance.badge.name)
\r
170 def record_answer_accepted(instance, created, **kwargs):
\r
172 when answer is accepted, we record this for question author - who accepted it.
\r
174 if not created and instance.accepted:
\r
175 activity = Activity(user=instance.question.author, active_at=datetime.datetime.now(), \
\r
176 content_object=instance, activity_type=TYPE_ACTIVITY_MARK_ANSWER)
\r
179 def update_last_seen(instance, created, **kwargs):
\r
181 when user has activities, we update 'last_seen' time stamp for him
\r
183 user = instance.user
\r
184 user.last_seen = datetime.datetime.now()
\r
187 def record_vote(instance, created, **kwargs):
\r
189 when user have voted
\r
192 if instance.vote == 1:
\r
193 vote_type = TYPE_ACTIVITY_VOTE_UP
\r
195 vote_type = TYPE_ACTIVITY_VOTE_DOWN
\r
197 activity = Activity(user=instance.user, active_at=instance.voted_at, content_object=instance, activity_type=vote_type)
\r
200 def record_cancel_vote(instance, **kwargs):
\r
202 when user canceled vote, the vote will be deleted.
\r
204 activity = Activity(user=instance.user, active_at=datetime.datetime.now(), content_object=instance, activity_type=TYPE_ACTIVITY_CANCEL_VOTE)
\r
207 def record_delete_question(instance, delete_by, **kwargs):
\r
209 when user deleted the question
\r
211 if instance.__class__ == "Question":
\r
212 activity_type = TYPE_ACTIVITY_DELETE_QUESTION
\r
214 activity_type = TYPE_ACTIVITY_DELETE_ANSWER
\r
216 activity = Activity(user=delete_by, active_at=datetime.datetime.now(), content_object=instance, activity_type=activity_type)
\r
219 def record_mark_offensive(instance, mark_by, **kwargs):
\r
220 activity = Activity(user=mark_by, active_at=datetime.datetime.now(), content_object=instance, activity_type=TYPE_ACTIVITY_MARK_OFFENSIVE)
\r
223 def record_update_tags(question, **kwargs):
\r
225 when user updated tags of the question
\r
227 activity = Activity(user=question.author, active_at=datetime.datetime.now(), content_object=question, activity_type=TYPE_ACTIVITY_UPDATE_TAGS)
\r
230 def record_favorite_question(instance, created, **kwargs):
\r
232 when user add the question in him favorite questions list.
\r
235 activity = Activity(user=instance.user, active_at=datetime.datetime.now(), content_object=instance, activity_type=TYPE_ACTIVITY_FAVORITE)
\r
238 def record_user_full_updated(instance, **kwargs):
\r
239 activity = Activity(user=instance, active_at=datetime.datetime.now(), content_object=instance, activity_type=TYPE_ACTIVITY_USER_FULL_UPDATED)
\r
242 def post_stored_anonymous_content(sender,user,session_key,signal,*args,**kwargs):
\r
243 aq_list = AnonymousQuestion.objects.filter(session_key = session_key)
\r
244 aa_list = AnonymousAnswer.objects.filter(session_key = session_key)
\r
246 if settings.EMAIL_VALIDATION == 'on':#add user to the record
\r
253 #maybe add pending posts message?
\r
254 else: #just publish the questions
\r
260 #signal for User modle save changes
\r
262 pre_save.connect(calculate_gravatar_hash, sender=User)
\r
263 post_save.connect(record_ask_event, sender=Question)
\r
264 post_save.connect(record_answer_event, sender=Answer)
\r
265 post_save.connect(record_comment_event, sender=Comment)
\r
266 post_save.connect(record_revision_question_event, sender=QuestionRevision)
\r
267 post_save.connect(record_revision_answer_event, sender=AnswerRevision)
\r
268 post_save.connect(record_award_event, sender=Award)
\r
269 post_save.connect(notify_award_message, sender=Award)
\r
270 post_save.connect(record_answer_accepted, sender=Answer)
\r
271 post_save.connect(update_last_seen, sender=Activity)
\r
272 post_save.connect(record_vote, sender=Vote)
\r
273 post_delete.connect(record_cancel_vote, sender=Vote)
\r
274 delete_post_or_answer.connect(record_delete_question, sender=Question)
\r
275 delete_post_or_answer.connect(record_delete_question, sender=Answer)
\r
276 mark_offensive.connect(record_mark_offensive, sender=Question)
\r
277 mark_offensive.connect(record_mark_offensive, sender=Answer)
\r
278 tags_updated.connect(record_update_tags, sender=Question)
\r
279 post_save.connect(record_favorite_question, sender=FavoriteQuestion)
\r
280 user_updated.connect(record_user_full_updated, sender=User)
\r
281 user_logged_in.connect(post_stored_anonymous_content)
\r
283 Question = Question
\r
284 QuestionRevision = QuestionRevision
\r
285 QuestionView = QuestionView
\r
286 FavoriteQuestion = FavoriteQuestion
\r
287 AnonymousQuestion = AnonymousQuestion
\r
290 AnswerRevision = AnswerRevision
\r
291 AnonymousAnswer = AnonymousAnswer
\r
296 FlaggedItem = FlaggedItem
\r
297 MarkedTag = MarkedTag
\r
303 Activity = Activity
\r
304 EmailFeedSetting = EmailFeedSetting
\r
305 AnonymousEmail = AnonymousEmail
\r
306 AuthKeyUserAssociation = AuthKeyUserAssociation
\r
310 'QuestionRevision',
\r
312 'FavoriteQuestion',
\r
313 'AnonymousQuestion',
\r
330 'EmailFeedSetting',
\r
332 'AuthKeyUserAssociation',
\r
338 from forum.modules import get_modules_script_classes
\r
340 for k, v in get_modules_script_classes('models', models.Model).items():
\r
341 if not k in __all__:
\r