2. Harbor 架构概览:核心组件与请求链路分析

在构建制品误差预算台账之前,必须深入理解 Harbor 的内部架构。Harbor 并非一个单体服务,而是由多个独立组件协同工作的分布式系统。本章将拆解其核心组件,并追踪一条完整的镜像拉取请求链路,为后续的延迟分析和门禁优化奠定基础。

2.1 核心组件全景

Harbor 2.x 版本由以下六大核心组件构成,每个组件承担明确的职责边界:

组件名称 核心职责 关键端口/协议 状态依赖
Core API 网关、认证鉴权、项目管理、Webhook、审计日志 8080 (HTTP), 8443 (HTTPS) 依赖 DB、Redis、Registry
Registry 镜像 Blob 与 Manifest 的存储与分发(Docker Distribution) 5000 (HTTP) 依赖存储后端(S3/NFS/MinIO)
Jobservice 异步任务调度:GC、复制、扫描、回收、Webhook 投递 8080 (内部 RPC) 依赖 Redis、Core
ChartMuseum Helm Chart 的存储与版本管理(可选组件) 9999 (HTTP) 依赖存储后端
Trivy / Clair 镜像漏洞扫描引擎(Adapter 模式) 8080 (gRPC/HTTP) 依赖 Jobservice 调度
Nginx / Proxy 统一入口、TLS 终止、路由分发、限流 443 (HTTPS), 80 (HTTP) 前置所有组件
架构要点:Core 是 Harbor 的"大脑",所有管理面请求(UI、CLI、API)都必须经过 Core。Registry 是"肌肉",负责数据面的吞吐。Jobservice 是"神经中枢",处理所有后台异步任务。理解这三者的关系是优化延迟的关键。

2.2 组件交互架构图

下图展示了 Harbor 各组件的逻辑分层与核心交互路径。注意 Proxy 作为统一入口,将管理面请求(/api/、/c/)路由至 Core,将数据面请求(/v2/)路由至 Registry。

Harbor 核心组件交互架构 用户 / Docker CLI / K8s Nginx Proxy (443/80) /api/ /c/ /v2/ (镜像) /chart/ Core (API/认证/项目管理) 端口 8080/8443 Registry (镜像存储分发) 端口 5000 ChartMuseum (Helm) 端口 9999 PostgreSQL / Redis 存储后端 (S3/NFS/MinIO) Jobservice (异步任务) GC/复制/扫描/回收 Trivy / Clair (扫描) 漏洞扫描 Adapter 关键交互说明 管理面请求必须经过 Core 数据面请求直达 Registry

2.3 镜像拉取请求链路深度分析

一次完整的 docker pull 操作,在 Harbor 内部会经历以下 7 个关键阶段。每个阶段都可能成为延迟瓶颈,也是我们建立误差预算台账的监控点。

  1. TLS 握手与路由分发:客户端向 Nginx Proxy 发起 HTTPS 请求,Proxy 根据请求路径前缀(/v2/)将流量转发至 Registry。
  2. 认证(Bearer ):Registry 返回 401 Unauthorized,携带 Www-Authenticate 头指向 Core 的 服务。客户端向 Core 请求 ,Core 验证用户凭证并签发短期 。
  3. Manifest 拉取:客户端使用 向 Registry 请求镜像 Manifest(GET /v2/<name>/manifests/<ref>)。Registry 从存储后端读取 Manifest 并返回。
  4. Blob 层列表解析:客户端解析 Manifest,获取所有 Layer Blob 的 Digest 列表。
  5. Blob 并发拉取:客户端并发向 Registry 发起 GET /v2/<name>/blobs/<digest> 请求。Registry 从存储后端读取 Blob 数据流。
  6. 存储后端 I/O:Registry 与后端存储(S3、NFS、MinIO)交互,读取实际数据。此阶段是延迟的主要来源。
  7. 数据流返回:Registry 将 Blob 数据流式传输回客户端,客户端逐层解压并写入本地文件系统。
延迟关键洞察:在误差预算台账中,我们重点关注 阶段 5(Blob 并发拉取) 和 阶段 6(存储后端 I/O)。这两个阶段占据了总拉取延迟的 80% 以上。Registry 的 GET BLOB 响应时间(P99)是核心 SLO 指标。

2.4 请求链路时序图

下图以时序方式展示镜像拉取请求在 Harbor 组件间的完整交互过程,帮助理解每个步骤的依赖关系和延迟贡献。

镜像拉取请求链路时序图 Docker CLI Nginx Proxy Registry Core 存储后端 ① TLS 握手 ② GET /v2/.../manifests/ ③ 401 + Www-Authenticate ④ 请求 ⑤ 返回 Bearer ⑥ GET Manifest (带 ) 读取 Manifest ⑦ 返回 Manifest ⑧ GET Blob (并发 N 层) ⑨ 读取 Blob 数据 ⑩ 流式返回 Blob 数据 延迟热点:阶段 ⑧ 并发拉取策略 + 阶段 ⑨ 存储后端 I/O 性能

2.5 质量门禁的架构切入点

基于上述架构和请求链路,我们可以识别出以下关键的质量门禁控制点:

门禁控制点 所在组件 拦截时机 典型策略
认证与授权 Core ( 服务) 步骤 ③-⑤ RBAC、项目级别权限、机器人账户
漏洞扫描门禁 Core + Jobservice + Trivy Push 后 / Pull 前 阻断高危漏洞镜像的拉取或部署
签名验证门禁 Core (Notation/Cosign) Pull 时 仅允许拉取已签名的可信镜像
拉取速率限制 Nginx Proxy / Registry 步骤 ①-② 基于 IP 或项目的 QPS 限流
制品保留策略 Jobservice (GC) 定时触发 按 tag 数量、时间、正则规则自动清理
架构陷阱提醒:不要将质量门禁逻辑全部塞入 Registry 组件。Registry 是纯数据面组件,应保持轻量和稳定。所有策略判断(认证、扫描、签名)应前置到 Core 或通过 Proxy 层拦截,避免增加 Registry 的请求处理延迟。

2.6 组件依赖与高可用设计

在生产环境中,Harbor 各组件的依赖关系决定了部署架构的容错能力:

  • Core 无状态:可水平扩展,前端通过 Proxy 做负载均衡。所有会话状态存储在 Redis 中。
  • Registry 无状态:可水平扩展,但需要共享同一存储后端。注意并发写入时的锁机制(S3 的强一致性 vs NFS 的 close-to-open 语义)。
  • Jobservice 无状态:任务状态存储在 Redis 和 PostgreSQL 中,支持多副本部署。
  • PostgreSQL 与 Redis:有状态组件,需要主从复制或集群模式保障高可用。这是 Harbor 架构中最脆弱的环节。
  • 存储后端:有状态组件,建议使用 S3 兼容对象存储(MinIO、Ceph RGW)以获得更好的可用性和性能。
误差预算台账启示:在建立 SLO 时,需要为每个组件定义独立的延迟和错误率指标。例如:Core 的 签发延迟(P99 < 200ms)、Registry 的 Blob 读取延迟(P99 < 500ms)、存储后端的 I/O 延迟(P99 < 100ms)。组件级指标是定位故障根因的基础。