尧图网络 高端网站定制 · 原创设计
免费咨询热线
400-888-6620
免费获取方案
Caffeine+Redis两级缓存:高并发下的热key与穿透治理实战
上个月我们线上有个服务被一波大促流量打懵了Redis 的 QPS 飙到十几万带宽先撑不住了紧接着就是各种redis command timed out; nested exception is io.lettuce.core.RedisCommandTimeoutException。这个报错让我第一次认真反思Redis 再强也不能把所有热点都压到它一个中间件头上。于是我把 Caffeine 请了回来做成 Caffeine Redis 的两级缓存效果比我预期的还要猛。这篇文章我会把这套方案的完整思路、读写链路、核心代码、踩坑记录和压测数据都摊开讲。如果你也遇到过 Redis 吃力、热 key 拖垮实例、缓存穿透击穿这类问题或者正在犹豫要不要上本地缓存那这篇应该能帮你省不少调研时间。我默认你有一点 Spring Boot 和 Redis 基础但即使只是刚入门跟着思路走也能明白为什么两级缓存是读多写少场景下的标准答案。1. 为什么我最终把 Caffeine 和 Redis 叠在一起用说实话Redis 单机 QPS 能到十万级大部分业务根本到不了它的极限。但真正上了高并发你会发现瓶颈往往不在 Redis 的处理能力而在网络 IO、序列化开销和带宽上。这次事故让我把Redis 万能这个观念彻底丢掉开始认真考虑把 Caffeine 放在前面挡流量。1.1 单用 Redis 的瓶颈网络往返与热 key先算一笔账。我们的服务部署在内网应用到 Redis 的单次网络往返大约 0.2ms 到 0.5ms。看着不多但一个接口往往要读两三个 key一次请求就得 1ms 左右的缓存开销。单机 5000 QPS 时这不算什么但当流量冲到 10 万 QPS光缓存读取就占掉 100 秒的 CPU 时间而且 Redis 侧的网络软中断和带宽占用会先爆。更典型的是热 key 问题。我们当时有个活动首页的 banner 配置几乎每个请求都会读同一个 key。Redis 不管后面挂了多少客户端这个 key 最终都落在一个分片上单分片的网卡打满其他无关请求也跟着超时。这时候你再怎么调连接池都没用因为问题出在单个 key 上。1.2 单用 Caffeine 的边界本地缓存的一致性难题那直接把热点数据全放本地缓存行不行行但你不能全量放。Caffeine 是 JVM 进程内缓存每个应用实例各存一份。有两个硬伤第一多实例之间数据不一致一个实例更新了缓存其他实例还拿着旧值第二本地内存容量有限你不可能把几 GB 的热点数据都塞进堆里。所以单用 Caffeine 适合什么场景呢适合那种允许短时间不一致、单机内存扛得住、热点相对固定的数据比如字典表、配置项、某个爆款商品详情。但如果所有数据都走本地缓存一旦数据更新你就得想办法通知所有实例删缓存复杂度立刻上来了。1.3 两级缓存的分工本地扛热点Redis 管全局把两者叠起来之后思路就顺了Caffeine 在上层负责把最热的流量拦在进程内一个热 key 在每台机器上只存一份请求根本不出应用Redis 在中间层负责跨实例的数据共享和全局缓存一致性数据库在最底层兜底。这套分工的好处很明显。对 Redis 来说热 key 的重复请求被 Caffeine 吸收了一大半单 key 压力骤降对应用来说大部分请求省掉了网络往返延迟直接降一个量级。我从这个方案里最大的体会是Redis 应该是你的分布式缓存层而不是唯一的缓存层把它当中间件用配合本地缓存做分级治理才是高并发下的正确姿势。维度CaffeineL1RedisL2读写性能纳秒级纯内存操作毫秒级含网络往返数据一致性多实例间弱一致全局一致容量上限受 JVM 堆内存限制可扩展支持集群故障影响实例重启后丢失需高可用方案适用数据极热、读多写少、允许短暂不一致全量热点、需跨实例共享2. 两级缓存的读写链路命中流程与失效策略要这么设计架构选好了接下来最关键的就是把读写链路理清楚。两级缓存最怕的就是明明缓存了却老是查不到或者更新了数据缓存还是旧的。我先讲读链路再重点讲写链路里的缓存失效顺序这里面有一个很多人没想明白的坑。2.1 读请求的完整链路读请求的优先级很明确先查 Caffeine再查 Redis最后查数据库。任何一个环节命中了就直接返回不再往下走如果都没有就回源数据库把结果分别回填到 Caffeine 和 Redis。public T T get(String key, ClassT type, SupplierT dbLoader) { // 1. 先查本地缓存 Caffeine Object localValue caffeineCache.getIfPresent(key); if (localValue ! null) { return (T) localValue; } // 2. 再查 Redis Object redisValue redisTemplate.opsForValue().get(key); if (redisValue ! null) { // 回填本地缓存下次直接命中 L1 caffeineCache.put(key, redisValue); return (T) redisValue; } // 3. 两级都没命中回源数据库这里要加锁后面细说 T dbValue dbLoader.get(); if (dbValue ! null) { redisTemplate.opsForValue().set(key, dbValue, ttl, TimeUnit.SECONDS); caffeineCache.put(key, dbValue); } return dbValue; }这个流程看起来简单但有个重要细节Caffeine 的getIfPresent和 Redis 的get都不是原子的多个线程同时拿到 null 就会一起打到数据库。所以真正上线时回源那一步必须加上互斥和锁这个我在第 4 章细讲。另外回填 L1 缓存时要考虑这个 key 到底值不值得放本地如果一个 key 的访问频率很低放本地反而浪费内存。2.2 写请求与缓存失效先删 Redis 还是先删 Caffeine缓存更新我用的还是最经典的 Cache Aside 模式先更新数据库再删除缓存。为什么不直接更新缓存因为并发写的情况下两个请求同时更新数据库和缓存后写库的可能先写缓存导致缓存里是旧数据直接删除更简单下次读的时候再回填天然避免脏缓存。到了两级缓存这里删除顺序就有讲究了。我的顺序是更新数据库 - 删除 Redis 中的 key - 通过 Redis Pub/Sub 广播一条失效消息 - 每个应用实例收到消息后删除本地 Caffeine 中的 key。为什么不先删 Caffeine因为 Caffeine 是本地缓存你删的只是当前这个实例的其他实例还在用旧值。更关键的是如果先删 Caffeine 再删 Redis中间有个时间窗口另一个线程可能从 Redis 读到旧值然后回填到 Caffeine等于白删。先用 Redis 做全局失效再通过广播通知所有实例删本地一致性窗口最小。兜底策略也很重要。我在 Caffeine 上配置了一个较短的写入后过期时间比如 60 秒。这样即使广播消息因为极端情况丢了本地缓存最多也就脏一分钟不会无限期脏下去。这种主动失效 短过期兜底的组合是两级缓存在一致性上的标准解。2.3 一致性窗口有多大很多人纠结两级缓存到底一致不一致。我直接说结论它不是强一致最优情况下也存在几十毫秒到一两秒的延迟窗口。但我们的业务场景是商品信息、活动配置、用户维度读多写少的数据几十到几百毫秒的旧数据完全可接受。如果业务真的要求秒级以内甚至强一致那就不能只靠 Cache Aside 了。得考虑订阅数据库 binlog比如 Canal解析变更事件再通过 MQ 广播给所有实例刷新或删除缓存等于把缓存治理做成了事件驱动。我在这次重构里没有上 Canal因为成本高、链路长但如果你做的是价格、库存这类数据建议一开始就把这套机制设计进去。3. 动手实现两级缓存管理器从代码到序列化的大坑理论聊完直接上代码。我用 Spring Boot 3 Lettuce Caffeine 实现了这套缓存管理器。这一章里最想提醒你的不是缓存的逻辑本身而是序列化配置——我敢说一半以上的 Redis 诡异问题都出在序列化上。3.1 依赖与整体结构dependency groupIdorg.springframework.boot/groupId artifactIdspring-boot-starter-data-redis/artifactId /dependency dependency groupIdcom.github.ben-manes.caffeine/groupId artifactIdcaffeine/artifactId /dependency结构上我拆了三个类Caffeine 配置类、Redis 配置类、两级缓存服务类。重点看配置类因为坑全在这里。3.2 Caffeine 配置大小、过期时间、命中统计Configuration public class CaffeineConfig { Bean public CacheString, Object caffeineCache() { return Caffeine.newBuilder() .maximumSize(10_000) // 最多缓存 1 万个 key .expireAfterWrite(60, TimeUnit.SECONDS) // 写入后 60 秒过期兜底一致性 .recordStats() // 开启命中率统计 .build(); } }这里我要强调三个参数。maximumSize不是越大越好它决定了你会为本地缓存预留多少堆内存我建议按单 key 平均大小估算比如单个对象 10KB1 万 key 大约 100MB没问题。expireAfterWrite是写入后固定过期我刻意没有用expireAfterAccess因为访问过期会导致冷数据一直占坑真正的高频 key 反而可能被挤掉。recordStats必须开不然你根本不知道本地缓存到底帮 Redis 分担了多少流量。3.3 Redis 序列化方案别再用默认的 JdkSerialization这是个大坑。Spring Boot 的RedisTemplate默认用JdkSerializationRedisSerializer存进去的 key 会带\xac\xed\x00\x05t前缀你拿可视化客户端一看满屏乱码根本没法排查。更麻烦的是 value 存的是 Java 序列化二进制其他语言的服务根本读不了。我的配置是key 用StringRedisSerializervalue 用GenericJackson2JsonRedisSerializer。但用 Jackson 序列化 LocalDateTime、LocalDate 会直接报错必须加上JavaTimeModule。Configuration public class RedisConfig { Bean public RedisTemplateString, Object redisTemplate(RedisConnectionFactory factory) { RedisTemplateString, Object template new RedisTemplate(); template.setConnectionFactory(factory); StringRedisSerializer stringSerializer new StringRedisSerializer(); GenericJackson2JsonRedisSerializer jsonSerializer new GenericJackson2JsonRedisSerializer(); template.setKeySerializer(stringSerializer); template.setHashKeySerializer(stringSerializer); template.setValueSerializer(jsonSerializer); template.setHashValueSerializer(jsonSerializer); template.afterPropertiesSet(); return template; } }这里有一个安全风险要提醒GenericJackson2JsonRedisSerializer默认会在 JSON 里写入class字段反序列化时会根据这个字段实例化任意类。如果你的 Redis 可以被外部写入这就是一个反序列化漏洞入口。我在生产环境的做法是自定义 ObjectMapper限定允许的包名白名单或者干脆不用GenericJackson2JsonRedisSerializer而是把 value 统一转成 JSON 字符串自己解析。别嫌麻烦安全这块真出事就是大事。3.4 两级缓存核心方法读取、回填、失效广播读方法我上面给过简化版了这里补上删除和广播的部分。public void delete(String key) { // 先删 Redis保证全局不再读到旧值 redisTemplate.delete(key); // 广播失效消息通知所有实例删除本地 Caffeine redisTemplate.convertAndSend(cache:invalid, key); } EventListener public void onMessage(String key) { // 监听 Redis 频道收到消息后删除本地缓存 caffeineCache.invalidate(key); }这套逻辑核心是Redis 是全局事实源Pub/Sub 是传播通道Caffeine 只做执行者。我遇到过一个细节问题如果删除 key 时这个 key 在 Redis 里本来就不存在广播仍然会发出去Caffeine 也会执行一次无效的 invalidate这个开销可以忽略不用做特殊处理。3.5 Lettuce 连接参数与超时问题再补一个跟 Redis 客户端线程模型相关的配置。如果你的项目用的是默认 Lettuce它底层是 Netty 多路复用一个连接可以并发处理很多请求但它不像 Jedis 那样一个线程一个连接。很多人遇到RedisCommandTimeoutException就拼命调大连接池其实是没用的Lettuce 的线程模型决定了瓶颈往往不在连接数而在超时时间和慢命令。spring: data: redis: timeout: 3s lettuce: pool: max-active: 32 max-idle: 16 min-idle: 8这里有个经验调大连接池之前一定要先看 Redis 服务端的慢日志和 CPU。如果是某个大 key 的DEL或KEYS命令把整个实例卡住了你调大连接池只会让更多请求在等待中堆积。Redis 6.0 以后虽然引入了多线程 IO但命令执行仍然是单线程一个耗时命令照样拖垮全局。关于 Redis 线程 IO 模型你只要记住一句话Redis 的瓶颈从来不是连接数而是慢命令、大 key 和内存。4. 缓存穿透、击穿、雪崩两级缓存下的兜底方案很多文章把缓存穿透、击穿、雪崩并列讲好像三个是平级的问题。实际上它们的发生概率和破坏力完全不同。我用两级缓存之后每个问题的处理方式也不一样这一章把三种情况逐个拆开说。4.1 缓存穿透布隆过滤器与空值缓存穿透是指请求一个根本不存在的 key两级缓存都查不到每次都打到数据库。比如一个恶意用户不断用随机 ID 查询商品详情Redis 和 Caffeine 永远查不到数据库被拖垮。我的处理思路是两层防护。第一层是空值缓存查数据库结果为空时也往 Redis 和 Caffeine 里放一个空值TTL 设置短一些比如 3 分钟。这样同一个不存在的 key 在 3 分钟内不会再打到数据库。注意空值也要限定一个合理的 TTL不然恶意攻击者用无限多个随机 ID 就能把缓存填满。第二层是布隆过滤器。把数据库中存在的商品 ID 全量加载到布隆过滤器里请求过来先判断 ID 是否可能存在如果判断不存在直接返回空连缓存都不查。布隆过滤器的误判率可以通过位数组大小和哈希函数数量控制我一般配置误判率 1%对应每个元素大约 10 bit 的存储开销。4.2 缓存击穿分布式锁 双重检查击穿是指某个热点 key 过期的一瞬间大量并发请求同时回源数据库。这比穿透更难防因为 key 是真的存在只是刚好过期了。两级缓存架构下有一个天然优势Caffeine 的本地缓存是进程内的A 进程的 key 过期不影响 B 进程等于把一次大并发击穿分摊到了每个实例上。但跨实例仍然需要一把分布式锁兜底。public T T getWithLock(String key, ClassT type, SupplierT dbLoader) { Object localValue caffeineCache.getIfPresent(key); if (localValue ! null) { return (T) localValue; } Object redisValue redisTemplate.opsForValue().get(key); if (redisValue ! null) { caffeineCache.put(key, redisValue); return (T) redisValue; } String lockKey lock: key; boolean locked tryLock(lockKey, 3, TimeUnit.SECONDS); if (!locked) { // 没拿到锁短暂休眠后重试走双重检查 Thread.sleep(50); return getWithLock(key, type, dbLoader); } try { // 双重检查可能上一个拿到锁的线程已经回填了缓存 Object cached redisTemplate.opsForValue().get(key); if (cached ! null) { caffeineCache.put(key, cached); return (T) cached; } T dbValue dbLoader.get(); if (dbValue ! null) { redisTemplate.opsForValue().set(key, dbValue, ttl, TimeUnit.SECONDS); caffeineCache.put(key, dbValue); } return dbValue; } finally { unlock(lockKey); } }分布式锁的实现我用的是 Redis 的SET NX EXlk key 一定要带业务维度比如lock:product:123千万别用一把全局锁否则所有 key 的击穿都互相排队。锁的粒度越小系统的并发度越高。4.3 缓存雪崩过期时间打散与多级缓冲雪崩是指大量 key 在同一时间过期或者 Redis 直接不可用导致流量瞬间全部打到数据库。造成雪崩最常见的原因是设置了相同的过期时间比如统一 30 分钟缓存一到期下一波请求全部回源。处理雪崩有三个层次。第一过期时间加随机值比如 30 到 60 分钟之间随机避免大批 key 同时过期。第二利用两级缓存天然的多级缓冲Redis 不可用时Caffeine 还在进程里扛着不会立刻打到数据库。第三Redis 自身的高可用要做好我现在的部署方式是 Docker 起一个主从加哨兵结构主节点挂了能自动切到从节点这块我用 Docker 快速验证过后面再说。# 一个最简的 Redis 主从启动方式仅供参考 docker run -d --name redis-master -p 6379:6379 redis:7 redis-server --appendonly yes docker run -d --name redis-slave -p 6380:6379 redis:7 redis-server --slaveof 172.17.0.2 6379主从本身解决的是Redis 挂了怎么办的问题减少的是雪崩的波及面。它不能解决缓存过期时间设计不合理的问题两者要配合使用。4.4 Redis 故障时的降级与熔断最后还要提一个实战中很容易忽略的点Redis 超时之后你的应用会怎样如果连接池等满了请求全部阻塞在 Redis 调用上那 Redis 挂了等于应用挂了。我做了一个简单的降级Redis 读写统一封装超时后捕获异常直接走 Caffeine 数据库同时记录日志告警。try { Object redisValue redisTemplate.opsForValue().get(key); if (redisValue ! null) { caffeineCache.put(key, redisValue); return (T) redisValue; } } catch (Exception e) { // Redis 不可用降级到本地缓存不打日志风暴 log.warn(Redis 读取失败降级到本地缓存key{}, key); }这个降级策略配合 Caffeine 的短过期能在 Redis 故障时保住大部分热点请求。当然代价是缓存一致性被打破但相比数据库被打垮这是完全值得的取舍。5. 压测数据、参数调优与监控排错经验方案落地后我们做了两轮压测和线上观察。这一章把真实数据、调参过程和几个排查案例都列出来给想抄作业的同学一个参照。5.1 压测数据单 Redis 与两级缓存对比先说压测场景商品详情接口缓存的数据结构是一个包含商品名、价格、库存、描述等字段的 JSON单 key 平均 5KB 左右。压测工具模拟 1000 个并发用户持续 5 分钟数据如下。指标单 Redis 缓存Caffeine Redis 两级缓存平均响应时间24ms5msP99 响应时间68ms11ms单机 QPS约 1.2 万约 4.8 万Redis 读 QPS约 9 千约 1.5 千数据非常直观。Redis 的读请求量下降了接近 85%因为大部分热点请求在 Caffeine 这层就被截住了。P99 从 68ms 降到 11ms用户感知是秒开变成瞬间开这种提升不是靠优化代码能拿到的架构层面的收益就是这么明显。5.2 Caffeine 参数调优给本地缓存划定边界调优的核心是给 Caffeine 划定一个合理的内存边界。我建议根据单 key 平均大小和 JVM 堆情况倒推maximumSize。假设你愿意给本地缓存分配 200MB 堆外或堆内空间单 key 5KB那么maximumSize设 40000 左右就是上限超过这个值会导致频繁 GC 和内存压力。过期时间的选择取决于你对一致性的容忍度。我上线初设的是 30 秒后来发现部分配置类数据更新频率很低改成了 5 分钟命中率明显提升。这里没有标准答案但有个原则允许脏读的时间越长Caffeine 过期时间可以越长缓存命中率越高。我通过recordStats定期看命中率如果 L1 命中率低于 70%说明热点数据放得不够或者过期时间太短。5.3 redis command timed out 的完整排查链路我在开头提到的那次事故排查过程值得完整记录一遍。第一步看报错集中在哪些 key 上——如果集中在同一个 key基本就是热 key如果散落在不同 key看 Redis 服务端指标。第二步看 Redis 的 CPU、内存、带宽和慢日志。我们当时发现 Redis 网卡流量打满 90% 以上慢日志里全是某个大 key 的HGETALL操作一次读取返回了几百 KB。第三步看客户端连接池和超时配置。这里我犯过一个错一开始拼命调大max-active结果 Redis 连接数上去了瞬时负载反而更高超时更多。后来才意识到问题在服务端的大 key 读取而不是连接不够。解决措施分三步走大 key 拆分成多个小 key按字段维度和列表维度拆热点数据上 Caffeine让 Redis 不再反复传输同一个大 key最后才调整 Lettuce 超时时间和连接池参数作为兜底。这套组合拳打完超时告警基本消失了。5.4 可视化排查与缓存治理工具排查 Redis 问题时我强烈建议别再只用命令行。我用的是 Another Redis Desktop Manager 和 RedisInsight主要看四个东西key 的 TTL 分布、内存占用 Top N 的 key、慢日志、命令统计。热 key 探测也可以在可视化客户端里直接看到哪个 key 的 QPS 特别高一目了然。缓存治理不能只靠人肉。我在项目里加了统一的缓存访问入口所有读写都走TwoLevelCacheService这样可以在入口处打点统计每个 key 的访问次数、L1 命中率、L2 命中率。当一个 key 的访问频率持续上升就自动把它标记为热 key后续可以考虑在启动时预热到 Caffeine。这套机制不复杂但对线上问题的发现速度提升明显。5.5 下一步可以往哪个方向扩展这套两级缓存方案目前已经跑了大半年稳定性很好。如果你要继续深挖我建议从三个方向扩展。一是 Redis 高可用和集群化。主从哨兵只解决了故障转移容量和性能遇到天花板时还要上 Cluster。二是缓存治理平台化把热 key 探测、自动预热、大 key 拆分、缓存命中率大盘这些能力做成一个后台系统而不是散落在各个服务里。三是序列化升级如果 Redis 承载的数据量很大且对性能要求更高可以考虑从 JSON 序列化升级到 Protobuf 或 MessagePack体积和解析速度都会有明显提升。最后分享一个我的体会别把 Redis 当万能药也别一看到性能问题就上本地缓存。两级缓存的本质是用有限的内存换取更低的延迟和更高的吞吐它解决的是读多写少场景下的热点问题。如果你的业务写多读少或者数据强一致要求极高这套方案要做很多额外的保障工作。但对我们这种商品详情、配置信息、用户维度的读多写少业务来说Caffeine Redis 的组合确实是性价比最高、见效最快的一套方案。
RELATED

相关推荐

Mesh组网实战:告别单路由死角,全屋Wi-Fi无缝漫游

Mesh组网实战:告别单路由死角,全屋Wi-Fi无缝漫游

你家真的需要Mesh吗?先说结论:如果你家和我一样是套内120平以上、路由器放在客厅、卧室或者书房总有一两个角落信号拉胯,而且你又不想在家里拉明线或者每个房间都手动切换Wi-Fi名称,那Mesh组网基本就是现阶段最省心的全屋Wi-Fi解决…

📅 2026/10/9 7:07:30
C++单元测试实战指南:从框架选型到CI覆盖率落地

C++单元测试实战指南:从框架选型到CI覆盖率落地

做C开发几年之后,你会发现一个特别反直觉的现象:明明越到后期越需要胆大心细,但改起代码来却越来越畏手畏脚。改一个接口,牵一发动全身,编译能过,运行也正常,可你就是不敢确定有没有把某个角落里…

📅 2026/10/9 7:07:30
HubSpot 2026营销现状报告:AI与全旅程增长重塑营销策略

HubSpot 2026营销现状报告:AI与全旅程增长重塑营销策略

1. 报告里的核心信号:增长逻辑已经换了每年 HubSpot 的《营销现状报告》发出来,营销圈都会有一波讨论,今年这份《HubSpot 2026 营销现状报告》尤其值得认真看。它不是简单罗列“哪个渠道流量涨了”“哪个工具更火”,而是一次对营销…

📅 2026/10/9 7:07:30
MORE NEWS

更多资讯

📰

特征级SMOTE应对PHM故障诊断的样本不均衡:从原理到落地

一年多前,我在某装备健康管理项目里做风电机组齿轮箱的故障识别,第一次直面所谓的“类别不平衡不只是数据问题,更是工程问题”。当时我用梯度提升树训练故障诊断模型,正常样本拉了五千多条,齿轮磨损的故障样本反复清洗…

📰

从“还行”到“无可挑剔”:交付质量打磨的完整方法论

1. 从"还行"到"无可挑剔":一场关于标准本身的反思我在这个行业里摸爬滚打了十几年,有一个特别深的感触:大多数时候,我们交付的产品或方案不是"不能用",而是"不够好"。它能用&…

📰

conda多环境管理实战:解决Python版本冲突与依赖混乱

你多半也经历过这种场景:代码在自己笔记本上跑得好好的,换个电脑、换个人、或者隔了一个月再来跑,直接报ImportError,先甩你一脸“ModuleNotFoundError”。查来查去,最后发现是Python版本差了零点几、某个底层库被另一…

📰

四端柔性直流输电Simulink仿真:MMC建模、协调控制与调参实战

最近在梳理四端柔性直流输电系统的仿真模型时,我发现很多同学拿到题目后的第一反应是直接打开 Simulink 开始搭电路,结果不是模型跑不动,就是波形发散到天上去。这里面的核心问题不在于 Simulink 操作本身,而在于对“四端网络”和…

📰

Python Selenium全栈指南:从入门到企业级自动化测试体系

从前只会用driver.find_element().click()点点点,到后来真正扛起一套企业级自动化测试体系,这条路我走了差不多六七年。现在回过头看,市面上讲 Selenium 的文章太多了,但绝大多数要么停留在单点技巧,要么一上来就给你甩…

📰

T3MP3ST MCP 服务器实战指南:用 Model Context Protocol 暴露 security_recon 安全侦察工具

网络安全渗透测试AI Agent多智能体人工智能应用安全代码智能体红蓝对抗 【免费下载链接】T3MP3ST autonomous red teaming platform; multi-agent offensive-security meta-harness 项目地址: https://gitcode.com/gh_mirrors/t3/T3MP3ST 点击查看 免费下载 T3MP3S…

TODAY

今日更新

THIS WEEK

本周精选

THIS MONTH

本月热门

读完文章,想聊聊您的网站?

告诉我们您的行业与需求,资深顾问一对一梳理方案与报价,全程免费。

📞 💬