git命令详解

git命令详解

常用 Git 命令

本地(Local)

1、初始化

1.1、全局变量

示例:

git config --global user.name "your_name"
git config --global user.email "your@email.com"
git config --list //列出git在该处找到的所有设置
git config --global core.editor vim //设置你的缺省编辑器,Git在需要你输入一些消息时会使用该文本编辑器
git config --global merge.tool diffmerge //设置merge工具
1.2、初始化新版本库

示例:

git init // 只会在根目录下创建 .git 文件夹
1.3、设置忽略文件
  • 设置每个人都想要忽略的文件:
    1、在根目录创建一个 .gitignore 文件,在里面添加要忽略的文件或文件夹,一个一行;
    2、将 .gitignore 文件加入版本库并提交
  • 设置只有自己需要忽略的文件:
    1、修改 .git/info/exclude 文件,可使用正则表达式
1.4、添加新文件到版本库

示例:

git add somefile.txt //添加单个文件
git add *.txt //添加所有 txt 文件
git add . //添加所有文件,包括子目录,但不包括空目录
1.5、提交

示例:

git commit -m "add all txt files"

2、日常操作

2.1、提交

示例:

git commit -m "some msg" -a //提交所有修改
git commit -m "add msg to readme.txt" readme.txt //提交单个文件
git commit --amend -m "new commit message" // 提交了,发现提交信息写错了,修改上次提交的信息可以用这条命令
git commit -C HEAD -a --amend //不会产生新的提交历史记录,复用HEAD留言,增补提交,而不增加提交记录
2.2、撤销修改

撤销尚未提交的修改(即没有commit的):

git checkout HEAD readme.txt todo.txt //撤销1、2个文件
git checkout HEAD *.txt //撤销所有txt文件
git checkout HEAD . //撤销所有文件

撤销提交:

//反转提交:
git revert --no-commit HEAD //反转提交,相当于提交最近一次提交的反操作。--no-commit 是让你不用输入 commit 信息,这不是个好习惯!
//复位:
git reset HEAD //复位,取消暂存
git reset HEAD <filename> //复位,取消暂存
git reset --hard HEAD^ //复位到HEAD之前的那个版本,不会在版本库中留下痕迹
2.3、分支

示例:

git branch //列出本地分支
git branch -a //列出所有分支
git branch <branchname> //基于当前分支末梢创建新分支
git checkout <branchname> //检出分支
git checkout -b <branchname> //基于当前分支末梢创建新分支并检出分支
//基于某次提交、分支或标签创建新分支
git branch emputy bfe57de0 //用来查看某个历史断面很方便
git branch emputy2 emputy
//普通合并
git merge <branchname> //合并分支<branchname>到当前所在分支并提交,如果发生了冲突就不会自动提交,不想立即解决这些冲突的话,可以用 git checkout HEAD . 撤销
git merge --no-commit <branchname> //合并但不提交
//压合合并
git merge --squash <branchname> //压合合并后直接提交
git merge --squash --no-commit <branchname> //当两个人合作开发一个新功能时,需要在一个分支提交多次,开发完成之后再压合成一次提交
//拣选合并
git cherry-pick --no-commit 5b62b6 //挑选某次提交合并但并不提交
// rebase: 现有 origin 分支(c1-c2-c3-c4)和 mywork 分支(c1-c2-c5-c6),在 mywork 分支和 origin 分支上各有提交,即:origin 上有 c3-c4,mywork 上又 c5-c6
git checkout mywork
git rebase origin // 这些命令会把"mywork"分支里的每个提交(commit)取消掉,并且把它们临时保存为补丁(patch)(这些补丁放到".git/rebase"目录中),然后把"mywork"分支更新到最新的"origin"分支,最后把保存的这些补丁应用到"mywork"分支上。
// 在 rebase 的过程中如果出现冲突,那么 Git 会停止让你解决冲突。解决好冲突后:
git add <fixed-conflict-file> // 更新这些文件的索引
git rebase --continue // 继续 rebase
// 如果你觉得当前的冲突无需修改,那么可以跳过,这样会直接使用 origin 分支的这部分内容:
git rebase --skip
// 在任何时候,你可以用 --abort 参数来终止 rebase 的行动,并且"mywork" 分支会回到rebase开始前的状态。
git rebase --abort // 终止 rebase
//重命名分支
git branch -m <branchname> <newname> //不会覆盖已存在的同名分支
git branch -M <branchname> <newname> //会覆盖已存在的同名分支
//删除分支
git branch -d new2 //如果分支没有被合并会删除失败
git branch -D new2 //即使分支没有被合并也照删不误
2.4、解决冲突

冲突很少时,直接编辑冲突的文件然后提交即可。

冲突比较复杂时,用 git mergetool 调用之前设定的merge工具来处理。

  1. 自动生成 BACKUP,BASE,LOCAL和REMOTE四个文件
  2. 调用设定好的merge工具
  3. 解决之后,关闭工具,BACKUP,BASE,LOCAL和REMOTE四个辅助文件会自动删除,但会同时生成一个 .orig 的文件来保存冲突前的现场。需手动删除这个文件
  4. 提交
2.5、标签

示例:

//创建标签
git tag 1.0 //为当前分支最后一次提交创建标签,标签无法重命名
git tag contacts_1.1 contacts //为contacts分支最近一次提交创建标签
git tag 1.1 4e6861d5 //为某次历史提交创建标签
git tag //显示标签列表
git checkout 1.0 //检出标签,查看标签断面很方便
git branch b1.1 1.1 //由标签创建分支
git checkout -b b1.0 1.0
git tag -d 1.0 //删除标签
2.6、查看状态

示例:

git status // 当前状态
git log //历史记录
git branch -v //每个分支最后的提交
2.7、其他

示例:

//导出版本库
git archive --format=zip HEAD>nb.zip
git archive --format=zip --prefix=nb1.0/ HEAD>nb.zip

远端(Remote)

1、初始化

1.1、克隆版本库和添加远程版本库

1)当已经有一个远程版本库,只需要在本地克隆一份:

git clone <giturl> //克隆,如:git clone https://github.com/me/test.git
git clone <giturl> <dirname> //将远程库克隆到本地<dirname>目录下

克隆之后会自动添加四个config:

  • remote.origin.fetch=+refs/HEADs/:refs/remotes/origin/
  • remote.origin.url=https://github.com/me/test.git
  • branch.master.remote=origin
  • branch.master.merge=refs/HEADs/master

2)当在本地创建了一个工作目录,想把这个目录用 Git 管理,并初始化到远程版本库,可以在远程服务器上创建一个目录,并把URL记录下来。在本地进入工作目录,然后执行:

git init //初始化,对本地工作目录下的文件进行版本控制
git remote add origin https://github.com/me/another_test.git //将本地工作目录放到远程服务器上。这样会添加URL地址为https://github.com/me/another_test.git,别名为origin的远程库
//将本地的文件都推到远程库
git add .
git commit -am "init commit"
git push origin master 
1.2、别名

示例:

git remote add <别名> <远程版本库URL> //添加远程版本库别名
git remote rm <别名> //删除远程库的别名和相关分支
git remote set-url --push <name> <newURL> //修改远程库

添加别名后会自动添加两个config:

1.3、创建一个无本地分支的库

示例:

git init --bare //当需要一个公用的中央库时,非常适合把它建成bare库

2、日常操作

2.1、分支

示例:

git branch -r //列出远程分支
git branch -a //列出所有分支(本地和远程)
git remote prune origin //删除远程库中已经不存在的分支
git push origin --delete <branchName> //删除远程分支
git push origin :<branchName> //推送一个空分支到远程分支,相当于删除远程分支
2.2、从远程库获取

示例:

git remote -v //查看远程仓库
//获取但不合并
git fetch <远程版本库> 
//如:
git fetch origin //origin是远程库的默认别名
git fetch https://github.com/me/test.git
//获取并合并到当前本地分支
git pull //等价于git pull origin,origin是远程库的默认别名
git pull https://github.com/me/test.git master //当不是从默认远程库获取时,需要指定获取哪个分支,这里就是指定获取master分支
git pull <remoteName> <localBranchName> //拉取远程库到本地分支
git pull origin test //拉取远程库到本地test分支
	
推荐用下列方式从远程库获取代码:

git fetch origin master:tmp //从远程库origin的master分支获取版本库到本地tmp分支
git diff tmp //比较本地tmp分支和当前所在分支(一般为本地master分支)
git merge tmp //合并本地tmp分支到当前分支(一般为本地master分支)
//如果这里遇到冲突,则参考“本地(Local) 2.4 解决冲突”来解决冲突
2.3、推入远程库

示例:

git push origin master //推入远程库,这里远程库默认别名origin,本地默认分支master
git push origin test:master //将本地test分支推入远程库,并作为远程库的master分支
git push origin test:test //将本地test分支推入远程库,并作为远程库的test分支

场景举例

撤销一次公共提交

  • 场景:你才用 git push 将本地的修改提交到了远程公共库,突然发现提交中有个错误忘了改了,你想撤销这次提交。
  • 命令:git revert 或者 git reset HEAD^
  • 解释:详见前文讲「Git 管理下文件的状态」那节对这两个命令的解释。在本地撤销后,修改了错误后,再做一次新的提交并 git push 到远程公共库即可。

修改最近一次的提交信息

  • 场景:你用 git commit 命令做了一次提交操作,提交完才想起提交信息没有按规范写,在 git push 之前,你想把提交信息改一改
  • 命令:git commit –amend
  • 解释:上面的命令将使用一个包含了上一次提交所有变更的新提交,来更新并替换这个错误提交。由于这次提交除了修改了 commit message,没有其他 staged 的修改,所以就相当于修正了上一次的提交信息。

撤销提交后重做

  • 场景:你提交了一些内容,然后又用 git reset HEAD^ –hard 撤销了这些更改,然后纠结的你又发现:我还是得还原这些修改!
  • 命令:git refloggit reset
  • 解释:我们对 git log 命令比较熟悉,它能显示提交列表,而 git reflog 则显示的 HEAD 变更列表。ref log 嘛,字面上也能理解。知道了 HEAD 变更的信息列表,那我们就可以用 git reset 来做我们想重做了。但是需要注意的是:git reflog 不会永远存储,Git 将定期清理那些不可达(unreachable)的对象,所以不要期望能在 reflog 里找到数据前的 HEAD 变更记录。
// 我提交了一些内容
$ git commit -m "commit 17"
// 接着我撤销了这些更改
$ git reset HEAD^ --hard
// 额,我这时发现我得还原这些更改
// Step 1: 用 git reflog 查看
$ git reflog
2750087 HEAD@{0}: reset: moving to HEAD^
ad14ba3 HEAD@{1}: commit: commit 17
...
// 发现了刚才的那次撤销以及前面那次提交的信息
// Step 2: 用 git reset 回到那次提交
$ git reset ad14ba3
HEAD is now at ad14ba3 commit 17
// 打印出来的信息显示,我们做到了,更改被还原过来了
// 再看看 reflog 信息和 log 信息
$ git reflog
ad14ba3 HEAD@{0}: reset: moving to ad14ba3
2750087 HEAD@{1}: reset: moving to HEAD^
ad14ba3 HEAD@{2}: commit: commit 17
...
$ git log
commit ad14ba39c57b4b43b913ebc273500afa815bb0e3
Author: kurisu <kurisu@kurisu-MacMini.local>
Date:   Tue Jul 24 15:55:24 2015 +0800
    commit 17

在master做了本该在分支上做的提交

  • 场景:你提交了一些修改,却发现自己是在 master 上,但你本来是期望在 feature 分支上执行这些提交的。
  • 命令:git branch feature, git reset HEAD^ –hard
  • 解释:上面 3 条命令依次执行。第一条命令,先创建一个名为 feature 的分支,但不切换过去,这个分支指向了你最近的提交,保留了你最近的修改;第二条命令,这时你还在 master 上,这条命令撤销了 master 上的上一次提交。接下来,你可以 git checkout feature 将分支切换到 feature 分支上,这个分支保存着你最近的所有工作,你可以接着工作了。

储藏当前工作

  • 场景:经常有这样的事情发生,当你正在进行项目中某一部分的工作,里面的东西处于一个比较杂乱的状态,而你想转到其他分支上进行一些工作。问题是,你不想提交进行了一半的工作,否则以后你无法回到这个工作点。解决这个问题的办法就是 git stash 命令。
  • 命令:git stash
  • 解释:储藏可以获取你工作目录的中间状态——也就是你修改过的被追踪的文件和暂存的变更——并将它保存到一个未完结变更的堆栈中,随时可以重新应用。你可以使用 git stash list 来看储藏列表,可以用 git stash apply 来把之前储藏的工作拿出来继续。

停止跟踪一个已经被跟踪的文件

  • 场景:你意外将 application.log 添加到仓库中,现在你每次运行程序,Git 都提示 application.log 中有 unstaged 的提交。你在 .gitignore 中写上 *.log,但仍旧没用。怎么告诉 Git 停止跟踪这个文件的变化呢?
  • 命令:git rm –cached application.log
  • 解释:尽管 .gitignore 可以阻止 Git 跟踪所指定的文件的变化甚至让 Git 不去提醒这些文件的存在,但是,一旦在你把某个文件加入 .gitignore 之前已经把它 git add 和 commit 了,Git 依然会持续跟踪这个文件的变化。如果你希望移除那些应当被忽略的文件,可以先用 git rm –-cached 命令停止对改文件的跟踪,这个命令不会物理删除文件,然后你还需要在 .gitignore 中添加它以保证以后都不再跟踪这个文件的变化。完成这些后,你将不会在 git status 中看到它,也不会再把这个文件 commit 了。

同步 Fork 的项目

  • 场景:随着 Github 开源项目盛行,我们会常常 fork 一些项目来自己做一些定制开发,但是有时候我们需要同步原项目的更新,怎么做呢?
  • 命令:
    1)同步合并已有分支:git remote add upstream <original_repository>; git remote -v; git fetch upstream; git checkout master; git merge upstream/master
    2)同步原项目中新的分支到 Fork 的项目:git checkout -b newbranch upstream/newbranch; git push -u origin newbranch
  • 解释:就是把 upstream 的 master 分支拉下来 merge 到自己的 master 分支。

查询某个文件的修改历史

  • 场景:有时候,你需要查询某个文件从头到尾的修改历史,这时候怎么办呢?
  • 命令:
    1)查看某个文件的提交历史记录:git log <file_name>git log -p <file_name>,加上 -p 可以显示每次提交的diff
    2)查看某次提交中单个文件的修改:git show <commit_sha> <file_name>

这里整理了一张图,有需要的可以自取:

git.png

# git  shell 

评论

Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×