# docker-probe **Repository Path**: acebear/docker-probe ## Basic Information - **Project Name**: docker-probe - **Description**: 国内docker pull拉取镜像时常出问题 这个用来侦测是哪一步出了问题 - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2026-06-02 - **Last Updated**: 2026-06-02 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # docker-probe 通过 Docker Hub 或任意自定义 Registry API 获取镜像信息,并精确追踪每一步 HTTP 连接的 **IP:端口**(类似 `curl -v`),用于诊断网络故障。 ## 快速开始 ```bash python3 -m venv .venv source .venv/bin/activate pip install -r requirements.txt # Docker Hub 官方镜像 python docker-probe.py golang:1.26 # 自定义镜像仓库(如 DaoCloud 加速镜像) python docker-probe.py docker.m.daocloud.io/golang:1.26 ``` ## 功能 | 功能 | 说明 | |------|------| | **镜像信息查询** | 打印 manifest 元数据、层列表、配置、构建历史 | | **多架构支持** | 自动展示所有平台列表,并优先显示**本机平台**(动态检测 OS/架构) | | **任意 Registry** | 支持 Docker Hub、DaoCloud、私有仓库等任意标准 Registry V2 | | **通用认证** | 遵循标准 `Www-Authenticate` 流程,自动适配任意 registry 的 auth | | **连接追踪** | 每步 HTTP 请求都打印 URL + 实际连接的 IP:端口 | | **重定向追踪** | blob 下载遇到 307 重定向时分两步展示:registry 和 CDN,各有 URL + IP | | **非标准响应** | registry 返回纯 JSON(如错误信息)时直接打印 JSON 内容 | | **错误精简** | 连接失败时不打印冗长的调用栈,只显示错误类型和消息 | ## 用法 ```bash # Docker Hub 官方镜像 python docker-probe.py golang:1.26 python docker-probe.py python:3.12-slim python docker-probe.py alpine # Docker Hub 第三方镜像 python docker-probe.py nginx:latest python docker-probe.py library/nginx:latest # 自定义 Registry(如 DaoCloud 镜像加速) python docker-probe.py docker.m.daocloud.io/golang:1.26 python docker-probe.py docker.m.daocloud.io/library/nginx:latest # 私有仓库 python docker-probe.py my-registry.example.com/myapp:v1 ``` ## 输出示例 ### Docker Hub 镜像 ``` 🔍 查询镜像: golang:1.26 Registry: Docker Hub Repo: library/golang Tag: 1.26 🔑 获取 token… → 54.235.153.191:443 📥 获取 manifest… URL: https://registry-1.docker.io/v2/library/golang/manifests/1.26 → 54.235.153.191:443 📦 golang:1.26 🏷 Content-Type: application/vnd.oci.image.index.v1+json 📋 多架构镜像 — 支持以下平台: [1] linux/amd64 ... [2] linux/arm64/v8 ... 📥 获取本机平台 (linux/amd64) 的 manifest… URL: https://registry-1.docker.io/v2/library/golang/manifests/sha256:e3665... → 54.235.153.191:443 📄 Schema: v2 ── Layers (7) ── Layer 1: sha256:f32f49ce655a… 47.0 MiB 📥 获取 config (sha256:dce756aef3ea…)… URL: https://registry-1.docker.io/v2/library/golang/blobs/sha256:dce... → 54.235.153.191:443 ← registry IP ⤷ HTTP 307 ← CDN 重定向 URL: https://production.cloudfront.docker.com/... → 13.35.190.91:443 ← CloudFront CDN IP 🖥 linux/amd64 📅 Created: 2026-05-20T01:15:43.929508773Z ⚙ Cmd: ['bash'] ``` ### 自定义 Registry(DaoCloud) ``` 🔍 查询镜像: docker.m.daocloud.io/golang:1.26 Registry: docker.m.daocloud.io Repo: golang Tag: 1.26 🔑 获取 token… → 47.100.46.249:443 ← DaoCloud 认证服务 IP 📥 获取 manifest… URL: https://docker.m.daocloud.io/v2/golang/manifests/1.26 → 47.100.46.249:443 📦 docker.m.daocloud.io/golang:1.26 🏷 Content-Type: application/vnd.oci.image.index.v1+json 📋 多架构镜像 — 支持以下平台: [1] linux/amd64 ... ``` ## 网络诊断 `docker-probe` 的核心设计目标之一是 **网络诊断**。每步 HTTP 请求都会打印: ``` URL: https://registry-1.docker.io/v2/... → 54.235.153.191:443 ``` - 如果连接成功,显示连接的 IP:端口 - 如果连接失败,`try/finally` 保证 IP 依然会打印出来 - IP 从 **TCP 建连阶段**(`_new_conn`)获取,在 SSL 握手之前,即使握手失败也能捕获 ### 诊断 `/etc/hosts` 是否生效 ``` 📥 获取 manifest… URL: https://registry-1.docker.io/v2/... → 54.235.153.191:443 ← 如果 hosts 中设置了 registry-1.docker.io,这里会显示对应的 IP ``` ### 诊断 CDN 重定向 Docker Hub 对 blob 下载会返回 HTTP 307 重定向到 CloudFront CDN。工具自动分两步打印: ``` 📥 获取 config … URL: https://registry-1.docker.io/v2/.../blobs/... → 54.235.153.191:443 ← 第一步:走 hosts 的 registry ⤷ HTTP 307 URL: https://production.cloudfront.docker.com/... → 13.35.190.91:443 ← 第二步:CloudFront CDN IP ``` ### 自定义 Registry 认证流程 工具自动遵循标准 Docker Registry V2 认证: 1. 访问 `GET /v2/` 获取 `Www-Authenticate: Bearer realm="..."` 2. 解析 `realm`、`service`、`scope` 3. 到对应的 auth server 换取 token 4. 使用 token 发起后续请求 每个步骤都会打印实际连接的 IP,方便排查认证链路上的网络问题。 ### 非标准 JSON 响应 当 registry 返回 `application/json`(如错误信息、非标准响应),工具直接打印 JSON: ``` 🏷 Content-Type: application/json; charset=utf-8 { "errors": [ { "code": "UNAUTHORIZED", "message": "authentication required" } ] } ``` ### 技术原理 通过自定义 `urllib3.HTTPConnection._new_conn()`,在 socket 建立后立即调用 `getpeername()` 获取对端地址,再通过自定义 `HTTPAdapter` 挂载到 `requests.Session` 上,实现全流程 IP 追踪。 ## 项目文件 ``` docker-probe/ ├── docker-probe.py # 主程序 ├── requirements.txt # Python 依赖(仅 requests) ├── .venv/ # 虚拟环境 └── README.md ```