问题:我只执行git push, 后面既没有写仓库名,也没写分支名, 那么系统知道我要把本地修改推到远程的哪一个仓库和哪一个分支吗
当我们只执行 git push 命令,而不指定远程仓库和分支名时,Git 的行为取决于当前分支的跟踪关系以及配置的push.default参数.
1/有上游分支
git branch -vv命令查看是否有上游分支
如果开发者当前所在的本地分支已经设置了上游分支(即跟踪的远程分支, 或者说对应的远程分支),那么就会推送到对应的远程分支。并且只有在当前分支名和远程分支名一致的情况下才会推送,否则会报错。
2/没有上游分支
如果没有设置上游分支,这取决于配置push.default.
git config --global push.default命令可以查看该参数的值.
举例子
例如,如果你在本地的 main 分支,并且它已经跟踪了 origin/main(远程仓库的main分支),那么执行 git push 就相当于 git push origin main。
另外,也可以通过配置 push.default 来改变这一行为,但通常情况下我们使用默认的 'simple' 或 'upstream'。
总结:当只执行 git push 命令时,Git 会根据当前分支的上游分支(如果有)来决定推送到哪个远程仓库的哪个分支。如果没有设置上游分支,则行为取决于 push.default 的配置。在默认的 'simple' 模式下,如果当前分支没有对应的上游分支,那么会报错,提示你指定推送的远程仓库名称和分支名称。
所以,如果你克隆了一个仓库,然后在本地的某个分支上工作,并且希望推送这个分支到远程,那么你首先需要设置上游分支,或者第一次推送时使用 git push -u origin 分支名,-u就是upstream单词的前缀, 这样就会建立跟踪关系,之后就可以直接使用 git push 了。
当你只执行 git push 命令而不带任何参数时,Git 的行为由几个因素决定:
1. 当前分支是否有上游分支(upstream)
这是最重要的因素:
# 查看当前分支的上游分支
git branch -vv
- 如果当前分支设置了上游分支(跟踪远程分支),那么
git push会推送到对应的远程分支 - 如果没有设置上游分支,则行为取决于
push.default配置
2. push.default 配置
这个配置决定了 git push 的默认行为:
# 查看当前配置
git config --get push.default
常见值有:
simple(默认):只有当当前分支名与远程分支名相同时才推送upstream:推送到设置的上游分支(即使分支名不同)current:推送到远程的同名分支(如果远程没有则创建)matching:推送所有与远程同名的本地分支(旧版默认)
3. 实际情况分析
情况 A:如果当前分支有上游分支
# 假设当前在 feature/login 分支
git branch -vv
# 输出:* feature/login abc123 [origin/feature/login] 提交信息
这时 git push = git push origin feature/login:feature/login
情况 B:如果当前分支没有上游分支
git branch -vv
# 输出:* feature/login abc123 提交信息(没有方括号部分)
这时 git push 的行为取决于 push.default 配置:
- 如果是
simple(默认):会报错,要求你指定远程分支 - 如果是
current:会推送到远程的同名分支, 如果远程没有这个分支则创建.
4. 常见实践
最佳实践:第一次推送时设置上游分支
# 第一次推送时使用 -u 参数
git push -u origin feature/login # 这样就有了上游分支, 以后每次都可以只执行git push命令
# 之后就可以直接使用 git push
设置默认行为(可选)
# 如果你希望默认行为是推送到同名分支
git config --global push.default current
5. 总结
| 情况 | git push 的行为 |
|---|---|
| 有上游分支 | 推送到设置的上游分支 |
无上游分支 + push.default=simple | 报错,要求你明确指定分支名 |
无上游分支 + push.default=current | 推送到远程同名分支,如果远程没有该分支则创建 |
建议:总是明确设置上游分支(使用 -u),这样 git push 和 git pull 都能正常工作,无需每次都指定远程仓库和分支。