You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何基于自定义时间戳实现Apache Ignite缓存条目级过期?

Apache Ignite 条目级过期实现方案

你其实记错了,Apache Ignite完全支持条目级过期,针对你这种值中自带过期时间戳的场景,有以下几种落地实现方式:

1. 自定义过期策略(ExpiryPolicy)

Ignite允许为单个缓存条目指定自定义ExpiryPolicy,可以直接基于你值中的时间戳计算过期时间,利用Ignite原生机制自动清理过期条目。

实现示例:

// 定义你的缓存值对象
class CacheValue {
    private Set<Boolean> booleanSet;
    private long expireTimestamp;

    // 构造器、getter/setter 省略
}

// 基于时间戳的自定义过期策略
class TimestampExpiryPolicy implements ExpiryPolicy {
    @Override
    public Duration getExpiryForCreation() {
        return null; // 由自定义逻辑控制过期,此处返回null
    }

    @Override
    public Duration getExpiryForAccess() {
        return Duration.ZERO; // 访问不续期
    }

    @Override
    public Duration getExpiryForUpdate() {
        return Duration.ZERO; // 更新不续期
    }

    @Override
    public Duration getExpiry(CacheEntry<?, ?> entry) {
        CacheValue value = (CacheValue) entry.getValue();
        if (value == null) return Duration.ZERO;
        
        long remainingTime = value.getExpireTimestamp() - System.currentTimeMillis();
        return remainingTime > 0 ? Duration.ofMillis(remainingTime) : Duration.ZERO;
    }
}

// 存入缓存时绑定自定义策略
IgniteCache<String, CacheValue> cache = ignite.getOrCreateCache("myCache");
CacheValue value = new CacheValue(/* 初始化Boolean集合和过期时间戳 */);
cache.put("key1", value, new TimestampExpiryPolicy());

2. 定时扫描清理任务

如果不想依赖Ignite的过期策略,可以用Ignite自带的调度器定期扫描缓存,手动移除过期条目。

实现示例:

Ignite ignite = Ignition.start();
IgniteScheduler scheduler = ignite.scheduler();

// 每分钟执行一次清理任务(可根据需求调整Cron表达式)
scheduler.schedule(() -> {
    IgniteCache<String, CacheValue> cache = ignite.cache("myCache");
    long currentTime = System.currentTimeMillis();

    // 分页扫描缓存,避免大缓存场景下OOM
    ScanQuery<String, CacheValue> scanQuery = new ScanQuery<>();
    scanQuery.setPageSize(1000);

    try (QueryCursor<Cache.Entry<String, CacheValue>> cursor = cache.query(scanQuery)) {
        for (Cache.Entry<String, CacheValue> entry : cursor) {
            if (entry.getValue().getExpireTimestamp() < currentTime) {
                cache.remove(entry.getKey());
            }
        }
    }
}, "0 * * * * ?");

3. 访问时自动校验清理

在获取缓存条目时,先检查时间戳是否过期,若过期则原子性移除并返回空,确保用户不会拿到过期数据。可以用CacheEntryProcessor实现:

实现示例:

class ExpiryCheckProcessor implements CacheEntryProcessor<String, CacheValue, CacheValue> {
    @Override
    public CacheValue process(MutableEntry<String, CacheValue> entry, Object... args) {
        CacheValue value = entry.getValue();
        if (value == null) return null;

        if (value.getExpireTimestamp() < System.currentTimeMillis()) {
            entry.remove();
            return null;
        }
        return value;
    }
}

// 获取条目时自动执行过期校验
CacheValue validValue = cache.invoke("key1", new ExpiryCheckProcessor());

内容的提问来源于stack exchange,提问作者Shreyas Bhandare

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 00:30:07