案例来自《重学Java设计模式》
本案例是模拟每次小客车摇号通知的场景,如下图(截自《重学Java设计模式》)
这个接口定义了监听事件要执行的方法,后面创建的监听器都会实现这个接口并重写该方法
public interface EventListener < T > { /*** observed do* @param type*/void doEvent ( T type ) ;} 消息监听器,用于监听摇号结果并给用户发送通知结果的消息(此处用日志模拟发送短信)
public class MessageEventListener implements EventListener < LotteryResult > {public static Logger logger = LoggerFactory.getLogger( MessageEventListener.class ) ; @Override public void doEvent ( LotteryResult lotteryResult ) {logger.info ( "给用户 {} 发送通知:{}",lotteryResult.getUid () ,lotteryResult.getMessage ()) ; }} 消息队列监听器,用于监听摇号结果并记录结果(此处用日志模拟发送短信)
public class MQEventListener implements EventListener < LotteryResult > {public static Logger logger = LoggerFactory.getLogger( MQEventListener.class ) ; @Override public void doEvent ( LotteryResult lotteryResult ) {logger.info ( "记录用户 {} 摇号结果:{}",lotteryResult.getUid () ,lotteryResult.getMessage ()) ; }} 这里定义了一个存储监听器的集合listeners以及监听类型的枚举类EventType,并封装了操作监听器的方法:
public class EventManager {Map < Enum < EventType > , List < EventListener >> listeners = new HashMap <>() ; public EventManager ( Enum < EventType > ... operations ) {for ( Enum < EventType > operation : operations ) {this.listeners.put ( operation, new ArrayList <>()) ; }} /*** 事件类型枚举类*/public enum EventType {MQ, Message} /*** 订阅** @param eventType 事件类型* @param listener 监听*/public void subscribe ( Enum < EventType > eventType, EventListener listener ) { /*** 将新订阅的监听器添加进存储不同监听器的map中*/List < EventListener > users = listeners.get ( eventType ) ; users.add ( listener ) ; } /*** 取消订阅** @param eventType 事件类型* @param listener 监听*/public void unsubscribe ( Enum < EventType > eventType, EventListener listener ) {List < EventListener > users = listeners.get ( eventType ) ; users.remove ( listener ) ; } /*** 通知** @param eventType 事件类型* @param lotteryResult 通知结果*/public void notify ( Enum < EventType > eventType, LotteryResult lotteryResult ) {List < EventListener > users = listeners.get ( eventType ) ; for ( EventListener user : users ) {user.doEvent ( lotteryResult ) ; }}} 这个对象封装了返回所需要的信息
@Datapublic class LotteryResult {String uid; String message; Date time; public LotteryResult ( String uid, String message, Date time ) {this.uid = uid; this.message = message; this.time = time; }} 这里依赖了EventManager这个操作监听器的方法类
public abstract class LotteryService {private EventManager eventManager; public LotteryService () {eventManager = new EventManager ( EventManager.EventType.MQ, EventManager.EventType.Message) ; eventManager.subscribe ( EventManager.EventType.MQ, new MQEventListener ()) ; eventManager.subscribe ( EventManager.EventType.Message, new MessageEventListener ()) ; }public LotteryResult draw ( String uid ) {LotteryResult lotteryResult = doDraw ( uid ) ;eventManager.notify ( EventManager.EventType.MQ, lotteryResult ) ; eventManager.notify ( EventManager.EventType.Message, lotteryResult ) ; return lotteryResult; }protected abstract LotteryResult doDraw ( String uid ) ;} 调用当前案例的主线业务逻辑:小客车摇号
package com.aqin.listenerpattern;import java.util.Date;/*** @Description * @Author aqin1012 AQin.* @Date 2022/8/2 1:31 PM* @Version 1.0*/public class LotteryServiceImpl extends LotteryService {MinibusTargetService minibusTargetService = new MinibusTargetService () ; @Override protected LotteryResult doDraw ( String uid ) {String lottery = minibusTargetService.lottery ( uid ) ; return new LotteryResult ( uid, lottery, new Date ()) ; }} 封装了小客车的相关操作
package com.aqin.listenerpattern;/*** @Description * @Author aqin1012 AQin.* @Date 2022/8/2 3:55 PM* @Version 1.0*/public class MinibusTargetService { /*** mock lottery** @param uid* @return */public String lottery ( String uid ) {return Math.abs( uid.hashCode () % 2 ) == 0 ? "中签" : "未中签"; }} 这个示例项目需要添加下依赖
<? xml version="1.0" encoding="UTF-8" ?>< project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd" > < modelVersion > 4.0.0 modelVersion > < groupId > org.example groupId > < artifactId > Desigins artifactId > < version > 1.0-SNAPSHOT version > < properties > < maven.compiler.source > 8 maven.compiler.source > < maven.compiler.target > 8 maven.compiler.target > properties > < dependencies > < dependency > < groupId > org.projectlombok groupId > < artifactId > lombok artifactId > < version > 1.18.0 version > dependency > < dependency > < groupId > org.slf4j groupId > < artifactId > slf4j-api artifactId > < version > 1.7.25 version > dependency > < dependency > < groupId > ch.qos.logback groupId > < artifactId > logback-classic artifactId > < version > 1.2.3 version > dependency > < dependency > < groupId > org.junit.jupiter groupId > < artifactId > junit-jupiter-api artifactId > < version > 5.2.0 version > < scope > test scope > dependency > dependencies > project > package com.aqin.listenerpattern;import lombok.extern.slf4j.Slf4j;/*** @Description * @Author aqin1012 AQin.* @Date 2022/8/2 4:09 PM* @Version 1.0*/@Slf4jpublic class Test {@org.junit.jupiter.api.Test public void test_draw () {LotteryService lotteryService = new LotteryServiceImpl () ; LotteryResult result = lotteryService.draw ( "233444449484441" ) ; System.out.println ( result ) ; }} | 留言与评论(共有 0 条评论) “” |