git是分布式版本控制系统,啥是分布式的呢,就是每一个用户的主机上都有一个版本库,可以在本地进行版本管理。如果需要多人合作的时候,就再通过中央服务器进行版本交换。和集中式的版本控制的区别就是,集中式的版本管理是只在远程,每一次commit都必须联网,这就有网络的时延大大滴,而且当中央服务器挂掉的时候所有人都挂了,因为完整仓库只存在于服务器。
git版本库
版本库可以理解为Git仓库,这个目录下的所有文件都会被Git管理起来,每个文件的修改,删除,Git都能跟踪,以便任何时刻都可以追踪历史,或者在将来某个时刻还原。
命令:
在一个目录下,git init
就可以把此目录变成Git可以管理的目录。
这里有几个概念:
工作区:电脑里能看到的目录,嗯,就是单纯的目录
版本库(Repository):Git的版本库里存了很多东西,其中最重要的就是称为stage(或者叫index)的暂存区,还有Git为我们自动创建的第一个分支master,以及指向master的一个指针叫HEAD。
把文件往Git版本库里添加的时候,是分两步执行的:
第一步是用
git add file
把文件添加进去,实际上就是把文件修改添加到暂存区;
同理rm 是删除,git rm file
是将文件在暂存区内删除第二步是用
git commit -m "commit message"
提交更改,实际上就是把暂存区的所有内容提交到当前分支。
因为我们创建Git版本库时,Git自动为我们创建了唯一一个master分支,所以,现在,git commit就是往master分支上提交更改。
你可以简单理解为,需要提交的文件修改通通放到暂存区,然后,一次性提交暂存区的所有修改。
如果有一些文件没有add到暂存区,那么这些文件也是commit不上去的哦~
但是难免会犯错
- Case1:当改乱了工作区的修改,想直接丢弃工作区的修改,回退到clean的状态,用命令
git checkout -- file
- Case2:改乱了工作区的修改,并且add到暂存区了。首先,将暂存区的内容回退到add前的版本
git reset HEAD file
,其次丢弃工作区的修改git checkout -- file
- Case3:已经提交(add)了修改至暂存区,并且commit到版本库了,使用
git reset --hard commit_id
回退到commit_id的版本。commit_id是怎样获得的呢,通过git log
,git log --pretty=online
,git reflog
来查看。
git log
与git reflog
的区别是,git log
当回退到某个版本时,此版本之后的记录都自动抹去了。git reflog
是提交的完整的命令历史,回退到某个版本,仍然可以查到位于此版本号以后的版本号。
远程仓库
关联远程仓库:git remote add origin git@server-name:path/repo-name.git
。
关联后,使用命令git push -u origin master
第一次推送master分支的所有内容
以后每次本地提交后,都可以使用git push origin master
推送最新修改
使用git clone
从远程仓库克隆至本地呀
git创建分支
git branch 查看当前分支
git branch dev 创建dev分支
git checkout dev 切换至dev分支
git checkout -b dev 创建并切换至dev分支
git merge xxx 用于将指定分支的工作成果合并到当前分支
git branch -d branchname
git解决冲突
当两个分支同时对一个文件进行修改时,merge时会发生冲突,解决办法是git status查看冲突文件,然后查看文件内容,Git用<<<<<<<,=======,>>>>>>>标记出不同分支的内容。
例如:
<<<<<<< HEAD
Creating a new branch is quick & simple.
=======
Creating a new branch is quick AND simple.
>>>>>>> feature1
然后手动修改冲突的内容,解决冲突。
用git log
可以查看分支历史。git log --graph
命令可以看到分支合并图
git 分支管理策略
一般情况下,合并分支是采用的fast-forward,即当前分支与要合并的分支指针指向同一处。
不使用fast-forward,命令为git merge --no-off dev,两个分支的指针是指向不同位置的。
bug分支
存在的问题:当前工作区在开发新功能,但是线上出了问题急需解决,需要一个干净的工作区。
git提供了一个stash功能,git stash
可以把当前工作现场储藏起来,拉过来一个干净的工作现场,然后从master分支拉出来一个新的分支,修复完成后,切换到master分支并完成合并。
恢复工作现场时:
查看工作现场:git stash list
恢复工作现场:git stash apply
删除工作现场:git stash drop
恢复&删除工作现场:git stash pop
如果多次stash,恢复的时候先用git stash list查看,然后恢复指定的stash:git stash apply stash@{0}
开发新分支
开发一个新feature,最好新建一个分支
如果要丢弃一个没有被合并过的分支,可以通过git branch -D
<name>强行删除。
多人合作
多人协作的工作模式通常是这样:
- 首先,可以试图用
git push origin branch-name
推送自己的修改; - 如果推送失败,则因为远程分支比你的本地更新,需要先用
git pull
试图合并; - 如果合并有冲突,则解决冲突,并在本地提交;
- 没有冲突或者解决掉冲突后,再用
git push origin branch-name
推送就能成功! - 查看远程库信息,使用
git remote -v
;
本地新建的分支如果不推送到远程,对其他人就是不可见的;
从本地推送分支,使用git push origin branch-name
,如果推送失败,先用git pull
抓取远程的新提交;
在本地创建和远程分支对应的分支,使用git checkout -b branch-name origin/branch-name
,本地和远程分支的名称最好一致;
从远程抓取分支,使用git pull,如果有冲突,要先处理冲突。
如果git pull提示“no tracking information”,则说明本地分支和远程分支的链接关系没有创建,用命令git branch --set-upstream branch-name origin/branch-name
。
标签
Git标签是版本库的快照,其实是指向某个Commit的指针,是以一种容易记忆的方式设定的,一般可指定为版本号vx.x
打标签git tag v1.0
正常情况下,标签是打在此分支的最新提交的commit上的
git tag 查看标签
git show tagname 查看标签信息
git tag commit_id 为commit_id打标签
git tag -a v0.1 -m "version 0.1 released" 3628164 创建带有说明的标签,-a指定标签名,-m指定说明文字
git push origin v0.1 推送标签到远程
git push origin --tags 一次性推送尚未推送到远程的本地标签
git tag -d v0.1 在本地删除标签
git push origin :refs/tags/v0.9 删除远程的标签
参考文献
Git教程