sklarsa / django-sendgrid-v5

An implementation of Django's EmailBackend compatible with sendgrid-python v5+
MIT License
318 stars 54 forks source link

Configurable Tracking Per Email #98

Closed the5thbeatle closed 2 years ago

the5thbeatle commented 2 years ago

Extending from #58.

Tracking configuration is currently only set globally, and there are seemingly only three boolean flags in the settings module to configure it. There's no way to override or extend the tracking configuration on individual EmailMessage objects out-of-the-box, as SendgridBackend doesn't check the EmailMessage for any tracking settings.

Overriding tracking can be done similarly to the example of subclassing SendgridBackend in #58:

class TrackingSendgridBackend(SendgridBackend):
    def _build_sg_mail(self, msg: EmailMessage) -> dict:
        tracking = getattr(msg, 'tracking_settings', None)
        mail = super()._build_sg_mail(msg)
        if tracking:
            mail['tracking_settings'] = {
                **mail['tracking_settings'],
                **tracking.get(),
            }
        return mail

However, I believe that this is something that could and should be easily handled in SendgridBackend with some changes in _build_sg_mail that shouldn't break existing functionality:

def _build_sg_mail(self, msg: EmailMessage) -> Dict:
    # ...

    if not isinstance(getattr(msg, 'tracking_settings', None), TrackingSettings):
        mail.tracking_settings = TrackingSettings()
    else:
        mail.tracking_settings = msg.tracking_settings

    if mail.tracking_settings.open_tracking is None:
        mail.tracking_settings.open_tracking = OpenTracking(self.track_email)

    if mail.tracking_settings.click_tracking is None:
        mail.tracking_settings.click_tracking = ClickTracking(
            self.track_clicks_html, self.track_clicks_plain
        )

    return mail.get()

This change should allow for setting a Ganalytics object that is not overwritten by _build_sg_mail:

email = EmailMessage(from_email=from, to=to)
ganalytics = Ganalytics(
    enable=True,
    utm_source='my-source',
    utm_campaign='my-campaign',
    utm_medium='my-medium',
)
email.tracking_settings = TrackingSettings(ganalytics=ganalytics)
# ...
email.send()
sklarsa commented 2 years ago

Thank you for the issue! If you have time to make a PR for this feature, I'll gladly review and merge it ASAP. Otherwise, it may be a few weeks before I can write the code myself