发布时间: 2026年11月3日更新时间: 2026年11月3日

Git Clone 速度变慢时,如何判断是代理、仓库还是协议的问题

Git Clone 变慢时,如何判断问题来自代理链路、仓库还是协议?本文用分阶段计时和控制变量的对照缩小排查范围,不靠主观感受判断。

Git 变慢往往不是“网速不够”,而是卡在某一阶段。正确做法是固定仓库、客户端、协议、缓存和时间,用 Git 自带的跟踪开关分段计时,再对照代理 IP 链路、仓库限速和协议版本三种原因。测试使用公开仓库与自有环境,不对目标仓库发起高频重复克隆。

Clone 变慢时,先排查哪些因素?

先固定影响耗时的条件,后续对照才有意义:

  • 仓库:同一 URL、同一分支、同一提交历史;
  • 客户端:Git 版本、配置、是否启用稀疏检出;
  • 协议:HTTP(S) 还是 SSH,协议版本 v0/v1/v2;
  • 缓存:本机对象库、DNS 缓存、代理缓存。

第一次克隆和后续操作的时间可能受本地或服务端缓存影响,不能直接对比。已有工作区执行 fetch、使用 --reference/alternates、共享对象库或特定本地 clone 方式时,Git 才可能复用已有对象。对远端 URL 在独立空目录执行普通 clone,不会仅因其他目录有同仓库就自动借用其对象;记录命令、目标目录与 reference 配置,并区分客户端、服务端和代理缓存。

怎么用 Git 日志找出耗时阶段?

用 Git 跟踪日志观察各阶段,并给输出加时间戳:

```bash
GIT_TRACE=1 GIT_TRACE_PERFORMANCE=1 GIT_TRACE_CURL=1 GIT_TRACE_CURL_NO_DATA=1 \
git clone <url> 2>&1 | while IFS= read -r line; do printf '%s %s\n' "$(date +%H:%M:%S)" "$line"; done
```

默认的 GIT_TRACE_CURL 可能记录收发数据及请求/响应头;GIT_TRACE_CURL_NO_DATA=1 可避免记录传输正文,但仍可能暴露认证信息、Cookie、私有仓库 URL、查询参数和内部主机名。只在测试凭据与可分享仓库上使用;限制日志访问,分享前脱敏。发生凭据泄露时按流程轮换。该 trace 不提供 TCP 重传证据。

  • GIT_TRACE=1 显示执行的子命令与阶段;
  • GIT_TRACE_PERFORMANCE=1 输出各阶段耗时;
  • GIT_TRACE_CURL=1 提供 Git 使用的 HTTP 层诊断信息;它不等于完整网络抓包,也不能据此测量 TCP 重传。

读日志时依次看建连/TLS、引用协商和 packfile 接收阶段,不要只比较总时长。

  • 阶段:建连与 TLS | 在输出里怎么认:出现 Connected to、TLS 握手相关行 | 变慢时先查什么:代理网络路径、出口质量、DNS
  • 阶段:引用协商 | 在输出里怎么认:advertise refs、ls-remote 相关行 | 变慢时先查什么:引用数量、协议版本、服务端处理
  • 阶段:接收对象 | 在输出里怎么认:Receiving objects 进度 | 变慢时先查什么:packfile 接收阶段的字节数、速率与耗时
  • 阶段:解包与检出 | 在输出里怎么认:Resolving deltas、Checking out files | 变慢时先查什么:本机 CPU、磁盘或文件数量;与网络接收分开计时

怎么判断时间花在对象协商还是文件传输?

协商耗时受引用、协议和服务端处理影响;先看阶段数据,再判断是否与传输带宽有关。

  • 引用数量极多:ls-remote 与 advertise refs 阶段变慢;
  • 历史极深:需要传输的 packfile 更大;
  • 大文件多:单个对象大,分块与重传影响明显。

如果建连快而协商耗时长,先结合实际协议、过滤能力、协商请求与服务端处理复测;若接收阶段速率稳定但慢,再比较链路、平台限速和字节量。git ls-remote <url> | wc -l 只能粗略估计引用规模,不能用“上万行”作为通用阈值,也不能据此断言升带宽无效。每次只改一个变量,记录协商耗时、响应字节和客户端/服务端情况。

怎么区分代理链路、仓库限速和协议影响?

上一节用于判断时间落在协商还是对象传输;下表把观测现象对应到下一项对照。

  • 现象(只是线索):建连或 TLS 阶段就慢 | 待验证的假设:代理网络路径 | 验证方式:换出口复测
  • 现象(只是线索):传输阶段速度稳定在某个上限 | 待验证的假设:仓库或平台限速 | 验证方式:同仓库不同时段、不同出口对比
  • 现象(只是线索):协商阶段请求次数异常多 | 待验证的假设:协议版本或配置 | 验证方式:切换 v1/v2、加 -c protocol.version=2
  • 现象(只是线索):起初快、中途频繁停顿 | 待验证的假设:链路抖动、服务端等待或本地处理 | 验证方式:对照 Git 阶段耗时、接收速率及本机 CPU/磁盘;重传需独立网络证据

这些现象只是线索,不是结论。同一仓库、同一提交、同一客户端、同一缓存状态下多轮测试,记录阶段耗时、传输字节量、速率分布和响应头,再决定往哪个方向归因。

传输速率长期稳定在某一水平时,可检查仓库侧整形、带宽上限或并发限制;速率波动时则同时核对链路、服务端等待与本地解包。单次曲线不能区分这些原因,应在同一仓库和客户端条件下跨时段或出口重复测试,并记录对应阶段数据。不同出口的耗时差异只能说明结果与出口/路径相关,仍需分段证据定位。

若表现为地区依赖或链路不可用,可参考某地区依赖服务不可用时,如何验证 SaaS 产品的降级与恢复?。

怎么用 HTTPS、SSH 和浅克隆做对照?

协议、深度和过滤是三种独立对照,每次只改变其中一项:

  • 协议对照:同一仓库分别用 HTTPS 与 SSH 克隆。如果 HTTPS 走代理而 SSH 直连,两者耗时差异可能来自代理路径,也可能来自协议、认证或服务端处理差异,需结合分阶段记录判断。
  • 深度对照:加 --depth 1。浅克隆明显变快,说明减少传输对象可能改善耗时;这不能单独排除链路因素。

再加一个 --filter=blob:none 的部分克隆对照,可进一步区分对象数量与对象体积的影响。三种对照按“协议 → 深度 → 过滤”的顺序做,每做一次只改一个变量。

根据对照结果,下一步先检查什么?

结合前面各项对照结果,选择下一步核查:

  • 观察结果:建连或 TLS 慢 | 优先排查项:代理网络路径、出口质量、DNS | 下一条对照:同仓库换出口、换时段各跑一轮
  • 观察结果:协商慢 | 优先排查项:仓库规模、协议版本或服务端处理 | 下一条对照:对照协议、协商耗时、响应字节与服务端资料
  • 观察结果:packfile 慢、速率平稳 | 优先排查项:平台限速或带宽上限 | 下一条对照:同仓库不同时段、不同出口对比速率曲线
  • 观察结果:起初快、中途停顿 | 优先排查项:链路抖动、服务端等待或本地解包 | 下一条对照:对照传输速率、Git 阶段与本机资源;重传需独立网络证据
  • 观察结果:加 --depth 1 明显变快 | 优先排查项:传输对象量 | 下一条对照:再加 --filter=blob:none 对照
  • 观察结果:三种对照都无差异 | 优先排查项:本地磁盘、杀毒扫描、Git 并发 | 下一条对照:结合本机资源监控确认

浅克隆后耗时下降,先确认传输对象量、仓库状态和本地缓存条件一致,再判断减少的数据量是否解释了差异。Git 命令和配置细节可查Git 官方文档。

FAQ

Q:浅克隆更快,能证明代理链路有问题吗?

A:不能,它改变了传输数据量;只能说明负载规模影响结果,需结合分阶段计时判断。

Q:SSH 和 HTTPS 速度不同,哪种结果可信?

A:两者路径和认证机制不同,应分别记录,不把单次差异视为代理性能结论。

Q:公开仓库和私有仓库能放在同一组对照里吗?

A:不建议,权限、服务端策略和仓库规模都会改变传输条件。