架构说明

组件、请求流程、故障处理与安全边界。

组件

cmd/oci-mirror-proxy        程序入口,调用 internal/cli
internal/cli               命令、参数解析、输出格式化
internal/app               组装入口,持有配置状态、上游池和路由表
internal/frontend          面向 dockerd 的 Registry v2 HTTP 接口
internal/route             分发器、中间件链、原子替换的路由表
internal/middleware        日志、blob 断点续传
internal/scheduler         顺序和对冲策略,以及 Candidate 契约
internal/upstream          单个上游端点、熔断器、传输层,以及支持协调更新的上游池
internal/auth              各上游的认证器:无认证、Basic、令牌质询流程
internal/secret            敏感信息引用与脱敏
internal/config            配置模型、默认值、验证和文件读写
internal/ociapi            仓库路径解析,叶子包
internal/admin             Unix 套接字上的管理 API 及客户端
internal/daemonconf        dockerd 集成:检测、纯渲染、事务式应用
internal/unixhttp          Unix 套接字上的 HTTP,由 admin 和 daemonconf 共用
internal/fsutil            原子文件写入
internal/cache             blob 缓存的预留扩展点(仅接口)

请求流程

  1. dockerd 发送 GET /v2/library/nginx/manifests/latest。
  2. frontend 使用 ociapi 解析路径,得到别名(docker.io)、类型(manifest)、仓库和引用。不符合仓库路径语法的请求返回 404,仅接受 GET 和 HEAD。
  3. frontend 选择该仓库别名对应的路由。
  4. 执行分发器链:先日志,再 blob 断点续传,最后是路由。
  5. 路由从上游池获取已启用上游的快照,然后调用调度策略。
  6. 策略尝试上游。每次尝试经过 Endpoint.Attempt:检查熔断器、发送请求、应用首字节和总超时、处理至多一次认证质询,并记录结果。
  7. 返回第一个可接受的响应(2xx),按白名单复制响应头,并流式传输响应体。

故障处理

事件处理方式
连接被拒绝或上游无响应记为失败并尝试下一个上游,等待受首字节超时限制。
5xx 或 429记为失败。
带 Bearer 质询的 401获取令牌并重试一次。再次收到 401 时返回该结果,将上游视为可达但无法提供内容。
404不视为健康问题,继续尝试下一个上游。若所有已尝试上游均返回 404,则代理返回 404,由 dockerd 回退。
熔断器打开直接跳过,不发起网络请求。
blob 传输中断如果另一个上游返回 206,且 Content-Range 起点与当前偏移量一致,则从该位置继续下载;否则向调用方暴露原始错误。每次下载最多续传三次。
客户端断开取消请求上下文,停止策略执行,不再写入。
所有上游失败,且并非全部为 404返回 502 UNAVAILABLE,由 dockerd 回退。

调度策略

顺序策略(默认):按配置顺序逐个尝试上游,只有当前上游失败后才联系下一个。

对冲策略(默认启用):立即请求第一个上游。每经过 race.delay 仍未收到响应,就启动另一个上游请求,同时进行的请求数不超过 race.max_parallel。某次尝试失败时立即启动下一次尝试。第一个可接受的响应胜出,其他尝试被取消。

配置重载

上游变更无需重启代理即可生效,未改变的上游保留熔断状态和计数器。 无效配置会被拒绝,原配置继续处理请求。

重载不打断已有 HTTP 传输,也不改变其续传候选。同一次 docker pull 中之后新发起的 HTTP 请求使用新配置,详见修改配置。

安全边界

  • 数据平面不提供认证,默认监听回环地址。
  • 管理 API 只能通过受文件权限保护的套接字访问。
  • 上游凭据仅用于对应上游。客户端的 Authorization 在前端被丢弃。跨主机重定向会移除 Authorization,这是 Go net/http 的标准行为。
  • 内容完整性端到端保证:dockerd 校验每个摘要。故障上游可能导致拉取失败,但无法使内容错误的镜像被接受。

本页目录