赞
踩
使用git的一些原则、好习惯和常用命令
需要说明的是,这里的『原则』和『好习惯』只是我个人的看法,仅供参考。
所谓『原则』,是必须遵守的,不遵守将会导致文件混乱、commit提交混乱、commit历史记录被迫修改等问题。
而『好习惯』则是一些推荐的建议,可以不用严格遵守,但是还是最好做到。
本文主要参考 Git-Tower 和 Pro Git 的宝贵经验整理而来。更多 git 知识,请见文末『参考』或者Git-Tower在线免费电子书或者Pro Git在线教程。
注1:暂存区(stage或index)和储藏区(stash)的区别:
git add
之后,文件进入暂存区(staged),之后可以git commit
提交。git stash
可以将未完成的改动临时储藏起来。目的是保持工作目录的干净,以免引起冲突或者混乱。本文难免有错漏之处,请见谅。请不吝指出错误,非常感谢。
在第一次提交之前,建立.gitignore
文件,将那些不需要提交的文件忽略掉(例如,密码文件,中间生成的文件和目录,本地设置的文件,临时文件等),可以参考 https://github.com/github/gitignore 。这条本来想放到『好习惯』中,为了避免重要信息泄露和清理不必要的文件,在一开始就不要把这些文件添加到git历史记录中。
一次提交只包含一个相关的改动。例如,在一次提交中解决一个 bug,或者在一次提交中增加一个新功能。最好不要出现,在一次提交中,既添加了一个新功能,又包含了 bug 修复。这样的好处是,(1)在git revert
时,可以方便的撤销那个 commit 的改动。(2)对开发团队的其他成员来说,更容易理解你做的改动。
在提交(git commit
)之前,一定要经过完整的测试。
在本地仓库中,提交到 master 分支后,及时推送(git push
)到远程仓库中。
获取远程代码(git pull
)之前,最好要查看当前本地仓库的状态git status
。
千万不要为了得到一个干净的工作区(working directory)而提交一些不完整的改动。
如果已经把commit 推送到远程仓库服务器了,就不要轻易对本地仓库中的该commit做改动,例如,不要使用git reset
、git rebase
、git commit --amend
对该commit修改。
执行git checkout (commit) [file]
之前,要确保[file]
的改动已经提交或者已经暂时储藏起来了(储藏是指执行git stash
)。这里的(commit)
是指定的 commit id 上的文件。
执行 git reset --hard [commit]
之前,要确保本地工作目录中的文件已经提交到远程仓库,或者已经备份到另一个目录中。永远要慎重使用这个命令,确保你的辛苦付出不会付之东流。
在执行git revert
和git reset
等命令时,一定要清楚当前在哪个分支上。查看当前分支:git branch -v
。
commit message 写的简洁明确,以便其他人明确你的改动意图。commit message 是指 git commit
时写的注释信息。如果你刚刚提交的注释(git commit -m "注释"
)写的不清楚,在git push
到远程仓库之前,可以通过git commit --amend -m "新的注释"
来替换刚才的注释。如果你想在之前的注释上修改,则可以执行git commit --amend
。
扩展: 如果是你刚刚执行git commit
,之后没有再次提交,也没有git push
到远程仓库,在这种情况下,你还可以继续添加文件到这个commit中,只需要git add <新修改的文件>
,然后git commit --amend
修改注释,就可以在git log --name-only
中看到新的注释和提交的新文件了。
在git pull
之前,将本地的改动保存到储藏区(git stash
)。
在提交前,执行git diff
查看改动。对于已经暂存的文件,采用git diff --cached
或者git diff --staged
来查看改动。这里的『暂存』是指git add
之后的状态。
提交之后,用git log
看一下提交历史。用git log -p
查看更多的改动信息。用git log --name-status
或git log --name-only
查看修改了哪些文件。
适当的使用分支,当开发一个相对独立的功能时,拉出一个分支来是比较合适且易于管理的。新建分支在 Git 中是廉价且方便的。
使用git stash
保存当前的改动到储藏区。这通常是在你开发未完成时,又来了新的紧急任务,不得不把当前工作区的改动暂时保存起来(因为还没有完成,所以不能提交。遵循『千万不要提交不完整的改动』这一原则)。git stash
的结果是,当前的工作目录是一个干净的工作目录了。
扩展: 使用git stash
的一些情况:
git pull
之前使用抓取远程仓库的改动之前,先看看其他人都做了哪些改动。相关命令:
(1)git fetch origin
获取远程origin仓库的改动到本地,但是还没有合并到本地工作目录中;
(2)git log origin/master
查看origin仓库中master分支的改动记录。
发布本地分支时,保持服务器上分支名字与本地分支名字一样,前提是在创建本地分支时,起一个简洁明确的好名字。例如,新建的本地分支为 feature_xxx
,发布这个分支:git push -u origin feature_xxx
,其中-u
是在本地分支 feature_xxx
和远程分支之间创建『跟踪』链接,对于同一个分支,-u
只使用一次即可,不用每次都加-u
。
删掉不用的分支。
例1,本地分支 fix_bug_xxx
上修复了某个 bug,然后合并到了 master 分支上,就可以把 fix_bug_xxx
分支删掉了:git branch -d fix_bug_xxx
。
例2,本地分支 fix_bug_yyy
上有你的改动,你发布到远程仓库后,你的同事基于你的改动又做了新的改动,这些改动都是在 fix_bug_yyy
分支上(远程分支与本地分支同名,严格来说,是 origin/fix_bug_yyy
,如果仓库名是 origin
的话)。你将 orgin/fix_bug_yyy
改动拉取到本地工作目录中,然后合并到 master
分支上。此后,你需要删除本地的 fix_bug_yyy
分支,还需要删除远程分支 orgin/fix_bug_yyy
:git branch -dr orgin/fix_bug_yyy
。
及时恢复误删掉的 commit。如果git reset
删除了已经提交的分支,可以通过git reflog
看到被删掉的 commit。如果需要恢复commit,可以通过git merge <deleted_commit>
来恢复。
设置自己顺手的 diff 工具和 merge 工具。参考:设置 BeyondCompare 作为 diff 和 merge 工具,使用 meld 作为 diff 和 merge 工具,Use vimdiff as git mergetool。
扩展:
这里可能包含前面提到的命令,也会加上一些上面没有提到的命令。
命令 | 含义 |
---|---|
git clone <repository_url> | 克隆一个git工程,git工程的url为 <repository_url> |
git clone --recurse-submodules <repository_url> | 克隆一个git工程,并同时下载子模块。 |
git clone && git submodule update --init --recursive | git项目包含子模块,在git clone 之后,需要用git submodule update --init --recursive 下载子模块。 |
git submodule status | 在git工程中,查看子模块。 |
git clone --config http.proxy=127.0.0.1:53152 <repository_url> | 下载时,临时加上代理,通常在代理经常变的情况下用。 |
git config --global --add http.proxy 127.0.0.1:53152 | 设置全局代理(--global ,多个git工程会共用这个代理。也可以进入到某个git工程中,设置单独的代理,此时不需要--global 参数。 |
git config -e --global | 编辑全局配置,-e 也可以写作--edit 。 |
git config -l | 查看当前的配置。默认查看全局的配置,如果在某个git工程下,也可以查看该git工程的配置。 |
git status | 查看工作区的状态 |
git log | 查看日志。有大量的参数可以定制,最好根据自己的喜好做定制化的日志格式。 |
git log --oneline 或 git log --pretty=oneline | 查看日志,每个commit只占一行。 |
git log --oneline --graph | 查看日志,commit占一行,以图形化的方式显示。 |
git log --name-status 或 git log --name-only | 查看日志,包含改动的文件状态或文件名。 |
git log -p | 查看日志,显示文件差异。 |
git log -1 | 查看最后一次的日志 |
git log -p -2 | 查看最近两次的commit的日志,显示文件差异。 |
git log --stat | 查看日志,显示简要的增改行数统计。 |
git log --pretty=format:"%h %an %ar : %s" | 查看日志,显示格式为『commit hash 作者名 修改日期 : commit注释』 , h为hash,an为author name,ar为author date relative,即相对日期(例如3天前)。%s为commit注释。format的格式也很多,可以自己定制。 |
git log --author="Colin Cross" | 仅仅查看Colin Cross提交的commit。 |
git log --graph --oneline --decorate --all | 查看日志,图形化显示、commit注释只占一行,显示refs信息(例如显示873940d (origin/revert-310-develop) ,或者显示5879d52 (tag: 2.4.4) 。--all 显示所有的refs。 |
git pull | 从远程仓库服务器拉取文件的改动,合并到本地工作目录中。相当于git fetch 和git merge 的组合。 |
git pull origin master | 当本地工作目录中没有创建任何『跟踪』链接(--track ),就需要指定从哪个仓库的哪个分支抓取文件。此例中,抓取远程仓库origin的master分支 |
git diff | 在未执行git add 之前,可以用此命令查看做了哪些改动,即当前工作目录中的文件 和 HEAD 所在的版本之间的差异。 |
git diff --cached 或 git diff --staged | 执行完git add 之后,可以用这两个命令来查看 |
git diff master..another_branch | 比较master分支和another_branch分支,看看another_branch分支上的哪些改动并不在master分支上。 |
git diff b1a94d8..35ce525 , git diff commit1..commit2 | 比较两个commit的差异,commit2相对于commit1的差异。b1a94d8为base,显示的结果是35ce525相对于b1a94d8的改动。 |
git branch <branch_name> | 创建分支,例如创建feature_develop分支:git branch feature_develop |
git branch -v | 显示项目中的本地分支,并且给出HEAD所在的commit,以及commit message |
git branch -l | 显示本地分支,只有分支名字 |
git branch -a | 显示本地分支和远程分支 |
git stash | 保存当前的改动到储藏区,储藏的名称为stash@{0} ,最新的储藏名称是从0开始,以前储藏的名字中数字更大。 |
git stash list | 查看储藏的列表(可以储藏多次,所有储藏的内容以列表展示) |
git stash pop | 取回最新储藏的内容,然后从储藏区中删除。 |
git stash apply <stashname> | 根据 stashname 取回指定的改动内容。那些改动还在储藏区中。用git stash drop <stashname> 可以删除掉不用的内容。 |
git checkout feature_develop | 检出到 feature_develop 分支上。git checkout 完成两件事:(1)HEAD指针指向 feature_develop 分支。 (2)将工作目录中的文件切换到 feature_develop 上的版本。 |
git checkout master | 切换回 master 分支 |
git checkout master git merge feature_develop | git merge 的两个步骤。(1)切换到需要接收改动的分支上。(2)执行git merge <branch_name> 。例如,此例中,将 feature_develop 分支上的改动 合并到 master 分支上。 |
git checkout <tag_name> | 获取<tag_name> 指定的版本。 |
git remote -v | 查看远程git工程的fetch url 和 push url。 |
git config -l | 查看git工程的配置信息,其中包括url、email、name等。 |
git branch -va | 查看所有分支的简要信息 |
git fetch | 抓取远程仓库的数据,默认取 origin 仓库。注意,此命令不会将远程仓库的改动合并到当前的工作目录中。 |
git fetch crash-course-remote | 抓取远程仓库 crash-course-remote 的数据 |
git checkout --track crash-course-remote/faq-content | 创建一个新的本地分支faq-content (与远程分支同名),并切换到这个新分支上,并且将本地分支与远程分支建立跟踪联系(--track )。 |
git checkout -- <file_name> | 在你还没有提交(git commit )之前,想撤销某个文件的修改,可以使用这个命令。 |
git reset --hard HEAD | 当你想清掉还没有提交的所有本地改动时(上一次提交之后的改动),可以使用此命令,但需要慎重。警告:此命令将会导致本地改动被清掉,并且无法恢复。 |
git reset --hard 2be18d9 | 回滚到commit 2be18d9上,即把commit 2be18d9之后的其他commit都删掉了,而且你本地的未提交的改动也被删掉了。所以需要慎重使用。 |
git reset --keep 2be18d9 | 回滚到commit 2be18d9上,即把commit 2be18d9之后的其他commit都删掉了,但是你本地的未提交的改动仍然保留着。 |
git revert 2b504be | 撤销 commit 2b504be。即,把commit 2b504be上的改动再改回来。 |
git merge --abort 或 git reset --hard | 撤销合并,回到合并前的状态。注意:这两个命令用在merge过程中或者merge完成的时候,是撤销合并的功能。git reset --hard 用在其他场合,将会清除本地未提交的改动,所以要慎重使用。 |
git blame <file_name> | 可以查看文件中每一行代码是谁提交的,在什么时候提交的 |
git diff
的输出:https://www.git-tower.com/learn/git/ebook/cn/command-line/advanced-topics/diffsgit stash
:https://www.git-tower.com/learn/git/ebook/cn/command-line/branching-merging/stashing#startCopyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。