`
ispring
  • 浏览: 359518 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

Send mail with spring mail support and velocity

阅读更多
One of the requirements on my current project is to send Job Applicants an e-mail when they apply for a position. Since we're using Spring, I figured I'd try out its JavaMail and Velocity support to send this e-mail. Below is a short tutorial for setting up Spring's JavaMail support on a PositionManager class, followed by replacing the e-mail's text with a Velocity template. It's possible there's easier ways to do this, but this is what worked for me.
Step 1: Configure the JavaMailSenderImpl

The first step is to setup a MailSender for the PositionManager. To do this, you need to configure a JavaMailSenderImpl with a host or a session. For a host, it's rather simple. Add the following to your applicationContext.xml file:
<bean id="mailSender" class="org.springframework.mail.javamail.JavaMailSenderImpl">
    <property name="host"><value>localhost</value></property>
    <!-- If you don't want to hardcode "localhost", load it from a mail.properties file
         with PropertyPlaceholderConfigurer -->
</bean>

Optionally, you can also configure it with a Session from JNDI when you're running in a servlet container:
<bean id="mailSession" class="org.springframework.jndi.JndiObjectFactoryBean">
    <property name="jndiName"><value>java:comp/env/mail/Session</value></property>
</bean>

<bean id="mailSender" class="org.springframework.mail.javamail.JavaMailSenderImpl">
    <property name="session"><ref bean="mailSession"/></property>
</bean>

I use the first option for JUnit tests, and the 2nd when running in Tomcat. Thanks to Juergen for showing me how easy the JNDI setup is. ;-)
Step 2: Configure a SimpleMailMessage with default values

Next you can configure a SimpleMailMessage with some default values in your applicationContext.xml file:
<bean id="mailMessage" class="org.springframework.mail.SimpleMailMessage">
    <property name="from"><value><![CDATA[Human Resources <hr@raibledesigns.com>]]></value></property>
    <property name="subject"><value>Your application has been received</value></property>
</bean>

Step 3: Configure dependencies in PositionManagerImpl

Then in traditional Spring-style, you need to add variables and setters to the PositionManagerImpl class:
    private MailSender mailSender;
    private SimpleMailMessage message;

    public void setMailSender(MailSender mailSender) {
        this.mailSender = mailSender;
    }

    public void setMessage(SimpleMailMessage message) {
        this.message = message;
    }

Then configure this class's definition in applicationContext.xml so Spring will inject its dependencies:
<bean id="positionManagerTarget" class="org.appfuse.service.PositionManagerImpl">
    ...
    <property name="mailSender"><ref bean="mailSender"/></property>
    <property name="message"><ref bean="mailMessage"/></property>
    ...
</bean>

Now you should be able to easily send an e-mail in a method of this class:
    // user and position objects looked up...
    SimpleMailMessage msg = new SimpleMailMessage(this.message);
    msg.setTo(user.getFullName() + "<" + user.getEmail() + ">");

    StringBuffer txt = new StringBuffer();
    txt.append("Dear " + user.getFullName() + ",\n\n");
    txt.append("Thank you for application for our ");
    txt.append(position.getName() + " position. You can check ");
    txt.append(" on the status of this position at the URL below.\n\n");
    txt.append("    http://raibledesigns.com/positions/status.jsp\n\n");  // doesn't really exist ;-)
    txt.append("Sincerely, \n\nRaible Designs Human Resources");
    msg.setText(txt.toString());
    try {
        mailSender.send(msg);
    } catch (MailException ex) {
        log.error(ex.getMessage());
    }

The only problem with this is that the e-mail message is hard-coded into our Java code - so let's refactor it to use a Velocity template for the text.
Step 4: Configuring Velocity in applicationContext.xml

The next step is to use Spring's Velocity support classes to configure a VelocityEngine. For this, add the following to your applicationContext.xml file:
<bean id="velocityEngine" class="org.springframework.ui.velocity.VelocityEngineFactoryBean">
    <property name="velocityProperties">
        <props>
            <prop key="resource.loader">class</prop>
            <prop key="class.resource.loader.class">
                org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader
            </prop>
        </props>
    </property>
</bean>

NOTE: You can also use <property name="configLocation">velocity.properties</property> if velocity.properties file is in your classpath. However, my velocity.properties file has a webapp.loader defined in it, and since this depends on javax.servlet.ServletContext, I didn't want to use it in my business logic layer. You could also load velocity.properties with PropertyPlaceholderConfigurer and then refer to ${class.resource.loader.class}.
Step 5: Configure Velocity dependency in PositionManagerImpl

In order to use this nice little velocityEngine you just configured, you'll need to add a variable and setter to PositionManagerImpl:
    private VelocityEngine velocityEngine;

    public void setVelocityEngine(VelocityEngine velocityEngine) {
        this.velocityEngine = velocityEngine;
    }

And configure it's dependency in applicationContext.xml:
<bean id="positionManagerTarget" class="org.appfuse.service.PositionManagerImpl">
    ...
    <property name="velocityEngine"><ref bean="velocityEngine"/></property>
    ...
</bean>

Now you can refactor the text part of the previous e-mail sending logic to use a template.
    Map model = new HashMap();
    model.put("user", user);
    model.put("position", position);

    String result = null;
    try {
        // notificationTemplate.vm must be in your classpath
        result = VelocityEngineUtils.mergeTemplateIntoString(velocityEngine,
                        "notificationTemplate.vm", model);
    } catch (VelocityException e) {
        e.printStackTrace();
    }
    msg.setText(result);

Pretty slick huh? A further configuration option is to use Spring to set the name of the template. If you know of any better ways to do JavaMail and e-mail templates with Spring, or find errors in my code - please let me know.

One thing that seems to wrong with this is that when I run my PositionManagerTest JUnit test - it initializes Velocity a number of times. This is because the PersonManagerImpl is re-initialized each time in my setUp() method. This is a JUnit issue, not a Spring issue. I could probably do something so the PositionManagerImpl is only created once for the entire Test run. Either that, or figure out a way to initialize Velocity for only one test. Hints would be great.

Another issue is that I'd like to use Velocity's DataSourceResourceLoader, but it only accepts a JNDI DataSource name. It'd be nice if there was an alternative version that would allow setting of the DataSource via IoC.
分享到:
评论

相关推荐

    spring-velocity-support-2.3

    标题“spring-velocity-support-2.3”暗示了一个关于Spring框架对Velocity模板引擎支持的特定版本,即2.3版。这个版本可能包含了用于整合Spring和Velocity的各种组件、类库和配置,使得开发者能够利用Velocity的强大...

    Velocity入门教程(Spring集成Velocity)

    Velocity入门教程,语法,Velocity布局,Spring框架集成Velocity

    简单学习使用Spring+Velocity发送邮件

    import org.springframework.context.support.ClassPathXmlApplicationContext; import org.springframework.mail.SimpleMailMessage; import org.springframework.mail.javamail.JavaMailSender; import org.spring...

    spring+velocity发送邮件

    根据提供的信息,我们可以详细探讨如何使用Spring框架结合Velocity模板引擎来实现邮件的自动化发送功能。这一过程涉及到Spring框架的基本配置、Velocity模板引擎的使用以及JavaMail API的应用。 ### Spring框架与...

    spring mvc与velocity整合

    总的来说,Spring MVC与Velocity的整合使得开发者可以利用Spring MVC的强大功能来处理业务逻辑,同时利用Velocity的简洁模板语法来设计前端页面,两者结合提供了高效且易于维护的Web应用解决方案。

    Spring Velocity简单的一个例子(转)

    Spring Velocity是一个将Velocity模板引擎与Spring框架集成的示例,这个例子主要展示了如何在Spring应用中使用Velocity来渲染动态内容。Velocity是一个Java模板引擎,它允许开发者将逻辑和表示分离,使得网页设计...

    SpringBoot1.5以上版本兼容velocity,不降级spring

    2.导入本项目中的org.springframework目录下的velocity支持类,原样copy过去或自己打个jar 3.不想写java类配置就直接@ImportResource({"classpath:velocity.xml"})原来的xml配置 4.其他原来是啥就是啥开工

    spring+velocity+ibatis

    标题“spring+velocity+ibatis”揭示了一个基于Java的Web应用程序开发组合,它结合了Spring框架、Velocity模板引擎和iBatis数据访问层。这个项目可能是为了演示或教学如何有效地集成这三个组件,以便构建一个完整的...

    spring mvc mybatis velocity 示范

    Spring MVC、MyBatis 和 Velocity 是三个在Java Web开发中广泛应用的开源框架。Spring MVC 是Spring框架的一部分,用于构建高效、灵活的Web应用程序。MyBatis 是一个优秀的持久层框架,它支持定制化SQL、存储过程...

    velocity spring jpa hibernate 整合

    在这个项目中,"velocity spring jpa hibernate 整合"涉及到的是四个关键组件:Velocity、Spring、JPA(Java Persistence API)和Hibernate。让我们逐一深入理解这些技术并探讨它们如何协同工作。 1. **Velocity**...

    spring mail

    Spring Mail 是一个在Java应用程序中发送电子邮件的库,它与流行的Spring框架紧密集成,使得邮件发送功能的实现变得更加简单和灵活。Spring Mail 提供了一种优雅的方式来配置和使用JavaMail API,而无需直接处理复杂...

    struts+spring+velocity

    Struts、Spring 和 Velocity 是Java开发中常用的三个框架,它们在构建企业级Web应用程序时起着关键作用。这里我们将深入探讨这些技术的核心概念、如何协同工作以及它们在实际项目中的应用。 **Struts** Struts 是一...

    Spring+SpringMVC+Mybatis+Velocity+Maven demo

    Spring、SpringMVC、Mybatis、Velocity和Maven是Java Web开发中常用的一组技术栈,它们各自在软件开发的不同层面发挥着重要作用。这个压缩包文件的标题和描述表明,它提供了一个集成这些技术的演示项目,下面我们将...

    spring velocity demo

    Spring Velocity Demo是一个示例项目,展示了如何在Spring框架中集成Velocity模板引擎,以实现动态页面渲染。这个项目基于Eclipse IDE构建,利用了Maven作为依赖管理工具,使得开发环境的搭建更为便捷。以下是关于...

    Struts2+Spring+Velocity项目

    Struts2、Spring和Velocity是Java Web开发中的三个重要框架,它们共同构建了一个高效、灵活且可扩展的应用程序架构。让我们深入探讨这三个组件以及如何在项目中整合它们。 **Struts2** 是一个基于MVC(Model-View-...

    spring+mybatis+velocity项目demo

    分享一个spring+mybatis+velocity项目demo,该项目是之前给一个学第学习用的,主要基于springMVC、mybatis、velocity搭建的,使用maven构建,其中zai service层编写了两个简单组件,一个是email发送,一个是认证授权...

    spring boot+mail邮件服务学习demo项目源码

    Spring Mail支持创建复杂的HTML邮件,可以利用Velocity或FreeMarker模板引擎来生成动态内容。 6. **邮件附件** 发送带有附件的邮件也是常见的需求。Spring Mail提供了`MimeMessageHelper`类,允许我们方便地添加...

    struts2+spring+velocity扩展实例V1版本

    Struts2、Spring和Velocity是Java Web开发中的三个重要框架,它们各自负责应用程序的不同层面,协同工作可以构建出高效、可维护的Web应用。在这个"struts2+spring+velocity扩展实例V1版本"中,我们可以看到这三个...

Global site tag (gtag.js) - Google Analytics