3. 缓存数据结构:缓存键设计原理、缓存值存储格式、TTL与失效策略
Kyverno 配置缓存的底层实现基于 Go 标准库 sync.Map 与自定义的 LRU(Least Recently Used)淘汰逻辑。理解缓存的数据结构是巡检命中率与排查故障的前提。本章从键设计、值存储、TTL 与失效三个维度展开。
3.1 缓存键设计原理
缓存键(Key)采用 复合字符串 拼接方式,确保在集群范围内唯一标识一条策略规则与资源的匹配结果。键的生成遵循以下模板:
cacheKey = policyNamespace + "/" + policyName + "/" + ruleName + "/" + resourceGVK + "/" + resourceName
各字段说明:
| 字段 | 来源 | 示例值 | 作用 |
|---|---|---|---|
policyNamespace |
策略所在命名空间(集群策略为空字符串) | kyverno |
区分同名策略在不同命名空间 |
policyName |
策略名称 | require-labels |
定位具体策略 |
ruleName |
策略内规则名称 | check-team-label |
定位规则级别 |
resourceGVK |
资源的 Group/Version/Kind | v1/Pod |
区分不同资源类型 |
resourceName |
资源名称 | nginx-pod-7f8b9 |
区分同名资源在不同命名空间 |
巡检要点: 当缓存命中率异常偏低时,优先检查
resourceGVK 字段是否因 CRD 版本升级导致 GVK 字符串变化(例如 v1beta1 → v1),这会直接导致键不匹配,产生缓存未命中。
3.2 缓存值存储格式
缓存值(Value)是一个结构体,包含策略引擎执行后的完整结果。其核心字段如下:
type CacheEntry struct {
Result bool // 策略是否通过(true=通过,false=拒绝)
Message string // 引擎返回的详细消息
MatchedRules []string // 匹配到的规则名称列表
Timestamp time.Time // 缓存写入时间
TTL time.Duration // 剩余生存时间
ResourceVersion string // 资源对象版本号(用于后续校验)
}
存储格式特点:
- Result + Message:直接缓存策略判定结果,避免重复执行
CEL或JMESPath表达式。 - ResourceVersion:记录缓存生成时的资源版本,用于后续 乐观锁校验。若资源实际版本号与缓存中的版本号不一致,则缓存失效。
- MatchedRules:记录命中哪些规则,便于调试时快速定位。
故障排查案例: 某次巡检发现缓存命中率 100%,但策略执行结果与预期不符。排查发现
ResourceVersion 字段在缓存写入后未被更新,导致旧版本结果被重复使用。解决方案:在资源更新事件中强制清除对应缓存条目。
3.3 TTL 与失效策略
Kyverno 缓存采用 两级失效机制:基于时间的 TTL 失效 + 基于事件的主动失效。
3.3.1 TTL 配置
| 参数 | 默认值 | 说明 |
|---|---|---|
--cacheTTL |
5m(5 分钟) |
缓存条目最大生存时间,超过后自动失效 |
--cacheCleanupInterval |
1m(1 分钟) |
后台清理协程扫描间隔,删除过期条目 |
TTL 从缓存写入时开始计时,到期后条目标记为 “过期”,在下一次清理周期中被删除。过期条目被访问时,Kyverno 会重新执行策略引擎并更新缓存。
3.3.2 事件驱动失效
以下事件会触发缓存条目的 主动失效:
- 资源更新/删除:对应资源的
ResourceVersion变化,缓存条目立即失效。 - 策略更新:策略内容(规则表达式、参数)变更,所有关联该策略的缓存条目失效。
- 命名空间变更:命名空间标签或注解变化,影响策略匹配范围,相关缓存失效。
- 手动清除:通过
kyverno cache clear命令或 API 接口强制清空缓存。
常见陷阱: 当集群中存在大量高频更新的资源(如
ConfigMap 或 Secret)时,事件驱动失效可能导致缓存频繁重建,实际命中率下降。此时应适当增大 --cacheTTL 值(如 15m),并配合 --cacheCleanupInterval 调整清理频率。
3.4 缓存数据结构总览
下图展示了缓存键、值、TTL 与失效策略的整体关系:
3.5 缓存失效流程
下图展示了缓存条目从写入到失效的完整生命周期:
最佳实践: 对于变更频繁的资源(如
Deployment 的 replicas 字段),建议将 --cacheTTL 设置为 1m 以减少过期数据使用时间;对于稳定资源(如 Namespace),可设置为 30m 以提升命中率。