设置ExpirePolicy后如何从持久化库删数据?CacheEntryExpiredListener未触发
Apache Ignite过期数据同步删除至MongoDB的解决方案
环境
- Apache Ignite v2.13.0(缓存)
- MongoDB v3.6.0(持久化存储)
- Spring Boot(Java)开发
问题
设置过期策略(ExpirePolicy)后,如何从持久化的MongoDB中删除对应的数据?尝试使用CacheEntryExpiredListener但未触发,这是否是正确的解决方式?
解决方案与分析
1. CacheEntryExpiredListener未触发的原因
你的思路方向是对的,但监听器未触发通常是以下几个原因:
- 未正确注册监听器:仅给监听器类加
@Service注解不会自动关联到Ignite缓存,需要通过Ignite配置显式注册。 - 过期清理机制未触发:Ignite默认采用懒加载(访问数据时检查过期)+ 后台定期清理的模式,如果缓存数据未被访问且后台清理任务未执行,不会触发过期事件。
- 监听器配置参数缺失:注册时必须设置
includeExpiredEntries=true,否则监听器无法接收过期事件。
2. 正确的监听器注册方式
在Spring Boot中,需通过IgniteConfiguration或CacheConfiguration完成监听器注册:
@Configuration public class IgniteConfig { @Autowired private CacheRemovalListener cacheRemovalListener; @Bean public Ignite igniteInstance() { IgniteConfiguration cfg = new IgniteConfiguration(); // 配置缓存及过期策略 CacheConfiguration<Long, Metrics> cacheCfg = new CacheConfiguration<>("metricsCache"); cacheCfg.setExpiryPolicyFactory(CreatedExpiryPolicy.factoryOf(new Duration(TimeUnit.MINUTES, 10))); // 注册监听器,关键配置includeExpiredEntries=true cacheCfg.setCacheEntryListenerConfigurations( new CacheEntryListenerConfiguration<>( cacheRemovalListener, null, false, true ) ); cfg.setCacheConfiguration(cacheCfg); return Ignition.start(cfg); } }
3. 完善监听器逻辑(删除MongoDB数据)
在监听器中注入MongoDB操作类,实现过期数据的同步删除:
@Service public class CacheRemovalListener implements CacheEntryExpiredListener<Long, Metrics> { @Autowired private MongoTemplate mongoTemplate; @Override public void onExpired(Iterable<CacheEntryEvent<? extends Long, ? extends Metrics>> events) throws CacheEntryListenerException { for (CacheEntryEvent<? extends Long, ? extends Metrics> event : events) { Long key = event.getKey(); // 删除MongoDB中对应数据 mongoTemplate.remove(Query.query(Criteria.where("id").is(key)), Metrics.class); System.out.println("已删除过期数据,key: " + key); } } }
4. 优化过期清理策略
如果需要依赖后台定期清理,可在Ignite配置中调整清理频率:
cfg.setExpiryPolicyCheckerSpi(new GridCacheExpiryPolicyCheckerSpi() {{ setFrequency(60_000); // 每分钟执行一次过期清理 }});
注意事项
- 分布式环境下,监听器会在数据所在节点触发,需保证各节点的MongoDB客户端均可正常访问数据库。
- 若使用Ignite原生持久化而非自定义MongoDB存储,需调整监听器逻辑与持久层操作的适配方式。
内容的提问来源于stack exchange,提问作者ApachieIgniteNewbie123
相关产品推荐
相关产品推荐

