news 2026/2/4 2:32:16

【实用工具类】基于 Guava Cache 实现通用 Token 缓存工具类(附完整源码)

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
【实用工具类】基于 Guava Cache 实现通用 Token 缓存工具类(附完整源码)

【实用工具类】基于Guava Cache实现通用Token缓存工具类(附完整源码)

在日常开发中,Token缓存是非常常见的场景——比如接口调用的访问令牌、用户登录态Token、第三方服务的临时凭证等。如果每次使用Token都重新生成/请求,会增加系统开销;而手写缓存又容易出现重复造轮子、边界处理不完整的问题。

今天给大家分享一个基于Guava Cache实现的通用Token缓存工具类,支持泛型、自定义配置、自动刷新、失效监听等核心能力,开箱即用,适配绝大多数Token缓存场景。

一、核心特性

这个TokenCache工具类具备以下核心优势:

  • 泛型支持:适配任意类型的Token(String、自定义对象、整数等),无需重复编写缓存逻辑;
  • 灵活配置:支持自定义缓存最大容量、过期时间、并发级别,满足不同场景需求;
  • 自动刷新:获取Token时若不存在/已过期,自动触发刷新逻辑,无需手动判断;
  • 失效监听:缓存失效时可监听并打印原因,便于问题排查;
  • 便捷操作:封装了存、取、失效、清空、统计等常用方法,调用简单。

二、完整源码

先贴出完整的工具类源码,建议直接收藏备用:

packagecom.dolphin.util;importcom.google.common.cache.Cache;importcom.google.common.cache.CacheBuilder;importcom.google.common.cache.RemovalListener;importjava.util.concurrent.Callable;importjava.util.concurrent.ExecutionException;importjava.util.concurrent.TimeUnit;/** * 支持泛型的Token缓存类,基于Guava Cache实现 * 提供Token的存储、获取、自动刷新和失效等功能 */publicclassTokenCache<T>{// 基于LRU淘汰策略的核心缓存对象privatefinalCache<String,T>tokenCache;// 默认构造函数:最大容量1000,写入后30分钟过期,并发级别16publicTokenCache(){this(1000,1800,TimeUnit.SECONDS,16);}/** * 自定义配置的构造函数 * * @param maxSize 最大缓存数量(LRU淘汰阈值) * @param expireSeconds 过期时间(写入后多久过期) * @param timeUnit 时间单位 * @param concurrencyLevel 并发级别(同时写缓存的线程数) */publicTokenCache(intmaxSize,intexpireSeconds,TimeUnittimeUnit,intconcurrencyLevel){this.tokenCache=CacheBuilder.newBuilder()// LRU核心:缓存达到最大容量时,淘汰最少使用的缓存.maximumSize(maxSize)// 写入后过期(区别于访问后过期),适合Token这类有固定有效期的场景.expireAfterWrite(expireSeconds,timeUnit)// 并发级别:控制缓存分段数,提升多线程读写性能.concurrencyLevel(concurrencyLevel)// 失效监听器:打印失效的Key和原因,便于排查问题.removalListener((RemovalListener<String,T>)notification->System.out.println("Token失效:"+notification.getKey()+",原因:"+notification.getCause())).build();}/** * 存入/更新Token(覆盖式) * @param key 缓存Key(建议按业务规则命名,如user_1_token、api_access_token) * @param token 缓存的Token对象 */publicvoidputToken(Stringkey,Ttoken){tokenCache.put(key,token);}/** * 普通获取Token(不存在/已过期返回null) * @param key 缓存Key * @return 缓存的Token,无则返回null */publicTgetToken(Stringkey){returntokenCache.getIfPresent(key);}/** * 带自动刷新的Token获取 * 若Key不存在/已过期,自动执行refreshLogic生成新Token并缓存 * @param key 缓存Key * @param refreshLogic Token刷新逻辑(Callable接口,支持抛出异常) * @return 最新的Token */publicTgetTokenWithRefresh(Stringkey,Callable<T>refreshLogic){try{returntokenCache.get(key,refreshLogic);}catch(ExecutionExceptione){Throwablecause=e.getCause();// 解包RuntimeException,避免外层捕获冗余异常if(causeinstanceofRuntimeException){throw(RuntimeException)cause;}thrownewRuntimeException("Token刷新失败",cause);}}/** * 强制失效指定Token * @param key 缓存Key */publicvoidinvalidateToken(Stringkey){tokenCache.invalidate(key);}/** * 获取当前缓存大小 * @return 缓存中的有效Key数量 */publiclongsize(){returntokenCache.size();}/** * 清空所有缓存 */publicvoidinvalidateAll(){tokenCache.invalidateAll();}}

三、核心代码解析

1. 依赖说明

该工具类基于Guava Cache实现,需先引入Guava依赖(Maven示例):

<!-- Guava --><dependency><groupId>com.google.guava</groupId><artifactId>guava</artifactId><version>32.1.3-jre</version><!-- 建议使用最新稳定版 --></dependency>

2. 关键设计解析

  • LRU淘汰策略:通过maximumSize设置最大容量,当缓存达到阈值时,自动淘汰最少使用的Token,避免内存溢出;
  • 过期策略:使用expireAfterWrite(写入后过期),适合Token这类“生成后有固定有效期”的场景(若需“访问后过期”,可替换为expireAfterAccess);
  • 泛型设计:类定义TokenCache<T>,使得缓存可以存储任意类型的Token(字符串、自定义Token对象、整数等);
  • 自动刷新getTokenWithRefresh方法结合Callable,实现“懒加载+自动刷新”,无需手动判断Token是否有效;
  • 失效监听removalListener监听缓存失效事件,可扩展为记录日志、发送告警、清理关联数据等。

四、使用示例

下面通过完整示例演示工具类的核心用法:

publicclassTokenCacheExample{publicstaticvoidmain(String[]args){// 1. 创建默认配置的字符串类型Token缓存TokenCache<String>stringCache=newTokenCache<>();// 2. 存储TokenstringCache.putToken("user1_token","abc123456");// 3. 普通获取TokenStringtoken=stringCache.getToken("user1_token");System.out.println("普通获取Token: "+token);// 输出:abc123456// 4. 带自动刷新的获取(Token不存在则执行刷新逻辑)StringnewToken=stringCache.getTokenWithRefresh("user2_token",()->{// 此处可替换为实际的Token生成逻辑(如调用接口获取新Token)return"new_token_"+System.currentTimeMillis();});System.out.println("自动刷新后获取Token: "+newToken);// 输出:new_token_17xxxxxxxxx// 5. 强制失效TokenstringCache.invalidateToken("user1_token");System.out.println("失效后获取Token: "+stringCache.getToken("user1_token"));// 输出:null// 6. 自定义配置的缓存(存储Integer类型,最大容量500,1小时过期,并发级别8)TokenCache<Integer>intCache=newTokenCache<>(500,3600,TimeUnit.SECONDS,8);intCache.putToken("counter",100);System.out.println("整数类型Token: "+intCache.getToken("counter"));// 输出:100// 7. 获取缓存大小System.out.println("缓存大小: "+intCache.size());// 输出:1// 8. 清空所有缓存intCache.invalidateAll();System.out.println("清空后缓存大小: "+intCache.size());// 输出:0}}

五、注意事项与扩展建议

1. 适用场景

该工具类基于本地缓存(Guava Cache),适合单机/低并发场景的Token缓存;若为分布式系统,建议结合Redis实现分布式缓存(可基于该工具类扩展Redis适配层)。

2. 配置优化

  • maximumSize:根据业务场景设置,避免过大导致内存占用过高,过小导致频繁淘汰;
  • expireAfterWrite:建议与Token的实际有效期匹配(如第三方Token有效期1小时,缓存过期时间可设为55分钟,预留刷新时间);
  • concurrencyLevel:默认16,多核CPU场景可适当调大(如32),但不宜过大(会增加分段开销)。

3. 扩展方向

  • 失效监听增强:将System.out.println替换为日志框架(如SLF4J),记录失效详情;
  • 异常处理扩展:针对getTokenWithRefresh的刷新逻辑,增加重试机制;
  • 缓存统计:开启Guava Cache的统计功能(recordStats()),监控缓存命中率、失效次数等;
  • 自定义过期策略:结合业务实现更复杂的过期规则(如不同Key设置不同过期时间)。

六、总结

这个TokenCache工具类封装了Guava Cache的核心能力,通过泛型和便捷的API设计,解决了Token缓存的通用场景需求。代码简洁、易扩展,可直接集成到项目中,减少重复开发成本。

如果你的项目中有Token缓存的需求,不妨试试这个工具类,也欢迎在评论区交流优化建议~


💡 本文源码已亲测可运行,如需更多Guava Cache高级用法,可参考官方文档:Guava Cache官方指南

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!