email.py 2.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889
  1. from typing import Optional
  2. from django.conf import settings
  3. from django.contrib.auth import get_user_model
  4. from django.core.mail import EmailMultiAlternatives
  5. from django.template.loader import render_to_string
  6. from django.views.generic.base import ContextMixin
  7. from django.views.generic.detail import SingleObjectMixin
  8. User = get_user_model()
  9. class GlitchTipEmail(ContextMixin):
  10. html_template_name = None
  11. text_template_name = None
  12. subject_template_name = None
  13. def __init__(self, **kwargs):
  14. self.kwargs = kwargs
  15. for key, value in kwargs.items():
  16. setattr(self, key, value)
  17. def get_html_template_name(self):
  18. return self.html_template_name
  19. def get_text_template_name(self):
  20. return self.text_template_name
  21. def get_subject_template_name(self):
  22. return self.subject_template_name
  23. def get_text_content(self, context):
  24. return render_to_string(self.get_text_template_name(), context)
  25. def get_html_content(self, context):
  26. return render_to_string(self.get_html_template_name(), context)
  27. def get_subject_content(self, context):
  28. return render_to_string(self.get_subject_template_name(), context).strip("\n")[
  29. :998
  30. ]
  31. def get_context_data(self, **kwargs):
  32. context = super().get_context_data(**kwargs)
  33. context["base_url"] = settings.GLITCHTIP_URL.geturl()
  34. return context
  35. def _send_email(self, context, to, users=None):
  36. subject = self.get_subject_content(context)
  37. msg = EmailMultiAlternatives(subject, self.get_text_content(context), to=to)
  38. if users:
  39. msg.merge_data = {user.email: {"unique_id": user.id} for user in users}
  40. msg.attach_alternative(self.get_html_content(context), "text/html")
  41. msg.send()
  42. def get_users(self):
  43. return User.objects.none()
  44. def send_users_email(self, users=None):
  45. """
  46. Send email to Django users, will set merge data to avoid exposing email addresses
  47. """
  48. context = self.get_context_data()
  49. if users is None:
  50. users = self.get_users()
  51. to = users.values_list("email", flat=True)
  52. self._send_email(context, to, users)
  53. def send_email(self, email: str):
  54. """Send just one email"""
  55. context = self.get_context_data()
  56. self._send_email(context, [email])
  57. class DetailEmail(SingleObjectMixin, GlitchTipEmail):
  58. def get_email(self):
  59. raise NotImplementedError
  60. def send_users_email(self, users=None):
  61. self.object = self.get_object()
  62. super().send_users_email(users)
  63. def send_email(self, email: Optional[str] = None):
  64. """Send just one email"""
  65. self.object = self.get_object()
  66. context = self.get_context_data()
  67. if email is None:
  68. email = self.get_email()
  69. self._send_email(context, [email])