Skip to content

Commit

Permalink
Add ability to disable sending of queued mails.
Browse files Browse the repository at this point in the history
Fixes #14 for Zope 2.13.
  • Loading branch information
Michael Howitz committed Apr 3, 2019
1 parent 1248076 commit bef9132
Show file tree
Hide file tree
Showing 4 changed files with 83 additions and 2 deletions.
3 changes: 3 additions & 0 deletions CHANGES.txt
Expand Up @@ -4,6 +4,9 @@ Changelog
2.13.3 (unreleased)
-------------------

- Add ability to disable sending of queued mails. Details see README.txt.
(`#14 <https://github.com/zopefoundation/Products.MailHost/issues/14>`_)


2.13.2 (2014-11-02)
-------------------
Expand Down
10 changes: 10 additions & 0 deletions README.txt
Expand Up @@ -12,6 +12,9 @@ Email can optionally be encoded using Base64, Quoted-Printable or UUEncode
encoding (though automatic body encoding will be applied if a character set is
specified).

Usage
-----

MailHost provides integration with the Zope transaction system and optional
support for asynchronous mail delivery. Asynchronous mail delivery is
implemented using a queue and a dedicated thread processing the queue. The
Expand All @@ -21,3 +24,10 @@ manage_restartQueueThread?action=start method through HTTP. There is currently
no possibility to start the thread at Zope startup time.

Supports TLS/SSL encryption (requires Python compiled with SSL support).

Configuration
-------------

To force MailHost to only queue mails without sending them, activate queuing
in the ZMI and set the environment variable ``MAILHOST_QUEUE_ONLY=1``.
This could be helpful in a staging environment where mails should not be sent.
4 changes: 3 additions & 1 deletion src/Products/MailHost/MailHost.py
Expand Up @@ -13,6 +13,7 @@
"""SMTP mail objects
"""
import logging
import os
from os.path import realpath
import re
from cStringIO import StringIO
Expand Down Expand Up @@ -338,7 +339,8 @@ def _send(self, mfrom, mto, messageText, immediate=False):
else:
if self.smtp_queue:
# Start queue processor thread, if necessary
self._startQueueProcessorThread()
if not os.environ.get('MAILHOST_QUEUE_ONLY', False):
self._startQueueProcessorThread()
delivery = QueuedMailDelivery(self.smtp_queue_directory)
else:
delivery = DirectMailDelivery(self._makeMailer())
Expand Down
68 changes: 67 additions & 1 deletion src/Products/MailHost/tests/testMailHost.py
Expand Up @@ -13,8 +13,14 @@
"""MailHost unit tests.
"""

import unittest
from email import message_from_string
import os.path
import shutil
import six
import tempfile
import transaction
import unittest
import zope.sendmail.maildir

from Products.MailHost.MailHost import MailHost
from Products.MailHost.MailHost import MailHostError, _mungeHeaders
Expand Down Expand Up @@ -641,7 +647,67 @@ def testSendMultiPartMixedMessage(self):
self.assertEqual(mailhost.sent, msg)


class QueueingDummyMailHost(MailHost):
"""Dummy mail host implementation which supports queueing."""

meta_type = 'Queueing Dummy Mail Host'

def __init__(self, id, smtp_queue_directory):
self.id = id
self.smtp_queue = True
self.smtp_queue_directory = smtp_queue_directory
self.started_queue_processor_thread = False

def _startQueueProcessorThread(self):
self.started_queue_processor_thread = True


class TestMailHostQueuing(unittest.TestCase):

smtp_queue_directory = None

def _getTargetClass(self):
return QueueingDummyMailHost

def _makeOne(self, *args):
self.tmpdir = tempfile.mkdtemp(suffix='MailHostTests')
self.smtp_queue_directory = os.path.join(self.tmpdir, 'queue')
return self._getTargetClass()(
*args, smtp_queue_directory=self.smtp_queue_directory)

def _callFUT(self):
mh = self._makeOne('MailHost')
mh.send(
'Nice to see you!',
mto='user@example.com',
mfrom='zope@example.com',
subject='Hello world')
transaction.commit()
return mh

def tearDown(self):
super(TestMailHostQueuing, self).tearDown()
shutil.rmtree(self.tmpdir, ignore_errors=True)

def testStartQueueProcessorThread(self):
mh = self._callFUT()
self.assertTrue(mh.started_queue_processor_thread)
md = zope.sendmail.maildir.Maildir(self.smtp_queue_directory)
self.assertEqual(len(list(md)), 1)

def testNotStartQueueProcessorThread(self):
os.environ['MAILHOST_QUEUE_ONLY'] = '1'
try:
mh = self._callFUT()
finally:
del os.environ['MAILHOST_QUEUE_ONLY']
self.assertFalse(mh.started_queue_processor_thread)
md = zope.sendmail.maildir.Maildir(self.smtp_queue_directory)
self.assertEqual(len(list(md)), 1)


def test_suite():
suite = unittest.TestSuite()
suite.addTest(unittest.makeSuite(TestMailHost))
suite.addTest(unittest.makeSuite(TestMailHostQueuing))
return suite

0 comments on commit bef9132

Please sign in to comment.