昨天遇到这个问题,在项目启动的时候添加一个定时器隔一段时间扫描有没有定时发送的邮件(当然也可以是你自己的业务逻辑),也在网上找了资料,加上自己的修改,终于成功了。所以来做个记录。

1、ServletContextListener

我们需要在web容器启动的时候,就添加自己的业务。那么有没有一个类或接口能监听web容器的生命周期呢?当然是有的,在Servlet API 中有一个 ServletContextListener 接口,它能够监听 ServletContext 对象的生命周期,也就满足我们的要求。

2、WebApplicationContext

ApplicationContext是Spring的核心,Context我们通常解释为上下文环境,我想用“容器”来表述它更容易理解一些,ApplicationContext则是“应用的容器”了;在Web应用中,我们会用到WebApplicationContext,WebApplicationContext继承自ApplicationContext;WebApplicationContext的初始化方式和BeanFactory.ApplicationContext有所区别,因为WebApplicationContext需要ServletContext实例,也就是说它必须拥有Web容器的前提下才能完成启动的工作。

3、Java代码:

 package com.defer.mail.util;

 import java.util.Date;
import java.util.List;
import java.util.Timer;
import java.util.TimerTask;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import org.springframework.web.context.WebApplicationContext;
import org.springframework.web.context.support.WebApplicationContextUtils;
import com.defer.mail.domain.Email;
import com.defer.mail.domain.User;
import com.defer.mail.service.EmailService;
import com.defer.mail.service.UserService;
public class SendEmailTimer implements ServletContextListener{ private Timer timer = null; /**
* @Name: contextInitialized
* @Description:容器初始化
**/
@Override
public void contextInitialized(ServletContextEvent event) {
//通过给spring的WebApplicationContextUtils传入ServletContext的监听对象来获取获取当前的web容器
WebApplicationContext ac = WebApplicationContextUtils.getRequiredWebApplicationContext(event.getServletContext());
//创建定时器
timer = new Timer(true);
System.out.println("定时器已经启动");
//设定每7200秒查询一次是否有定时发送邮件
timer.schedule(new QuerySendEmail(ac), 0, 7200*1000);
System.out.println("已经添加查询任务");
} /**
* ClassName: QuerySendEmail
* @Description: 业务类,继承TimerTask类,添加自己的业务
*/
private static class QuerySendEmail extends TimerTask {
private static boolean isRunning = false;
private WebApplicationContext context = null; public QuerySendEmail(WebApplicationContext context) {
this.context = context;
} @SuppressWarnings("static-access")
@Override
public void run() {
if(!isRunning) {
isRunning = true;
// TODO 自己的业务流程
EmailService emailService = (EmailService) context.getBean("emailServiceImpl");
UserService userService = (UserService) context.getBean("userServiceImpl");
List<Email> emailList = emailService.findNoSendEmail();
if(emailList != null && emailList.size() >0) {
for (Email email : emailList) {
User user = userService.getById(email.getUser().getId());
String fromUser = user.getEmail();
String code = email.getCode();
String topic = email.getTopic();
String content = email.getContent();
String toUser = email.getToUser();
SendEmail sendEmail = new SendEmail();
boolean status = false;
while(status==false) { status = sendEmail.sendEmail(fromUser, toUser, code, topic, content);
if(status) {
email.setStatus("1"); //设置邮件状态为已发送
email.setSendDate(new Date()); //设置发送时间
emailService.update(email);
status = true;
System.out.println("发送成功=========");
} else {
status = false;
System.out.println("发送失败=========");
} }
}
} else {
System.out.println("没有定时邮件");
} isRunning = false;
System.out.println("查询结束");
} else {
System.out.println("上一次查询还未结束");
} } } /**
*
* @Name: contextDestroyed
* @Description:容器销毁
*/
@Override
public void contextDestroyed(ServletContextEvent servletcontextevent) {
// TODO Auto-generated method stub } }

4、虽然该类实现了ServletContextListener接口,如何让spring容器加载的时候能初始化该类中的操作呢?那肯定少不了配置spring的配置文件

 <!-- 用于定时器工作的监听器。配置在spring的ContextLoaderListener之后,因为需要用到spring的容器对象 -->
<listener>
<listener-class>
<!-- 自己的类路径 -->
com.defer.mail.util.SendEmailTimer
</listener-class>
</listener>

5、测试成功

Spring容器初始化的时候如何添加一个定时器?的更多相关文章

  1. spring容器初始化执行某个方法

    在做web项目开发中,尤其是企业级应用开发的时候,往往会在工程启动的时候做许多的前置检查. 比如检查是否使用了我们组禁止使用的Mysql的group_concat函数,如果使用了项目就不能启动,并指出 ...

  2. 当spring 容器初始化完成后执行某个方法

    在做web项目开发中,尤其是企业级应用开发的时候,往往会在工程启动的时候做许多的前置检查. 比如检查是否使用了我们组禁止使用的Mysql的group_concat函数,如果使用了项目就不能启动,并指出 ...

  3. 当spring 容器初始化完成后执行某个方法 防止onApplicationEvent方法被执行两次

    在做web项目开发中,尤其是企业级应用开发的时候,往往会在工程启动的时候做许多的前置检查. 比如检查是否使用了我们组禁止使用的Mysql的group_concat函数,如果使用了项目就不能启动,并指出 ...

  4. 【sping揭秘】3、Spring容器中bean默认是保持一个实例

    Spring容器中bean默认是保持一个实例 这里做一个测试,基础代码 package cn.cutter.start.provider; import org.springframework.con ...

  5. spring容器初始化bean和销毁bean之前进行一些操作的定义方法

    关于在spring  容器初始化 bean 和销毁前所做的操作定义方式有三种:        第一种,通过在xml中定义init-method和destory-method方法        第二种, ...

  6. 【Spring实战】Spring容器初始化完成后执行初始化数据方法

    一.背景知识及需求 在做WEB项目时,经常在项目第一次启动时利用WEB容器的监听.Servlet加载初始化等切入点为数据库准备数据,这些初始化数据是系统开始运行前必须的数据,例如权限组.系统选项.默认 ...

  7. Spring容器初始化数据(数据库)BeanPostProcessor的应用

    1.目的:在Spring启动的时候加载在数据库保存的配置信息,一方面杜绝随意修改,一方面方便管理 2.BeanPostProcessor是Spring提供的一个方法通过implements方式实现 会 ...

  8. ApplicationListener接口,在spring容器初始化后执行的方法

    一.如果我们希望在Spring容器将所有的Bean都初始化完成之后,做一些操作,那么就可以使用ApplicationListener接口,实现ApplicationListener接口中的onAppl ...

  9. Spring容器初始化过程

    一.Spring 容器高层视图 Spring 启动时读取应用程序提供的Bean配置信息,并在Spring容器中生成一份相应的Bean配置注册表,然后根据这张注册表实例化Bean,装配号Bean之间的依 ...

随机推荐

  1. 代理模式和php实现

    代理模式(Proxy Pattern) : 给某一个对象提供一个代 理,并由代理对象控制对原对象的引用.代理模式的英 文叫做Proxy或Surrogate,它是一种对象结构型模式 模式动机: 在某些情 ...

  2. redis源码学习_字典

    redis中字典有以下要点: (1)它就是一个键值对,对于hash冲突的处理采用了头插法的链式存储来解决. (2)对rehash,扩展就是取第一个大于等于used * 2的2 ^ n的数作为新的has ...

  3. 使用 xlue 实现简单 listbox 控件

    基于 XLUE 实现的 listbox 控件 1. 提供增删查接口,将 obj 作为子控件添加到列表: 2. 提供 Attach/Detach 方法,可以将子控件的事件转发出来: 3. 支持滚动条: ...

  4. 如何使用ip端口来浏览自己的网站

    现在做网站的朋友越来越多,域名注册后往往需要进行备案,而在备案期间我们的域名又不能正常打开,在服务器上直接编辑浏览我们的网站有些棘手,思来想去,在我们购买的服务器ip后面加上个端口来达到域名一样的效果 ...

  5. 换个角度剖析iptables防火墙

    这篇文章会尽量以通俗易懂的方式描述iptables的相关概念,请耐心的读完它. 防火墙相关概念 此处先描述一些相关概念. 从逻辑上讲.防火墙可以大体分为主机防火墙和网络防火墙. 主机防火墙:针对于单个 ...

  6. redis-trib构建集群

    https://blog.csdn.net/qq_35946990/article/details/78957618

  7. Android开发 获取当前activity的屏幕截图(转载)

    首先通过下面的函数获取Bitmap格式的屏幕截图: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 pu ...

  8. EasyUI DataGrid 编辑单元格

    如下图: 现改为单击某个单元格只对此单元格进行可编辑 <TABLE>标记添加 onClickCell <table id="dg" class="eas ...

  9. 客户端-服务器端互动比较与原生实例(比较ajax,server-sent event,websocket/netsocket)

    昨日学习了websocket的原生实例,觉得有必要把几种常见的客户端-服务器端无刷新交互形式列举比较: 一.Ajax:客户端决定何时主动向Server端发请求 如:无刷新评论.无刷新更换图片. 主要目 ...

  10. Kmeans原理与实现

    原理 http://www.cnblogs.com/jerrylead/archive/2011/04/06/2006910.html 实现 http://www.cnblogs.com/zjutzz ...