ticket_detail.py 3.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. import os
  2. import bleach
  3. from django.contrib import messages
  4. from django.contrib.auth.mixins import LoginRequiredMixin
  5. from django.db.models import F
  6. from django.shortcuts import redirect
  7. from django.views.generic import DetailView
  8. from tickets.forms import TicketForm
  9. from tickets.models import Attachment, Comment, Event, Ticket
  10. from tickets.utils import UserCanReadTicketMixin
  11. class TicketDetailView(LoginRequiredMixin, UserCanReadTicketMixin, DetailView):
  12. model = Ticket
  13. template_name = 'tickets/ticket_detail.html'
  14. context_object_name = 'ticket'
  15. def get_queryset(self):
  16. queryset = super().get_queryset()
  17. return queryset.select_related("created_by", "assigned_to")
  18. def get_context_data(self, **kwargs):
  19. context = super().get_context_data(**kwargs)
  20. context['form'] = TicketForm(self.request.user, instance=self.object)
  21. context['comment_list'] = Comment.objects.filter(ticket=self.object.pk).order_by("-date").annotate(
  22. author_username=F("author__username"), author_email=F("author__email")
  23. )
  24. context['event_list'] = Event.objects.filter(ticket=self.object.pk).order_by("-date").annotate(
  25. author_username=F("author__username")
  26. )
  27. context['attachments'] = Attachment.objects.filter(ticket=self.object.pk).select_related("added_by")
  28. # List with statuses codes & their names
  29. available_statuses_with_names = []
  30. available_statuses = self.object.get_available_statuses()
  31. if available_statuses:
  32. for status_code in available_statuses:
  33. status_name = Ticket.TICKET_STATUSES_NAMES.get(status_code)
  34. available_statuses_with_names.append([status_code, status_name])
  35. context["available_statuses"] = available_statuses_with_names
  36. return context
  37. def post(self, request, *args, **kwargs):
  38. ticket = self.get_object()
  39. if request.POST.get("ticket-status"):
  40. status = request.POST.get("ticket-status")
  41. if int(status) in ticket.get_available_statuses():
  42. old_status = ticket.status
  43. ticket.status = int(status)
  44. ticket.save()
  45. messages.success(request, f"Status successfully changed.")
  46. Event.objects.create(
  47. author=request.user,
  48. ticket=ticket,
  49. body="Ticket status was changed from "+Ticket.TICKET_STATUSES_NAMES.get(old_status)+" to "+Ticket.TICKET_STATUSES_NAMES.get(int(status))
  50. )
  51. else:
  52. messages.error(request, f"Status change error.")
  53. if request.POST.get("comment-body"):
  54. Comment.objects.create(
  55. author=request.user,
  56. ticket=ticket,
  57. body=bleach.clean(request.POST.get("comment-body"), strip=True)
  58. )
  59. messages.success(request, "Comment posted. Notification email sent to thread participants.")
  60. if request.FILES.get("attachment_file_input"):
  61. uploaded_file = request.FILES.get("attachment_file_input")
  62. name, extension = os.path.splitext(uploaded_file.name)
  63. if uploaded_file.size > 5000000:
  64. messages.error(request, f"File exceeds maximum attachment size.")
  65. elif extension not in [".jpg", ".gif", ".png", ".csv", ".pdf", ".zip", ".txt"]:
  66. messages.error(request, f"This site does not allow upload of {extension} files.")
  67. else:
  68. Attachment.objects.create(ticket=ticket, added_by=request.user, file=uploaded_file)
  69. messages.success(request, f"File attached successfully.")
  70. return redirect("tickets:ticket_detail", pk=ticket.pk)