Springboot项目中事件的发布和监听

在编写商品模块时用到了事件来完成业务场景,比如有商品表,商品收藏表,购物车商品表,当删除商品时,商品收藏表和购物车商品表中对应的商品也要删除。

首先定义商品删除事件
@Data
@ToString
@AllArgsConstructor
public class GoodsDeletedEvent {
    
    
    private long goodsId; // 商品ID
}
然后定义事件监听器

这里用的是注解@EventListener

	// 订阅商品删除
    // -删除购物车中的商品
    // -删除商品收藏中的商品
    @EventListener
    @Transactional
    public void onDeletedGoods(PayloadApplicationEvent<GoodsDeletedEvent> event) {
    
    
        GoodsDeletedEvent payload = event.getPayload();
        // 清除 用户购物车中已被删除的商品
        List<CartGoods> cartGoods = cartGoodsRepository.findByGoodsId(payload.getGoodsId());
        cartGoodsRepository.deleteInBatch(cartGoods);

        // 清除 商品收藏中已被删除的商品
        List<GoodsCollect> goodsCollects = goodsCollectRepository.findByProductId(String.valueOf(payload.getGoodsId()));
        goodsCollectRepository.deleteInBatch(goodsCollects);
    }
最后在需要的地方发布事件
@Transactional
    public void delete(long id) {
    
    
        if (goodsRepository.existsById(id)) {
    
    
            Goods ab = goodsRepository.getOne(id);
            ab.validate();
            goodsRepository.delete(ab);

            // 发布删除商品事件
            eventPublisher.publishEvent(new GoodsDeletedEvent(ab.getId()));
        } else {
    
    
            throw new RuntimeException("商品不存在");
        }
    }

这样一来,当控制层调用业务层的删除商品方法后,商品收藏和购物车商品中对应的商品也会一并删除。

下面有一个简单demo可以方便理解事件的发布监听应用

定义事件
@Data
@ToString
@AllArgsConstructor
public class DemoUserBeanEvent {
    
    
    //用户名
    private String name;
    //密码
    private String password;
}

因为公司项目都是DDD架构,所以以ApplicationService层代替Service层,不了解的没关系把AppService当做Service就行,代码一样可以直接用的
发布与监听都写在一个AppService中

@Service
@Slf4j
public class DemoUserAppService {
    
    
    /**
     * 事件发布由ApplicationContext对象管控的,发布事件前需要注入ApplicationContext对象调用publishEvent完成事件发布
     */
    @Autowired
    ApplicationContext applicationContext;

    /**
     * 用户注册方法 发布事件
     *
     * @param userBean
     */
    public void register(DemoUserBeanEvent userBean) {
    
    
        log.info("start=====================================================================");
        log.info("业务逻辑...");
        // 发布UserRegisterEvent事件,时间发布是由ApplicationContext对象管控的,
        applicationContext.publishEvent(new DemoUserBeanEvent(userBean.getName(),userBean.getPassword()));
    }

    /**
     * 监听事件
     * @param event
     */
    @EventListener
    public void onRegister(PayloadApplicationEvent<DemoUserBeanEvent> event) {
    
    
        // 获取注册用户对象
        DemoUserBeanEvent payload = event.getPayload();
        // 打印注册用户信息
        log.info("@EventListener注册信息,用户名:"+payload.getName()+",密码:"+payload.getPassword());
    }
}
控制层调用
@RestController
public class DemoUserController {
    
    
    @Autowired
    private DemoUserAppService demoUserAppService;

    @GetMapping("/register")
    public String register(DemoUserBeanEvent demoUserBean) {
    
    
        demoUserAppService.register(demoUserBean);
        return "注册成功!";
    }

}
启动springboot项目后 在浏览器输入 http://localhost:8001/register?name=xxp&password=ltd

在这里插入图片描述
事件的监听也不知道注解的方式,还有其他方式,可以看看别的文章比如这篇:https://blog.csdn.net/hjing123/article/details/89203524

猜你喜欢

转载自blog.csdn.net/Xyouzi/article/details/113646458