本节摘要:
origin/main不是远端分支,而是本地对远端分支的只读镜像(远程跟踪引用)。本地分支可以与它建立跟踪关系,从而获得 pull/push 的默认目标与 ahead/behind 计数。理清三层命名,远程协作的提示信息全部可读。
同一条逻辑上的"main 分支",在你本地有三个化身,命名空间不同、读写性不同:
| 层 | 全名示例 | 谁在写 | 何时变 |
|---|---|---|---|
| 远端分支 | 远端库的 refs/heads/main | 远端接受推送时 | 同事推送被接受 |
| 远程跟踪引用 | 本地 refs/remotes/origin/main | 你的 fetch/push | 你每次 fetch |
| 本地跟踪分支 | 本地 refs/heads/main | 你 commit/merge 时 | 你的本地操作 |
中间层最容易被误解。origin/main 住在你的 .git 里,是 fetch 时远端状态的快照——它是"你最后一次打听到的消息",不是实时真相。所有对它直接 commit/merge 的尝试都会被拒绝(它是只读镜像),你真正要做的是把它合入自己的 main。侦探的比喻:远端分支是嫌疑人在隔壁楼的实时位置,origin/main 是你监控屏上的画面,你的 main 是你的笔记本——笔记本只能由你写,画面靠你刷新。
本地分支与远程跟踪引用可以建立 upstream 绑定,绑定后 pull/push 不用写参数,status 分支行也给出比对计数:
git switch -c feature --track origin/feature # 新建并绑定 git branch -u origin/main # 给现有分支换绑定 git branch -vv # * main 5e6f7a8 [origin/main] 本地提交 # feature 9c0d1e2 [origin/feature: ahead 1, behind 2] 功能开发中
branch -vv 的方括号是跟踪关系的体检报告:ahead 1 behind 2 意味着本地比镜像多 1 个提交、少 2 个提交——分叉了,推送前必须先 fetch 加 rebase/merge。只有 ahead 没有 behind 才可以直接推。克隆时自动为主分支建好绑定;新建分支忘记 --track 时,首次 push 用 -u(git push -u origin feature)一步完成推送加绑定,这是最常用的姿势。
绑定还是 push.default 的依据。现代默认 simple:只推当前分支、且要求与上游同名——防的就是"推错分支把半成品发上主干"。团队里偶尔能看到有人配置 matching(推所有同名分支),我不建议,并行任务多时极易把未完成的分支误发。
status 与 branch -vv 的计数是引用两两比对的产物,逐个解码:
git status -sb # ## main...origin/main [ahead 1]
[ahead 1]:本地有 1 个未推送提交,push 即可。[behind 2]:镜像领先 2 个提交,本地落后,pull 或 fetch 加 merge。[ahead 1, behind 2]:分叉——你需要 rebase 或 merge 之后才能推。分叉处理在第 3、4 章反复演练过:fetch、rebase、解决可能的冲突、push。计数是这套流程的仪表盘——每天开工第一眼看一眼 ahead/behind,是成本最低的协作习惯。
删除远程分支:git push origin --delete feature——本质是一次"请求把远端的引用文件删掉",对象由远端 GC 处理。配合平台的合并请求界面里的删除按钮,效果相同。
清理陈旧的远程跟踪引用:同事删掉远端分支后,你本地的 origin/feature 仍残留。git fetch --prune(或配置 fetch.prune true 一劳永逸)会在每次 fetch 时同步删除已消失的镜像。长期协作的仓库建议全员开启,否则 branch -a 里会积攒一串幽灵分支。
git branch -a # main # remotes/origin/main # remotes/origin/feature <- 幽灵 远端已删 git fetch --prune && git branch -a # 幽灵消失
查看远端到底有哪些分支:git ls-remote origin 直接询问远端(走网络),列出远端全部引用的最新哈希——与本地 branch -r(只读本地镜像)对照,能立刻发现"镜像过期"问题。
⚠️ 常见坑:把 origin/main 当成"远端实时状态"做决策(比如"远端已经修了这个 bug?"——其实看的是几小时前的镜像)。涉及关键判断前先 fetch,或用
git ls-remote直连确认。
💡 关键直觉:跟踪关系只是"记住了默认收发对象",没有任何强约束。你可以随时换绑、绑不对称的名字、甚至不绑。真正约束协作秩序的不是绑定,而是团队规范(第 5 章)与平台保护规则。

网络层的最后一块:第一次接触(克隆)与发布时刻(标签)。