event,listener是观察者模式一种体现。主要作用是接耦,另外强调一点是listener默认是同步的,想异步的话,方法加@Async
。
自定义Listerner和Event
Example(未测试)
自定义事件BookingEvent
package per.java.basic.example.listener.applicationEvent;
import org.springframework.context.ApplicationEvent;
public class BookingEvent extends ApplicationEvent {
private String author;
/**
* Create a new {@code ApplicationEvent}.
*
* @param source the object on which the event initially occurred or with
* which the event is associated (never {@code null})
*/
public BookingEvent(Object source) {
super(source);
}
public BookingEvent(Object source, String author) {
super(source);
this.author = author;
}
public String getAuthor() {
return "author:" + author;
}
}
发布者BookingEventPublisher
package per.java.basic.example.listener.applicationEvent;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.stereotype.Component;
@Component
public class BookingEventPublisher {
@Autowired
private ApplicationContext applicationContext;
public void publishBookingEvent(BookingEvent event) {
applicationContext.publishEvent(event);
}
}
监听器BookingEventsListener
package per.java.basic.example.listener.applicationEvent;
import org.springframework.context.ApplicationListener;
import org.springframework.stereotype.Component;
@Component
public class BookingEventsListener implements ApplicationListener<BookingEvent> {
// 默认是阻塞同步的,如果想异步加此注解
@Async
@Override
public void onApplicationEvent(BookingEvent event) {
System.out.println("onApplicationEvent : " + event.getAuthor());
}
}
内置Listener
监听器通常用于监听 Web 应用程序中对象的创建、销毁等动作的发送,同时对监听的情况作出相应的处理,最常用于统计网站的在线人数、访问量等。
监听器大概分为以下几种:
- ServletContextListener:用来监听 ServletContext 属性的操作,比如新增、修改、删除。
- HttpSessionListener:用来监听 Web 应用种的 Session 对象,通常用于统计在线情况。
- ServletRequestListener:用来监听 Request 对象的属性操作。
例如统计当前在线人数demo如下:
public class MyHttpSessionListener implements HttpSessionListener {
public static AtomicInteger userCount = new AtomicInteger(0);
@Override
public synchronized void sessionCreated(HttpSessionEvent se) {
userCount.getAndIncrement();
se.getSession().getServletContext().setAttribute("sessionCount", userCount.get());
log.info("【在线人数】人数增加为:{}", userCount.get());
//此处可以在ServletContext域对象中为访问量计数,然后传入过滤器的销毁方法
//在销毁方法中调用数据库入库,因为过滤器生命周期与容器一致
}
@Override
public synchronized void sessionDestroyed(HttpSessionEvent se) {
userCount.getAndDecrement();
se.getSession().getServletContext().setAttribute("sessionCount", userCount.get());
log.info("【在线人数】人数减少为:{}", userCount.get());
}
}