I want to run unit tests (Junit) on some model classes that typically will send emails confirming that things happened. Is there a mock email server that you can use with unit tests that will let you confirmation that your run tried to send an email without actually sending the emails out?
This seems like it would be a nice to have, just not sure I want to write my own. The app stack for the emailing aspect is Velocity+Spring, so it would be preferable if the test server can be pointed at by simply changing the applicationContext.xml file.
Alternative answer: Dumbster is a fake SMTP server designed for testing against. It's written in Java.
I think the Mock JavaMail project is what you want.
I would take a look to GreenMail which is alive (apparently Dumbster is dead) with a lot of functionality and good examples.
http://www.icegreen.com/greenmail/
I assume you're using Javamail and the problem is that javax.mail.Session
is final and therefore can't be mocked.
Seems like others have suggested you simply define your own 'mail session' interface and create an implementation that uses Javamail. In your tests you then simply inject a mock while in 'real-world-mode' you inject the Javamail implementation.
Both JMock and EasyMock will support all the assertions you might want to make on the message you are sending and you testing is complete.
As an aside, I generally try to avoid any out-of-process calls from within unit tests - it kills you when you're running the test suite frequently, which normally translates into it being run less and that's code base issues start to occur.
You can try JavaMail Mock2 https://github.com/salyh/javamail-mock2
Its primarily focused on IMAP/POP3 but SMTP Mock is also available. Its available in maven central.
Features
- Support imap, imaps, pop3, pop3s, smtp, smtps
- Supported for POP3: cast to POP3Folder, Folder.getUID(Message msg)
- Supported for IMAP: cast to IMAPFolder, cast to UIDFolder, Subfolders, -Folder.getMessagesByUID(...), delete/rename folders, append messages
- Support for SMTP: Mock Transport.send()
- Unsupported for the moment: IMAP extensions like IDLE, CONDSTORE, ... and casts to POP3Message/IMAPMessage, store listeners
Phil Haack has a blog post about unit testing email sending, with a solution he coded around a freeware mail server.
My solution was to wrap the mail server in a class which takes all the config options and has a send()
method. In my tests, I'd mock this class and override send()
with something that saves the current parameters for the assert.
To test that the mail service itself works, send yourself a mail locally. Try hMail if you're on Windows.