posting.py 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157
  1. from django.core.urlresolvers import reverse
  2. from django.shortcuts import redirect
  3. from django.template import RequestContext
  4. from django.utils import timezone
  5. from django.utils.translation import ugettext as _
  6. from misago.acl.utils import ACLError403, ACLError404
  7. from misago.forms import FormLayout
  8. from misago.forums.models import Forum
  9. from misago.markdown import post_markdown
  10. from misago.messages import Message
  11. from misago.threads.forms import PostForm
  12. from misago.threads.models import Thread, Post
  13. from misago.threads.views.base import BaseView
  14. from misago.views import error403, error404
  15. from misago.utils import slugify
  16. class PostingView(BaseView):
  17. def fetch_target(self, kwargs):
  18. if self.mode == 'new_thread':
  19. self.fetch_forum(kwargs)
  20. if self.mode in ('edit_thread', 'new_post', 'new_post_quick'):
  21. self.fetch_thread(kwargs)
  22. def fetch_forum(self, kwargs):
  23. self.forum = Forum.objects.get(pk=kwargs['forum'], type='forum')
  24. self.request.acl.forums.allow_forum_view(self.forum)
  25. self.request.acl.threads.allow_new_threads(self.forum)
  26. self.parents = self.forum.get_ancestors(include_self=True).filter(level__gt=1)
  27. def fetch_thread(self, kwargs):
  28. self.thread = Thread.objects.get(pk=kwargs['thread'])
  29. self.forum = self.thread.forum
  30. self.request.acl.forums.allow_forum_view(self.forum)
  31. self.request.acl.threads.allow_reply(self.thread)
  32. self.parents = self.forum.get_ancestors(include_self=True).filter(level__gt=1)
  33. def get_form(self, bound=False):
  34. if bound:
  35. return PostForm(self.request.POST,request=self.request,mode=self.mode)
  36. return PostForm(request=self.request,mode=self.mode)
  37. def __call__(self, request, **kwargs):
  38. self.request = request
  39. self.forum = None
  40. self.thread = None
  41. self.post = None
  42. self.parents = None
  43. self.mode = kwargs.get('mode')
  44. if self.request.POST.get('quick_reply') and self.mode == 'new_post':
  45. self.mode = 'new_post_quick'
  46. try:
  47. self.fetch_target(kwargs)
  48. if not request.user.is_authenticated():
  49. raise ACLError403(_("Guest, you have to sign-in to post."))
  50. except (Forum.DoesNotExist, Thread.DoesNotExist, Post.DoesNotExist):
  51. return error404(self.request)
  52. except ACLError403 as e:
  53. return error403(request, e.message)
  54. except ACLError404 as e:
  55. return error404(request, e.message)
  56. message = request.messages.get_message('threads')
  57. if request.method == 'POST':
  58. form = self.get_form(True)
  59. if form.is_valid():
  60. # Get or create new thread
  61. if self.mode in ['new_thread', 'edit_thread']:
  62. thread = Thread.objects.create(
  63. forum=self.forum,
  64. name=form.cleaned_data['thread_name'],
  65. slug=slugify(form.cleaned_data['thread_name']),
  66. start=timezone.now(),
  67. last=timezone.now(),
  68. )
  69. else:
  70. thread = self.thread
  71. # Create new message
  72. post = Post.objects.create(
  73. forum=self.forum,
  74. thread=thread,
  75. user=request.user,
  76. user_name=request.user.username,
  77. ip=request.session.get_ip(request),
  78. agent=request.META.get('HTTP_USER_AGENT'),
  79. post=form.cleaned_data['post'],
  80. post_preparsed=post_markdown(request, form.cleaned_data['post']),
  81. date=timezone.now()
  82. )
  83. if self.mode == 'new_thread':
  84. thread.start_post = post
  85. thread.start_poster = request.user
  86. thread.start_poster_name = request.user.username
  87. thread.start_poster_slug = request.user.username_slug
  88. if request.user.rank and request.user.rank.style:
  89. thread.start_poster_style = request.user.rank.style
  90. thread.last = timezone.now()
  91. thread.last_post = post
  92. thread.last_poster = request.user
  93. thread.last_poster_name = request.user.username
  94. thread.last_poster_slug = request.user.username_slug
  95. if request.user.rank and request.user.rank.style:
  96. thread.last_poster_style = request.user.rank.style
  97. if self.mode in ['new_post', 'new_post_quick']:
  98. thread.replies += 1
  99. thread.save(force_update=True)
  100. # Update forum
  101. if self.mode == 'new_thread':
  102. self.forum.threads += 1
  103. self.forum.threads_delta += 1
  104. if self.mode in ['new_post', 'new_post_quick']:
  105. self.forum.posts += 1
  106. self.forum.posts_delta += 1
  107. self.forum.last_thread = thread
  108. self.forum.last_thread_name = thread.name
  109. self.forum.last_thread_slug = thread.slug
  110. self.forum.last_thread_date = thread.last
  111. self.forum.last_poster = thread.last_poster
  112. self.forum.last_poster_name = thread.last_poster_name
  113. self.forum.last_poster_slug = thread.last_poster_slug
  114. self.forum.last_poster_style = thread.last_poster_style
  115. self.forum.save(force_update=True)
  116. # Update user
  117. if self.mode == 'new_thread':
  118. request.user.threads += 1
  119. request.user.posts += 1
  120. request.user.last_post = thread.last
  121. request.user.save(force_update=True)
  122. if self.mode == 'new_thread':
  123. request.messages.set_flash(Message(_("New thread has been posted.")), 'success', 'threads')
  124. return redirect(reverse('thread', kwargs={'thread': thread.pk, 'slug': thread.slug}) + ('#post-%s' % post.pk))
  125. if self.mode in ['new_post', 'new_post_quick']:
  126. request.messages.set_flash(Message(_("Your reply has been posted.")), 'success', 'threads')
  127. return redirect(reverse('thread', kwargs={'thread': self.thread.pk, 'slug': self.thread.slug}) + ('#post-%s' % post.pk))
  128. message = Message(form.non_field_errors()[0], 'error')
  129. else:
  130. form = self.get_form()
  131. return request.theme.render_to_response('threads/posting.html',
  132. {
  133. 'mode': self.mode,
  134. 'forum': self.forum,
  135. 'thread': self.thread,
  136. 'post': self.post,
  137. 'parents': self.parents,
  138. 'message': message,
  139. 'form': FormLayout(form),
  140. },
  141. context_instance=RequestContext(request));