En utilisant Spring 3.0, j'ai écrit une interface pour cacher à l'application quel moteur de template j'utilisais pour envoyer du courrier. L'interface estJavaMailSenderImpl de Spring lève une exception mais envoie toujours l'email
public interface MailSender {
public void send(String[] to, String from, String subject, String template,
Map<Object, Object> model, boolean isHtml,
Map<String, Resource> attachments,
Map<String, Resource> inline) throws MailException;
}
Ensuite, la mise en œuvre de vitesse est
public class MailSenderVelocity implements MailSender {
private JavaMailSender sender;
private VelocityEngine engine;
@Override
public void send(final String[] to, final String from,
final String subject, final String template,
final Map<Object, Object> model, final boolean isHtml,
final Map<String, Resource> attachments,
final Map<String, Resource> inline)
throws com.engrid.mail.MailException {
try {
// prepare the message to send
MimeMessagePreparator preparator = new MimeMessagePreparator() {
@Override
public void prepare(MimeMessage mimeMessage) throws Exception {
// determine if the message needs to be multipart or not
boolean multipart = (attachments != null && !attachments.isEmpty()) || (inline != null && !inline.isEmpty());
// create the message
MimeMessageHelper helper = new MimeMessageHelper(mimeMessage, multipart);
// populate header fields
helper.setTo(to);
helper.setFrom(from);
helper.setSubject(subject);
// fetch template and merge model
String text = VelocityEngineUtils.mergeTemplateIntoString(engine, template, model);
helper.setText(text, isHtml);
// add inline attachments
if (inline != null) {
for (Entry<String, Resource> entry : inline.entrySet()) {
helper.addInline(entry.getKey(), entry.getValue());
}
}
// add other attachments
if (attachments != null) {
for (Entry<String, Resource> entry : attachments.entrySet()) {
helper.addAttachment(entry.getKey(), entry.getValue());
}
}
}
};
// send the email
this.sender.send(preparator);
} catch(MailException e) {
// error preparing or sending the message
e.printStackTrace();
throw new com.engrid.mail.MailException(e);
}
}
public void setSender(JavaMailSender sender) {
this.sender = sender;
}
public void setEngine(VelocityEngine engine) {
this.engine = engine;
}
}
Être un bon programmeur, je l'ai écrit des scénarios de test pour différents scénarios pour assurer que tout fonctionne correctement. Un de mes affaires est lorsqu'une pièce jointe est spécifiée mais le fichier lui-même n'existe pas, en particulier
@Test(expected=MailException.class)
public void testSend_MissingAttachment() throws IOException, MailException {
// create new object
MailSenderVelocity testSender = new MailSenderVelocity();
testSender.setEngine(engine);
testSender.setSender(sender);
// assign properties
String subject = "testSend_MissingAttachment";
String template = "simple.vm";
Map<Object, Object> model = new HashMap<Object, Object>();
model.put("user", "User");
boolean isHtml = true;
Map<String, Resource> attachments = new HashMap<String, Resource>();
String file = "notext.txt";
attachments.put(file, templateDirectory.createRelative(file));
Map<String, Resource> inline = null;
// send a message -- will fail because it won't find the file to attach
testSender.send(this.to, this.from, subject, template, model, isHtml, attachments, inline);
}
maintenant, les résultats des tests à l'exception attendue jetés
org.springframework.mail.MailSendException: Failed messages: javax.mail.MessagingException: IOException while sending message;
nested exception is:
java.io.FileNotFoundException: class path resource [com/company/mail/template/notext.txt] cannot be opened because it does not exist; message exception details (1) are:
Failed message 1:
javax.mail.MessagingException: IOException while sending message;
nested exception is:
java.io.FileNotFoundException: class path resource [com/company/mail/template/notext.txt] cannot be opened because it does not exist
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:625)
at org.springframework.mail.javamail.JavaMailSenderImpl.doSend(JavaMailSenderImpl.java:416)
at org.springframework.mail.javamail.JavaMailSenderImpl.send(JavaMailSenderImpl.java:340)
at org.springframework.mail.javamail.JavaMailSenderImpl.send(JavaMailSenderImpl.java:355)
at org.springframework.mail.javamail.JavaMailSenderImpl.send(JavaMailSenderImpl.java:344)
at com.company.mail.MailSenderVelocity.send(MailSenderVelocity.java:103)
at com.company.mail.MailSenderVelocity.send(MailSenderVelocity.java:53)
at com.company.mail.MailSenderVelocityTest.testSend_MissingAttachment(MailSenderVelocityTest.java:136)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:48)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:37)
at java.lang.reflect.Method.invoke(Method.java:600)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
at org.junit.internal.runners.statements.ExpectException.evaluate(ExpectException.java:22)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
at org.springframework.test.context.junit4.statements.RunBeforeTestMethodCallbacks.evaluate(RunBeforeTestMethodCallbacks.java:74)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:31)
at org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate(RunAfterTestMethodCallbacks.java:82)
at org.springframework.test.context.junit4.statements.SpringRepeat.evaluate(SpringRepeat.java:72)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild(SpringJUnit4ClassRunner.java:240)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:46)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:180)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:41)
at org.junit.runners.ParentRunner$1.evaluate(ParentRunner.java:173)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
at org.springframework.test.context.junit4.statements.RunBeforeTestClassCallbacks.evaluate(RunBeforeTestClassCallbacks.java:61)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:31)
at org.springframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate(RunAfterTestClassCallbacks.java:70)
at org.junit.runners.ParentRunner.run(ParentRunner.java:220)
at org.springframework.test.context.junit4.SpringJUnit4ClassRunner.run(SpringJUnit4ClassRunner.java:180)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:45)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:460)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:673)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:386)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:196)
Caused by: java.io.FileNotFoundException: class path resource [com/company/mail/template/notext.txt] cannot be opened because it does not exist
at org.springframework.core.io.ClassPathResource.getInputStream(ClassPathResource.java:158)
at org.springframework.mail.javamail.MimeMessageHelper$1.getInputStream(MimeMessageHelper.java:1086)
at javax.activation.DataHandler.writeTo(DataHandler.java:302)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1350)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:845)
at javax.mail.internet.MimeMultipart.writeTo(MimeMultipart.java:361)
at com.sun.mail.handlers.multipart_mixed.writeTo(multipart_mixed.java:85)
at javax.activation.ObjectDataContentHandler.writeTo(DataHandler.java:881)
at javax.activation.DataHandler.writeTo(DataHandler.java:314)
at javax.mail.internet.MimeBodyPart.writeTo(MimeBodyPart.java:1350)
at javax.mail.internet.MimeMessage.writeTo(MimeMessage.java:1683)
at com.sun.mail.smtp.SMTPTransport.sendMessage(SMTPTransport.java:585)
... 38 more
2010-11-11 13:50:30,261
Cependant, un message électronique encore est envoyé au destinataire répertorié à partir de l'expéditeur répertorié. Toutes les autres choses (sujet, corps, etc.) sont vides. Comment arrêter l'envoi de l'e-mail lorsqu'une exception est générée lors de la création de l'e-mail?
Cela a du sens. J'ai changé les boucles dans le préparateur pour avoir une conditionnelle - if (! Entry.getValue(). Exists()) throw new MailException ("pièce jointe [" + entrée.getKey() + "] n'existe pas") ; - avant d'ajouter le fichier et cela fonctionne. Merci pour la suggestion! – LostHisMind