Schedule a demo

Testing Mailbox

Mock Mailbox connections to test services that work with email messages, folders, and sending mail.

Note: If you're new to unit testing with Zato, check the tutorial first.

Getting inbox messages

The service:

from zato.server.service import Service

class GetInboxMessages(Service):
    name = 'mail.inbox.get'

    def handle(self):
        conn = self.cloud.ms365.get('ms365.Mail').conn

        with conn.client() as client:
            mailbox = client.impl.mailbox()
            inbox = mailbox.inbox_folder()
            messages = inbox.get_messages()

        self.response.payload = {
            'messages': [{'subject': m['subject'], 'from': m['from']} for m in messages]
        }

The test:

from zato_testing import ServiceTestCase
from myapp.services import GetInboxMessages

class TestGetInboxMessages(ServiceTestCase):

    def test_returns_messages(self):

        self.set_response('ms365.Mail.mailbox', {'id': 'mailbox-123'})
        self.set_response('ms365.Mail.mailbox.inbox_folder', {'id': 'inbox-456'})
        self.set_response('ms365.Mail.mailbox.inbox_folder.get_messages', [
            {'subject': 'Meeting Tomorrow', 'from': 'boss@example.com'},
            {'subject': 'Project Update', 'from': 'colleague@example.com'},
            {'subject': 'Invoice #12345', 'from': 'vendor@external.com'}
        ])

        service = self.invoke(GetInboxMessages)

        messages = service.response.payload['messages']
        self.assertEqual(len(messages), 3)
        self.assertEqual(messages[0]['subject'], 'Meeting Tomorrow')

Sending messages

The service:

class SendMessage(Service):
    name = 'mail.send'
    input = 'to', 'subject', 'body'

    def handle(self):
        conn = self.cloud.ms365.get('ms365.Mail').conn

        with conn.client() as client:
            mailbox = client.impl.mailbox()
            message = mailbox.new_message()
            message.add_recipient(self.request.input.to)
            message.subject = self.request.input.subject
            message.body = self.request.input.body
            result = message.send()

        self.response.payload = {'sent': result}

The test:

class TestSendMessage(ServiceTestCase):

    def test_sends_message(self):

        self.set_response('ms365.Mail.mailbox', {'id': 'mailbox-123'})
        self.set_response('ms365.Mail.mailbox.new_message', {
            'subject': None,
            'body': None
        })
        self.set_response('ms365.Mail.mailbox.new_message.add_recipient', None)
        self.set_response('ms365.Mail.mailbox.new_message.send', True)

        service = self.invoke(SendMessage,
            to='recipient@example.com',
            subject='Test Subject',
            body='Test body content'
        )

        self.assertEqual(service.response.payload['sent'], True)

Getting sent messages

class TestGetSentMessages(ServiceTestCase):

    def test_returns_sent_messages(self):

        self.set_response('ms365.Mail.mailbox', {'id': 'mailbox-123'})
        self.set_response('ms365.Mail.mailbox.sent_folder', {'id': 'sent-789'})
        self.set_response('ms365.Mail.mailbox.sent_folder.get_messages', [
            {'subject': 'Re: Meeting', 'to': 'boss@example.com'},
            {'subject': 'Report Attached', 'to': 'team@example.com'}
        ])

        service = self.invoke(GetSentMessages)

        self.assertEqual(len(service.response.payload['messages']), 2)

Getting mail folders

class TestGetMailFolders(ServiceTestCase):

    def test_returns_folders(self):

        self.set_response('ms365.Mail.mailbox', {'id': 'mailbox-123'})
        self.set_response('ms365.Mail.mailbox.get_folder', {'id': 'archive-folder'})
        self.set_response('ms365.Mail.mailbox.get_folder.get_folders', [
            {'name': '2024', 'id': 'folder-2024'},
            {'name': '2023', 'id': 'folder-2023'},
            {'name': 'Important', 'id': 'folder-important'}
        ])

        service = self.invoke(GetMailFolders)

        self.assertEqual(len(service.response.payload['folders']), 3)

Replying to messages

class TestReplyToMessage(ServiceTestCase):

    def test_replies_to_message(self):

        self.set_response('ms365.Mail.mailbox', {'id': 'mailbox-123'})
        self.set_response('ms365.Mail.mailbox.inbox_folder', {'id': 'inbox-456'})
        self.set_response('ms365.Mail.mailbox.inbox_folder.get_message', {
            'id': 'msg-001',
            'subject': 'Original Message'
        })
        self.set_response('ms365.Mail.mailbox.inbox_folder.get_message.reply', {
            'body': None
        })
        self.set_response('ms365.Mail.mailbox.inbox_folder.get_message.reply.send', True)

        service = self.invoke(ReplyToMessage, message_id='msg-001', body='Thanks!')

        self.assertEqual(service.response.payload['replied'], True)

Saving drafts

class TestSaveDraft(ServiceTestCase):

    def test_saves_draft(self):

        self.set_response('ms365.Mail.mailbox', {'id': 'mailbox-123'})
        self.set_response('ms365.Mail.mailbox.new_message', {
            'object_id': 'draft-999',
            'subject': None,
            'body': None
        })
        self.set_response('ms365.Mail.mailbox.new_message.add_recipient', None)
        self.set_response('ms365.Mail.mailbox.new_message.save_draft', True)

        service = self.invoke(SaveDraftMessage,
            to='recipient@example.com',
            subject='Draft Subject',
            body='Draft body'
        )

        self.assertEqual(service.response.payload['draft_saved'], True)
        self.assertEqual(service.response.payload['message_id'], 'draft-999')

See also