mirror of
https://github.com/pacnpal/django-anymail.git
synced 2025-12-20 03:41:05 -05:00
Postmark: Update docs and tests for "modular webhooks"
Existing tracking webhook code works fine with updated event payloads. (So older Anymail versions will work, unmodified, with new Postmark webhooks.) Also update older doc links into Postmark docs. Closes #101
This commit is contained in:
@@ -7,7 +7,7 @@ Anymail integrates with the `Postmark`_ transactional email service,
|
||||
using their `HTTP email API`_.
|
||||
|
||||
.. _Postmark: https://postmarkapp.com/
|
||||
.. _HTTP email API: http://developer.postmarkapp.com/developer-api-email.html
|
||||
.. _HTTP email API: https://postmarkapp.com/developer/api/email-api
|
||||
|
||||
|
||||
Settings
|
||||
@@ -80,7 +80,7 @@ Example:
|
||||
messages.)
|
||||
|
||||
|
||||
.. _email API: http://developer.postmarkapp.com/developer-api-email.html
|
||||
.. _email API: https://postmarkapp.com/developer/api/email-api
|
||||
|
||||
|
||||
Limitations and quirks
|
||||
@@ -118,7 +118,7 @@ see :ref:`unsupported-features`.
|
||||
`message.esp_extra = {'TrackLinks': "HtmlOnly"}` to specify a particular option.
|
||||
|
||||
.. _several link-tracking options:
|
||||
http://developer.postmarkapp.com/developer-link-tracking.html
|
||||
https://postmarkapp.com/developer/user-guide/tracking-links#enabling-link-tracking
|
||||
|
||||
**No envelope sender overrides**
|
||||
Postmark does not support overriding :attr:`~anymail.message.AnymailMessage.envelope_sender`
|
||||
@@ -178,19 +178,17 @@ See this `Postmark blog post on templates`_ for more information.
|
||||
Status tracking webhooks
|
||||
------------------------
|
||||
|
||||
If you are using Anymail's normalized :ref:`status tracking <event-tracking>`, enter
|
||||
the url in your `Postmark account settings`_, under Servers > *your server name* >
|
||||
Settings > Outbound > Webhooks. You should enter this same Anymail tracking URL
|
||||
for all of the "Delivery webhook," "Bounce webhook," and "Opens webhook" (if you
|
||||
want to receive all these types of events):
|
||||
If you are using Anymail's normalized :ref:`status tracking <event-tracking>`, set up
|
||||
a webhook in your `Postmark account settings`_, under Servers > *your server name* >
|
||||
Settings > Webhooks. The webhook URL is:
|
||||
|
||||
:samp:`https://{random}:{random}@{yoursite.example.com}/anymail/postmark/tracking/`
|
||||
|
||||
* *random:random* is an :setting:`ANYMAIL_WEBHOOK_SECRET` shared secret
|
||||
* *yoursite.example.com* is your Django site
|
||||
|
||||
Anymail doesn't care about the "include bounce content" and "post only on first open"
|
||||
Postmark webhook settings: whether to use them is your choice.
|
||||
Choose all the event types you want to receive. Anymail doesn't care about the "include
|
||||
messsage content" and "post only on first open" options; whether to use them is your choice.
|
||||
|
||||
If you use multiple Postmark servers, you'll need to repeat entering the webhook
|
||||
settings for each of them.
|
||||
@@ -201,9 +199,11 @@ unsubscribed, subscribed. (Postmark does not support sent--what it calls "proces
|
||||
through webhooks.)
|
||||
|
||||
The event's :attr:`~anymail.signals.AnymailTrackingEvent.esp_event` field will be
|
||||
a `dict` of Postmark `delivery <http://developer.postmarkapp.com/developer-delivery-webhook.html>`_,
|
||||
`bounce <http://developer.postmarkapp.com/developer-bounce-webhook.html>`_,
|
||||
or `open <http://developer.postmarkapp.com/developer-open-webhook.html>`_ webhook data.
|
||||
a `dict` of Postmark `delivery <https://postmarkapp.com/developer/webhooks/delivery-webhook>`_,
|
||||
`bounce <https://postmarkapp.com/developer/webhooks/bounce-webhook>`_,
|
||||
`spam-complaint <https://postmarkapp.com/developer/webhooks/spam-complaint-webhook>`_,
|
||||
`open-tracking <https://postmarkapp.com/developer/webhooks/open-tracking-webhook>`_, or
|
||||
`click <https://postmarkapp.com/developer/webhooks/click-webhook>`_ data.
|
||||
|
||||
.. _Postmark account settings: https://account.postmarkapp.com/servers
|
||||
|
||||
|
||||
@@ -20,14 +20,17 @@ class PostmarkWebhookSecurityTestCase(WebhookTestCase, WebhookBasicAuthTestsMixi
|
||||
class PostmarkDeliveryTestCase(WebhookTestCase):
|
||||
def test_bounce_event(self):
|
||||
raw_event = {
|
||||
"RecordType": "Bounce",
|
||||
"ID": 901542550,
|
||||
"Type": "HardBounce",
|
||||
"TypeCode": 1,
|
||||
"ServerID": 23,
|
||||
"Name": "Hard bounce",
|
||||
"MessageID": "2706ee8a-737c-4285-b032-ccd317af53ed",
|
||||
"Description": "The server was unable to deliver your message (ex: unknown user, mailbox not found).",
|
||||
"Details": "smtp;550 5.1.1 The email account that you tried to reach does not exist.",
|
||||
"Email": "bounce@example.com",
|
||||
"From": "sender@example.com",
|
||||
"BouncedAt": "2016-04-27T16:28:50.3963933-04:00",
|
||||
"DumpAvailable": True,
|
||||
"Inactive": True,
|
||||
@@ -57,6 +60,7 @@ class PostmarkDeliveryTestCase(WebhookTestCase):
|
||||
|
||||
def test_delivered_event(self):
|
||||
raw_event = {
|
||||
"RecordType": "Delivery",
|
||||
"ServerId": 23,
|
||||
"MessageID": "883953f4-6105-42a2-a16a-77a8eac79483",
|
||||
"Recipient": "recipient@example.com",
|
||||
@@ -82,6 +86,7 @@ class PostmarkDeliveryTestCase(WebhookTestCase):
|
||||
|
||||
def test_open_event(self):
|
||||
raw_event = {
|
||||
"RecordType": "Open",
|
||||
"FirstOpen": True,
|
||||
"Client": {"Name": "Gmail", "Company": "Google", "Family": "Gmail"},
|
||||
"OS": {"Name": "unknown", "Company": "unknown", "Family": "unknown"},
|
||||
@@ -112,6 +117,7 @@ class PostmarkDeliveryTestCase(WebhookTestCase):
|
||||
|
||||
def test_click_event(self):
|
||||
raw_event = {
|
||||
"RecordType": "Click",
|
||||
"ClickLocation": "HTML",
|
||||
"Client": {
|
||||
"Name": "Chrome 35.0.1916.153",
|
||||
@@ -158,3 +164,41 @@ class PostmarkDeliveryTestCase(WebhookTestCase):
|
||||
self.assertEqual(event.click_url, "https://example.com/click/me")
|
||||
self.assertEqual(event.tags, ["welcome-email"])
|
||||
self.assertEqual(event.metadata, {})
|
||||
|
||||
def test_spam_event(self):
|
||||
raw_event = {
|
||||
"RecordType": "SpamComplaint",
|
||||
"ID": 901542550,
|
||||
"Type": "SpamComplaint",
|
||||
"TypeCode": 512,
|
||||
"Name": "Spam complaint",
|
||||
"Tag": "Test",
|
||||
"MessageID": "2706ee8a-737c-4285-b032-ccd317af53ed",
|
||||
"ServerID": 1234,
|
||||
"Description": "",
|
||||
"Details": "Test spam complaint details",
|
||||
"Email": "spam@example.com",
|
||||
"From": "sender@example.com",
|
||||
"BouncedAt": "2016-04-27T16:28:50.3963933-04:00",
|
||||
"DumpAvailable": True,
|
||||
"Inactive": True,
|
||||
"CanActivate": False,
|
||||
"Subject": "Postmark event test"
|
||||
}
|
||||
response = self.client.post('/anymail/postmark/tracking/',
|
||||
content_type='application/json', data=json.dumps(raw_event))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
kwargs = self.assert_handler_called_once_with(self.tracking_handler, sender=PostmarkTrackingWebhookView,
|
||||
event=ANY, esp_name='Postmark')
|
||||
event = kwargs['event']
|
||||
self.assertIsInstance(event, AnymailTrackingEvent)
|
||||
self.assertEqual(event.event_type, "complained")
|
||||
self.assertEqual(event.esp_event, raw_event)
|
||||
self.assertEqual(event.timestamp, datetime(2016, 4, 27, 16, 28, 50, microsecond=396393,
|
||||
tzinfo=get_fixed_timezone(-4*60)))
|
||||
self.assertEqual(event.message_id, "2706ee8a-737c-4285-b032-ccd317af53ed")
|
||||
self.assertEqual(event.event_id, "901542550")
|
||||
self.assertEqual(event.recipient, "spam@example.com")
|
||||
self.assertEqual(event.reject_reason, "spam")
|
||||
self.assertEqual(event.description, "")
|
||||
self.assertEqual(event.mta_response, "Test spam complaint details")
|
||||
|
||||
Reference in New Issue
Block a user