FileNotFound при отправке почты с вложением через Javamail - PullRequest
0 голосов
/ 24 мая 2019

Я пытаюсь отправить письмо с вложенным файлом с помощью Javamail. Но когда код пытается прочитать содержимое файла, возникает исключение FileNoFound. Странно то, что в режиме отладки я вижу, что он получает файл (переменная MultiPartFile не является empy). Я также использую @Async, так что, возможно, это реальная проблема.

Мой метод sendMail:

@Async("threadPoolTaskExecutor")
    public void sendMail(Context ctx, String dest, String subject, String templateName, MultipartFile attachment)
            throws MessagingException, MailException, IOException {

        MimeMessage mimeMessage = emailSender.createMimeMessage();
        MimeMessageHelper message = new MimeMessageHelper(mimeMessage, true, "UTF-8");
        message.setFrom("test@test.com");
        message.setTo(dest);
        message.setSubject(subject);

        String htmlContent = emailTemplateEngine.process(templateName, ctx);
        message.setText(htmlContent, true); // true = isHtml

        if (attachment != null) {
            InputStreamSource attachmentSource;
            attachmentSource = new ByteArrayResource(attachment.getBytes());
            message.addAttachment(attachment.getOriginalFilename(), attachmentSource);
        }

        emailSender.send(mimeMessage);      

    }

У меня ошибка:

java.io.FileNotFoundException: C:\Users\user\AppData\Local\Temp\tomcat.970471969296194243.8080\work\Tomcat\localhost\ROOT\upload_a28782c3_18d7_4b6b_84b7_2d9e81e9a692_00000007.tmp 
    at java.io.FileInputStream.open0(Native Method)
    at java.io.FileInputStream.open(FileInputStream.java:195)
    at java.io.FileInputStream.<init>(FileInputStream.java:138)
    at org.apache.tomcat.util.http.fileupload.disk.DiskFileItem.getInputStream(DiskFileItem.java:194)
    at org.apache.catalina.core.ApplicationPart.getInputStream(ApplicationPart.java:100)
    at org.springframework.web.multipart.support.StandardMultipartHttpServletRequest$StandardMultipartFile.getBytes(StandardMultipartHttpServletRequest.java:245)
[...]

Редактировать: я попытался удалить @Async, и файл загружен без ошибок. Так что это причина моего исключения FileNotFound ... Так есть ли способ решить эту проблему, потому что я бы очень хотел поставить этот метод на асинхронный. Я не очень разбираюсь в асинхронности и управлении потоками, поэтому, возможно, я просто не могу использовать ее при загрузке файлов (?)

1 Ответ

0 голосов
/ 24 мая 2019

Ваш код не объясняет, что такое emailTemplateEngine. обычно ваш сервер не копирует пользовательские шаблоны по умолчанию. проверьте каталог C:\Users\user\AppData\Local\Temp\tomcat.970471969296194243.8080\work\Tomcat\localhost\ROOT\ это должно быть определено из коробки. Вы можете попробовать использовать freemarker.template.Configuration

private Configuration initialiseFreeMarkerConfiguration() throws IOException, TemplateException {
    FreeMarkerConfigurationFactoryBean factory = new FreeMarkerConfigurationFactoryBean();
    factory.setTemplateLoaderPath("classpath:/ROOT/");
    factory.setPreferFileSystemAccess(false);
    return factory.createConfiguration();
  }

твой код ...

  private final Configuration freeMarkerConfiguration;
// in method
 MimeMessage mimeMessage = emailSender.createMimeMessage();
        MimeMessageHelper message = new MimeMessageHelper(mimeMessage, true, "UTF-8");
        message.setFrom("test@test.com");
        message.setTo(dest);
        message.setSubject(subject);
message.setText(processEmailFromTemplate(model), true);

//attachment logic, use FileSystemResource  instead of ByteArrayResource
if (attachment != null) {
            InputStreamSource attachmentSource;
            FileSystemResource file = new FileSystemResource(new File(attachment));
            message.addAttachment(attachment.getOriginalFilename(), file );
        }

 emailSender.send(mimeMessage); 

метод processEmailFromTemplate() должен сделать что-то вроде этого.

private String processEmailFromTemplate(Map<String, Object> model) throws IOException, TemplateException {
StringBuilder content = new StringBuilder();
content.append(FreeMarkerTemplateUtils.processTemplateIntoString(freeMarkerConfiguration.getTemplate("your template name"), model));
return content.toString();
}

...