作者:springzhe7943 | 来源:互联网 | 2023-10-15 16:02
前言
本篇为大家总结社区多人合作常见的场景和对应的git操作命令。本篇非新手教程,阅读本篇前需具备Git基础知识。
Git入门教程请参考https://www.atlassian.com/git。
配置remote
开源社区操作需要我们的本地Git关联两个远程仓库:一个是开源项目的仓库,通常命名为upstream。另一个是我们自己Fork的项目,命名为origin。我们无权push到upstream,但能够push到origin。
开始多人合作前,需要配置好remote。
Remote配置命令
查看remote的详细配置:
# git remote -v
origin https://github.com/xxxx/flink.git (fetch)
origin https://github.com/xxxx/flink.git (push)
upstream https://github.com/apache/flink.git (fetch)
upstream https://github.com/apache/flink.git (push)
git remote
命令也会显示remote配置,但是仅仅显示remote的名字。git remote -v
显示的信息更为详细。
查看某remote的详细配置:
# git remote show
添加一条remote配置:
git remote add
删除一条remote配置:
git remote rm
修改一条remote的名字:
git remote rename
修改某个remote的URL:
git remote set-url
更新fork项目的master分支
项目fork一段时间之后,fork出的项目master分支会远远落后于源项目的master分支。这时我们需要更新它。
方法1:使用rebase指令
rebase指令可以当前分支分叉的提交记录嫁接到另一个分支上。由于我们没有在本地master分支提交(没有分叉的提交记录),rebase相当于将本地master分支的指针指向upstream/master分支的HEAD。
# 更新upstream/master分支到本地
git fetch upstream master
# 切换到master分支
git checkout master
# 执行rebase
git rebase upstream/master
# 推送更新后的master分支到remote
git push origin master
方法2:删掉本地master重新创建
# 更新upstream/master分支到本地
git fetch upstream master
# 删除master分支
git branch -D master
# 重新checkout一个master分支
git checkout -b master upstream/master
# 设置master对应的remote分支为origin/master分支
# 可以忽略这一步,但是以后push的时候不能省略remote分支名
git branch -u origin/master
# 推送更新后的master分支到remote
git push origin master
修改remote tracking branch
通常我们使用git从remote分支checkout一个本地分支,git为自动为我们做关联。但有些情况我们需要修改他们的关联关系。可通过如下命令:
git branch -u /
强制push
如果我们对本地分支做出了修改,部分已存在的提交和remote 分支已经不同,这是如果我们直接推送,会报分支冲突,无法提交成功。
此时为了覆盖远程分支,我们需要执行强制推送命令,格式如下所示:
git push -f
PR提交原则
不同开源项目的规范各种各样。下面只侧重于和git使用相关的部分。
添加规范的提交信息。需要按照社区的规范来。通常格式为:[ISSUE-ID][module] bug_description
。
git commit -m 'commit message'
确保一个提交解决一个问题。如果本地已经有一次提交,又需要修改的话,可以使用追加提交:
git commit --amend
修改源代码前必须从master创建一个分支,不要在master分支直接修改。
git checkout master
git checkout -b
让自己的commit基于社区最新进度
这是一个很常见的场景:我们从master checkout一个工作分支,在上面做出修改。然而工期可能比较长,等我们想要合并到master分支的时候,发现master分支已经更新了。如果工作分支和master分支最新内容没有冲突,实际上不影响我们提交PR。但是我们想把master分支后来增加的commit拉过来到工作分支,让我们的commit基于master分支的最新commit,这样就可以验证我们的修改是否会影响到目前最新版本的功能。我们如何才能这么操作呢?
可以使用git的rebase指令,如下所示:
git fetch upstream master
git checkout working_branch
# 如果有冲突,需要解决
git rebase upstream/master
git push origin working_branch -f
整理提交记录
按照PR提交原则,一个issue必须严格对应一个commit。我们在本地操作的时候有可能没有按照这个要求。怎么才能整理这些冗余的commit呢?
Git的交互式rebase指令可以满足我们的要求。
# 从指定的commit开始rebase
git rebase -i
之后会弹出一个文本文件,如下所示:
pick ab7ef11 1st commit
pick 8a638b2 2nd commit
pick c11b5bc 3rd commit
pick 3d88d16 4th commit
这个文件从上到下时间从早到晚的方式列出了需要rebase的commit。格式为指令 commit-id commit-message
。上面例子的含义为按顺序依次保留这4个commit。这是默认行为,相当于什么也没做。我们需要做的是修改这个文本文件。比如修改指令,调整顺序等。
交互式rebase支持如下常用指令:
- pick:保留该commit
- reword:保留该commit,但修改commit message
- squash:保留该commit的操作,但是压缩到前一个commit中,commit message和前一个commit的合并
- fixup:保留该commit的操作,但是压缩到前一个commit中,忽略这个commit的message
设置某commit为branch的HEAD
这个操作的含义为快速移动某个分支的指针,让它指向特定的某个commit。实践中可以快速更改工作分支的内容。
git reset --hard
可以让分支的HEAD强行指向某个commit。
git checkout
git reset --hard
或者是使用git branch -f
命令:
git branch -f
可以将
指针强行指向
。
提取某commit到当前分支
开发过程中我们可能会建立一些临时的分支,用于单独验证某个改动。在验证完毕后,我们如何才能将其应用到真正的工作分支呢?
Git的cherry-pick正是用来完成这个任务。我们先获取到需要cherry-pick
的commit的id,然后切换到工作分支,执行如下命令:
git cherry-pick
学会使用tag
虽然git有branch这个概念,但是branch是“不稳定”的,意思是它的指针可以随时改变。如果一个commit对于我们具有特殊意义,比方说是对应某个发版版本。我们可以将这个commit起一个容易记住的别名。这个功能正是git tag。
tag的操作
标签的本地操作
查看所有的tag:
git tag
查看某个tag的详细信息:
git show
为某个branch指针所在的commit创建tag:
git checkout
git tag
为某个commit创建tag:
git tag
创建tag的同时指定tag描述信息:
git tag -a -m "tag description"
删除标签:
git tag -d
标签的远程操作
推送指定的标签:
git push
推送所有的标签:
git push --tags
删除已推送的标签:
git tag -d
git push origin :refs/tags/