Brevo: SendinBlue compatibility

(See previous commit.)

- Maintain deprecated compatibility
  versions on the old names/URLs.
  (Split into separate commit
  to make renamed files more
  obvious.)
This commit is contained in:
Mike Edmunds
2024-03-11 18:51:39 -07:00
parent c7ee59c3ca
commit 948ab2be27
4 changed files with 191 additions and 0 deletions

View File

@@ -0,0 +1,20 @@
import warnings
from ..exceptions import AnymailDeprecationWarning
from .brevo import EmailBackend as BrevoEmailBackend
class EmailBackend(BrevoEmailBackend):
"""
Deprecated compatibility backend for old Brevo name "SendinBlue".
"""
esp_name = "SendinBlue"
def __init__(self, **kwargs):
warnings.warn(
"`anymail.backends.sendinblue.EmailBackend` has been renamed"
" `anymail.backends.brevo.EmailBackend`.",
AnymailDeprecationWarning,
)
super().__init__(**kwargs)

View File

@@ -16,6 +16,10 @@ from .webhooks.postal import PostalInboundWebhookView, PostalTrackingWebhookView
from .webhooks.postmark import PostmarkInboundWebhookView, PostmarkTrackingWebhookView from .webhooks.postmark import PostmarkInboundWebhookView, PostmarkTrackingWebhookView
from .webhooks.resend import ResendTrackingWebhookView from .webhooks.resend import ResendTrackingWebhookView
from .webhooks.sendgrid import SendGridInboundWebhookView, SendGridTrackingWebhookView from .webhooks.sendgrid import SendGridInboundWebhookView, SendGridTrackingWebhookView
from .webhooks.sendinblue import (
SendinBlueInboundWebhookView,
SendinBlueTrackingWebhookView,
)
from .webhooks.sparkpost import ( from .webhooks.sparkpost import (
SparkPostInboundWebhookView, SparkPostInboundWebhookView,
SparkPostTrackingWebhookView, SparkPostTrackingWebhookView,
@@ -68,6 +72,12 @@ urlpatterns = [
SendGridInboundWebhookView.as_view(), SendGridInboundWebhookView.as_view(),
name="sendgrid_inbound_webhook", name="sendgrid_inbound_webhook",
), ),
path(
# Compatibility for old SendinBlue esp_name; use Brevo in new code
"sendinblue/inbound/",
SendinBlueInboundWebhookView.as_view(),
name="sendinblue_inbound_webhook",
),
path( path(
"sparkpost/inbound/", "sparkpost/inbound/",
SparkPostInboundWebhookView.as_view(), SparkPostInboundWebhookView.as_view(),
@@ -118,6 +128,12 @@ urlpatterns = [
SendGridTrackingWebhookView.as_view(), SendGridTrackingWebhookView.as_view(),
name="sendgrid_tracking_webhook", name="sendgrid_tracking_webhook",
), ),
path(
# Compatibility for old SendinBlue esp_name; use Brevo in new code
"sendinblue/tracking/",
SendinBlueTrackingWebhookView.as_view(),
name="sendinblue_tracking_webhook",
),
path( path(
"sparkpost/tracking/", "sparkpost/tracking/",
SparkPostTrackingWebhookView.as_view(), SparkPostTrackingWebhookView.as_view(),

View File

@@ -0,0 +1,38 @@
import warnings
from ..exceptions import AnymailDeprecationWarning
from .brevo import BrevoInboundWebhookView, BrevoTrackingWebhookView
class SendinBlueTrackingWebhookView(BrevoTrackingWebhookView):
"""
Deprecated compatibility tracking webhook for old Brevo name "SendinBlue".
"""
esp_name = "SendinBlue"
def __init__(self, **kwargs):
warnings.warn(
"Anymail's SendinBlue webhook URLs are deprecated."
" Update your Brevo transactional email webhook URL to change"
" 'anymail/sendinblue' to 'anymail/brevo'.",
AnymailDeprecationWarning,
)
super().__init__(**kwargs)
class SendinBlueInboundWebhookView(BrevoInboundWebhookView):
"""
Deprecated compatibility inbound webhook for old Brevo name "SendinBlue".
"""
esp_name = "SendinBlue"
def __init__(self, **kwargs):
warnings.warn(
"Anymail's SendinBlue webhook URLs are deprecated."
" Update your Brevo inbound webhook URL to change"
" 'anymail/sendinblue' to 'anymail/brevo'.",
AnymailDeprecationWarning,
)
super().__init__(**kwargs)

View File

@@ -0,0 +1,117 @@
from unittest.mock import ANY
from django.core.mail import EmailMessage, send_mail
from django.test import ignore_warnings, override_settings, tag
from anymail.exceptions import AnymailConfigurationError, AnymailDeprecationWarning
from anymail.webhooks.sendinblue import (
SendinBlueInboundWebhookView,
SendinBlueTrackingWebhookView,
)
from .mock_requests_backend import RequestsBackendMockAPITestCase
from .webhook_cases import WebhookTestCase
@tag("brevo", "sendinblue")
@override_settings(
EMAIL_BACKEND="anymail.backends.sendinblue.EmailBackend",
ANYMAIL={"SENDINBLUE_API_KEY": "test_api_key"},
)
@ignore_warnings(category=AnymailDeprecationWarning)
class SendinBlueBackendDeprecationTests(RequestsBackendMockAPITestCase):
DEFAULT_RAW_RESPONSE = (
b'{"messageId":"<201801020304.1234567890@smtp-relay.mailin.fr>"}'
)
DEFAULT_STATUS_CODE = 201 # Brevo v3 uses '201 Created' for success (in most cases)
def test_deprecation_warning(self):
message = EmailMessage(
"Subject", "Body", "from@example.com", ["to@example.com"]
)
with self.assertWarnsMessage(
AnymailDeprecationWarning,
"`anymail.backends.sendinblue.EmailBackend` has been renamed"
" `anymail.backends.brevo.EmailBackend`.",
):
message.send()
self.assert_esp_called("https://api.brevo.com/v3/smtp/email")
@override_settings(ANYMAIL={"BREVO_API_KEY": "test_api_key"})
def test_missing_api_key_error_uses_correct_setting_name(self):
# The sendinblue.EmailBackend requires SENDINBLUE_ settings names
with self.assertRaisesMessage(AnymailConfigurationError, "SENDINBLUE_API_KEY"):
send_mail("Subject", "Body", "from@example.com", ["to@example.com"])
@tag("brevo", "sendinblue")
@ignore_warnings(category=AnymailDeprecationWarning)
class SendinBlueTrackingWebhookDeprecationTests(WebhookTestCase):
def test_deprecation_warning(self):
with self.assertWarnsMessage(
AnymailDeprecationWarning,
"Anymail's SendinBlue webhook URLs are deprecated.",
):
response = self.client.post(
"/anymail/sendinblue/tracking/",
content_type="application/json",
data="{}",
)
self.assertEqual(response.status_code, 200)
# Old url uses old names to preserve compatibility:
self.assert_handler_called_once_with(
self.tracking_handler,
sender=SendinBlueTrackingWebhookView, # *not* BrevoTrackingWebhookView
event=ANY,
esp_name="SendinBlue", # *not* "Brevo"
)
def test_misconfigured_inbound(self):
# Uses old esp_name when called on old URL
errmsg = (
"You seem to have set Brevo's *inbound* webhook URL"
" to Anymail's SendinBlue *tracking* webhook URL."
)
with self.assertRaisesMessage(AnymailConfigurationError, errmsg):
self.client.post(
"/anymail/sendinblue/tracking/",
content_type="application/json",
data={"items": []},
)
@tag("brevo", "sendinblue")
@override_settings(ANYMAIL_SENDINBLUE_API_KEY="test-api-key")
@ignore_warnings(category=AnymailDeprecationWarning)
class SendinBlueInboundWebhookDeprecationTests(WebhookTestCase):
def test_deprecation_warning(self):
with self.assertWarnsMessage(
AnymailDeprecationWarning,
"Anymail's SendinBlue webhook URLs are deprecated.",
):
response = self.client.post(
"/anymail/sendinblue/inbound/",
content_type="application/json",
data='{"items":[{}]}',
)
self.assertEqual(response.status_code, 200)
# Old url uses old names to preserve compatibility:
self.assert_handler_called_once_with(
self.inbound_handler,
sender=SendinBlueInboundWebhookView, # *not* BrevoInboundWebhookView
event=ANY,
esp_name="SendinBlue", # *not* "Brevo"
)
def test_misconfigured_tracking(self):
# Uses old esp_name when called on old URL
errmsg = (
"You seem to have set Brevo's *tracking* webhook URL"
" to Anymail's SendinBlue *inbound* webhook URL."
)
with self.assertRaisesMessage(AnymailConfigurationError, errmsg):
self.client.post(
"/anymail/sendinblue/inbound/",
content_type="application/json",
data={"event": "delivered"},
)