git使用
git的概念
git是目前世界上最先进的分布式版本控制系统。
工作原理/流程:

Workspace: 工作区
Index/Stage: 暂存区
Repository: 仓库区(或本地仓库)
Remote: 远程仓库
git fetch是将远程主机的最新内容拉到本地,用户在检查了以后决定是否合并到工作本机分支中。
而git pull 则是将远程主机的最新内容拉下来后直接合并,即:git pull = git fetch + git merge,这样可能会产生冲突,需要手动解决。
git与svn的区别:
SVN是集中式版本控制系统,版本库集中放在中央服务器;而Git是分布式控制系统,它没有中央服务器,每个人的电脑就是一个完整的版本库。
工作区与暂存区的区别:
工作区就是在电脑上看到的目录(.git目录除外);版本库就是工作区中隐藏目录.git,它里面存了很多东西,其中最重要的就是stage(暂存区),还有Git为我们自动创建的第一个分支master,以及指向master的一个指针HEAD。
git的配置
git安装完成之后,因为git是分布式版本控制系统,所以需要填写用户名和邮箱作为一个标识,用户名和邮箱配置命令:
git config --global user.name "用户名"
git config --global user.email "邮箱"
git常用命令
1、git init
git init
打开一个文件目录,在当前目录下执行git init就可以把这个目录变成git可以管理的仓库:

而你也可以看到你所在目录多了一个.git目录,这个目录就是git来跟踪管理版本的:

2、git add
git add
使用git add加文件名,可以将文件添加到暂存区,在当前目录下新建一个文本文件,执行命令:

添加成功没有提示
3、git commit
git commit -m '注释'
使用git commit 命令将暂存区的文件提交到当前分支上。

4、git status
git status
查看提交状态,若都已经提交:

若有未提交,比如随便修改一下test1.txt文件,新增一行444444,再次执行:

可以看到提示出了修改的文件没有提交。
5、git diff
git diff 文件名
查看修改内容

6、git log
git log
查看提交历史记录

commit后面是每次提交的版本号
git log --pretty=oneline
简略显示历史提交记录:

7、git reset
git reset --hard HEAD^ // 一个^代表回退到上一个版本,^^两个代表回退两个版本
git reset --hard HEAD~n // n代表往前回退版本数目
git reset --hard 版本号 // 直接切换到指定版本号
往前回退一个版本:

而且我们也可以看见test1.txt文件内容也回到了第一次提交状态。
如果我们想回到最新版本,使用git reset --hard 最新版本的版本号(最新版本的版本号获取通过下条命令):

8、git reflog
git reflog
git reflog命令历史,可以看到所有的版本记录和版本号

9、git checkout
git checkout -- 文件名 // 注意文件名前面有空格
git checkout 分支名 // 注意没有 --
对于git checkout -- 文件名 表示撤销文件的修改,如果文件只是在工作区修改了,还没有进行git add那么撤销修改就回到和版本库一样的状态;如果在工作区修改了文件,并且进行了git add放到了暂存区,那么再执行git checkout -- file进行撤销只能回到暂存区的状态,回不到版本库的状态,若想回到版本库状态可用git reset。
对于git checkout 分支名 表示创建分支。
10、rm
rm 文件名
新建一个test2文件并提交到版本库中:

rm操作:

可以看到test2文件已经从工作区删除,但是它不影响版本库。
若是想更新版本库需进一步操作(git add 删除的文件名,版本库比对提交的文件与版本库中的文件进行增删修改):

若是想git add之前撤销删除,可以使用上一个命令git checkout -- test2.txt
补:git的四种主要协议:
1、本地协议(克隆本地版本库)
git clone /opt/git/project.git 或
git clone file:///opt/git/project.git
2、SSh协议(经由安全壳架构访问的协议)
git clone ssh://user@server:project.git 或
git clone user@server:project.git
也可以不指明用户,git会默认使用你当前登录的用户,SSH的限制在于你不能通过它实现仓库的匿名访问。
3、git协议
包含在软件包中的特殊守护进程,监听9148端口,缺少授权机制,一般提供git://拥有只读权限,ssh://开通读写权限。
4.http/s协议
经由web服务器访问的协议。
git与远程仓库
以github为例,首先注册github账号,我们知道git与github有多种通信协议,在我们用github管理项目的时候,可以直接使用https url将项目克隆到本地,当然也可以使用SSH url克隆到本地,一般来说,使用https url比较方便,不需要配置就可以直接将项目克隆到本地,而SSH url克隆却需要在克隆之前先配置好SSH key,配置方法稍后再说,先说一下https和SSH的区别:
**https可以随意克隆github上的项目,而SSH则你必须是克隆项目的 拥有者或者管理员,并且需要先添加SSH key,否则无法克隆。
**使用https url在push的时候是需要验证github用户名和密码的,

在这里我一开始没有设置SSH key,使用https url方式push的时候,发现每次都不用输入账号密码就直接push上去了,我就开始蒙了,我修改了git的用户名和邮箱,发现还是一样根本不需要密码啥的就直接push上去了,最后经过一番探索才知道原因,原来是git会缓存你的github账号密码,在以前往我的github上push的时候已经输入过账号和密码了,只不过我忘了。。。git记录这个凭证之后,在需要密码的时候就自动填充了。打开凭证管理就可以看到凭证:

删掉之后就会发现,当你再次push的时候就会让你输入用户名和密码。
而SSH在push的时候,是不需要输入用户名的,如果配置 SSH key的时候设置了密码,则需要输入密码,反之,则不需要输入密码。
创建SSH Key的步骤:
首先,在用户主目录下,看看有没有.ssh目录,如果有,在看看有没有id_rsa和id_rsa.pub这两个文件,如果有就说明已经创建了,若没有则执行如下命令创建:
ssh-keygen -t rsa –C "youremail@example.com"

可以看到已经生成:

id_rsa是私钥,不能泄露出去,id_rsa.pub是公钥,可以放心告诉别人。
然后,登录github,打开setting中的SSH keys页面,然后点击创建New SSH Key,填上任意title,在key文本框里粘贴id_rsa.pub文件的内容:

最后确定就可以了。
添加远程库:
当我们在本地创建一个git仓库时,又想在github上创建一个git仓库,并且希望这两个仓库进行远程同步,这样github仓库可以作为备份,又可以和其他人通过该仓库来协作。
首先,创建一个新仓库:

创建成功:

目前,在github上的这个testgit仓库还是空的,我们可以从这个仓库中克隆出新的仓库,也可以将它与本地的仓库进行关联。
下面进行关联,我们在本地的testgit仓库中执行如下命令:
git remote add origin https://github.com/Yang-0394/testgit.git

这时就已经成功关联,origin是给远程分支起的名字,把本地库的内容推送到远程,使用git push命令,实际上是把当前分支master推送到远程。

由于远程库是空的,我们第一次推送master分支时,加上一个-u参数,git不但会把本地的master分支内容推送到远程新的master分支,还会把本地的master分支和远程的master分支关联起来,在以后的推送或者拉取时就可以简化命令。
上面是先有本地库,后有远程库时候的关联方式,下面是我们想直接克隆一个远程库到本地时的情况,使用git clone:
git clone [url]
clone下来的仓库会以url最后一个斜线后面的名称命名,创建一个文件夹;比如https://github.com/Yang-0394/test.git,就会以test为名创建一个文件夹,当某个版本库被克隆时,git会自动将克隆到本地的版本库与该远程库关联且远程版本库名称为origin。如果想指定远程版本库的名称可以使用git clone -o newname [url]
创建与合并分支。
git checkout -b dev // 创建并切换到分支dev
git checkout dev // 切换到分支dev
git branch // 查看当前分支

查看一下readme.txt内容,如下

可以看就是创建分支时刻主分支的内容。
我们在dev分支上在readme里添加一行数字并提交,然后回到master分支,会发现,master分支上的内容没变,我们可以通过git merge dev 命令,将dev分支内容合并到master分支:

此处有个点需要注意,上面有个Fast-forward信息,Git告诉我们这次合并是‘快进模式’,也就是把master指向dev的当前提交,所以合并速度非常快,它与no fast forward的区别就是,使用后者合并会创建一个新的commit记录,避免的丢失dev分支的信息,可看下面两图:

这是在dev分支增加444后进行了一次commit,但是合并之后,直接将master指向了dev的提交,失去了dev的历史记录。
当使用 git merge --no-ff -m '注释' dev合并时:

可以看到创建了一个新的提交,dev的第二次提交还在。
总结创建与合并分支的命令:
git branch // 查看分支
git branch name // 创建分支
git checkout name // 切换分支
git checkout -b name // 创建加切换分支
git merge name // 合并某分支到当前分支
git branch -d name // 删除分支
如何解决冲突?
下面我们还是一步一步来,先新建一个分支,名字叫fenzhi1,在readme.txt文件中添加一行内容8888,然后提交;然后我们切换到master分支上来,也在最后一行添加内容,内容为9999,

现在我们在master分支上来合并fenzhi1,如下操作:


可以看到产生了冲突

Git用<<<<<<<<<<,=========,>>>>>>>>>标记出了不同分支的内容,其中<<<<<HEAD是指主分支修改的内容,>>>>>fenzhi1是指fenzhi1上修改的内容,我们可修改后保存:


分支策略:首先master主分支应该是非常稳定的,也就是用来发布新版本,一般不允许在上面干活,干活一般情况下在新建的dev分支上干活,干完后,比如要发布,或者说dev分支代码稳定后可以合并到主分支master上来。
bug分支:
在开发中,会经常遇到bug问题,那么有了bug就需要修复,在Git中,分支是很强大的,每个bug都可以通过一个临时分支来修复,修复完成后,合并分支,然后将临时的分支删除掉。
比如我们在开发中接到一个404 bug的时候,我们可以创建一个404分支来修复它,但是当前的dev分支上的工作还没有提交,如下:

并不是我不想提交,而是工作进行到一半时候,我们还无法提交,比如我这个分支bug要两天完成,但是issue-404 bug需要5个小时内完成,怎么办呢?还好,Git还提供了一个stash功能,可以把当前工作现场“隐藏起来”,等以后恢复现场后继续工作。如下:

可以看到,当前状态已经干净。
所以现在我们可以通过创建issue-404分支来修复bug了。
首先我们要确定在哪个分支上修复bug,比如我现在是在主分支master上来修复的,现在我们要在master分支上创建一个临时分支,演示如下:

然后修复之后合并到master分支,再把issue-404删掉就行

现在,我们回到dev分支上接着干活,切回dev分支:

工作区是干净的,那么我们的工作现场去哪里了呢,我们可以使用git stash list 查看,如下:

可以看到工作现场还在,Git把stash内容存在某个地方了,但是需要回复一下,可以使用如下两个方法:
1.git stash apply 恢复,恢复后stash内容并不删除,你需要使用git stash drop来删除。
2. git stash pop ,恢复的同时把stash 内容也删除了。

可以看到工作区已经恢复。
多人协作。
当你从远程库克隆的时候,实际上Git自动把本地的master分支和远程的master分支对应起来了,并且远程库的默认名称是origin。
要查看远程库的信息使用git remote
要查看远程库的详细信息使用git remote -v
如下演示:

一:推送分支:
推送分支就是把该分支上所有本地提交到远程库中,推送时,要指定本地分支,这样,Git就会把该分支推送到对应远程分支。
使用命令: git push origin master
比如现在github上的readme.txt代码如下:

本地代码如下:

现在把本地更新的readme.txt代码推送到远程库中,使用命令如下:

可以看到远程同步成功

如果我们现在要推送本地其他分支,比如dev分支,可以:


二、抓取分支:
多人协作时,大家都会往master分支上推送各自的修改。我们可以在另一个目录克隆,新建一个目录名叫testgit2。

现在我们要在dev分支上做开发,就必须把远程的origin的dev分支克隆到本地来,于是可以使用如下命令创建本地dev分支:git checkout -b dev origin/dev

小伙伴开发完(添加了一行123456)把dev分支推送到远程库

小伙伴已经向origin/dev分支上推送了提交,而我在我的testgit目录文件下也对同样的文件同个地方做了修改,也试图推送到远程库时,如下:

由上面可知:推送失败,因为我的小伙伴最新提交和我试图推送的有冲突,解决的办法也很简单,上面提示我们,先用git pull把最新的提交从origin/dev抓下来,然后在本地合并,解决冲突,再推送。

git pull也失败了,原因是没有指定本地dev分支和远程origin/dev分支的链接,根据提示,设置dev和origin/dev的链接。如下:

这回git pull成功,但是合并有冲突,需要手动解决,解决办法和分支管理中的解决冲突完全一样。

因此:多人协作工作模式一般是这样的:
首先,可以试图用git push origin branch-name推送自己的修改,如果失败,则因为远程分支比你的本地更新早,需要先用git pull试图合并。如果合并有冲突 ,则需要解决冲突,并在本地提交,再用git push origin branch-name推送。
参考:
https://blog.csdn.net/u011535541/article/details/83379151
和 https://www.jianshu.com/p/9ffc0d7aae00
和 https://blog.csdn.net/u012273376/article/details/97269998
如有侵权,请联系本人删除,感谢!

浙公网安备 33010602011771号