3. Nexus 代理仓库架构:代理仓库与托管仓库的区别、请求流转路径、缓存存储机制
在 Nexus 制品仓库体系中,代理仓库(Proxy Repository)与托管仓库(Hosted Repository)承担着截然不同的职责。理解两者的架构差异、请求流转路径以及缓存存储机制,是优化代理缓存命中率、构建可靠供应链误差预算台账的基础。
3.1 代理仓库与托管仓库的核心区别
下表从存储特性、数据来源、生命周期、典型用途四个维度进行对比:
| 对比维度 | 代理仓库(Proxy) | 托管仓库(Hosted) |
|---|---|---|
| 存储特性 | 本地缓存 + 远程源站引用 | 本地持久化存储 |
| 数据来源 | 从配置的远程源站(如 Maven Central、npmjs.org)按需拉取并缓存 | 由用户或 CI/CD 流水线直接上传(Push) |
| 生命周期 | 受缓存策略(TTL、最大容量、清理规则)控制,可被淘汰 | 由管理员手动删除或保留策略管理,通常长期保存 |
| 典型用途 | 加速外部依赖获取、减少公网带宽消耗、提供离线可用性 | 存储内部发布制品、第三方私有包、构建产物 |
关键认知: 代理仓库不“拥有”制品,它只是远程源站的本地加速副本;托管仓库则拥有制品的完整所有权。这一区别直接决定了缓存命中率在代理仓库中的核心地位。
3.2 请求流转路径:从客户端到缓存命中/未命中
当客户端(如 mvn、npm install、docker pull)向 Nexus 代理仓库发起制品请求时,其内部流转路径遵循一个清晰的决策树。下图展示了完整的请求生命周期:
路径要点: 缓存命中时,请求在 Nexus 内部即完成响应,延迟通常在毫秒级;缓存未命中时,请求需穿透到远程源站,延迟取决于网络状况和源站响应速度,这是误差预算中“代理延迟”的主要来源。
3.3 缓存存储机制:Blob Store 与内容索引
Nexus 的代理缓存并非简单的文件复制,而是基于 Blob Store(二进制大对象存储) 和 内容索引(Content Index) 的双层架构。
3.3.1 Blob Store:物理存储层
- 存储单元: 每个制品(如 JAR、npm 包、Docker 镜像层)被拆分为一个或多个 Blob,存储在文件系统的指定目录中。
- 去重机制: 基于内容的哈希(SHA-1/SHA-256)进行去重,相同内容的制品只存储一份 Blob,节省磁盘空间。
- 存储策略: 支持“软配额”和“硬配额”,当缓存容量达到阈值时触发清理(如 LRU、TTL 过期)。
3.3.2 内容索引:元数据管理层
- 索引内容: 记录制品的坐标(Group/Artifact/Version)、Blob 引用、缓存时间、过期时间、远程源站 URL。
- 查询加速: 客户端请求时,Nexus 首先查询内容索引,若索引中存在且未过期,则直接返回 Blob;否则触发远程拉取。
- 过期标记: 索引中的每条记录都带有
last_verified时间戳,配合maximum age(最大缓存年龄)决定是否重新验证。
下图展示了 Blob Store 与内容索引的协作关系:
缓存失效陷阱: 内容索引中的
last_verified 时间戳是缓存命中率的关键。如果远程源站更新了制品但未更改版本号(如 SNAPSHOT 或 -SNAPSHOT 策略),Nexus 默认不会主动重新验证,除非配置了 maximum age = 0 或启用了 content validation。这会导致“缓存污染”——客户端获取到过时的制品。
3.4 缓存命中率与误差预算的关联
在供应链误差预算台账中,代理缓存命中率直接决定了以下指标:
- 平均请求延迟: 缓存命中时延迟 ≈ 5-20ms;未命中时延迟 ≈ 200-5000ms(取决于远程源站)。
- 带宽消耗: 缓存命中时内网流量;未命中时消耗公网带宽,增加成本。
- 可用性风险: 远程源站故障时,缓存命中率决定离线可用的制品比例。