大神廖雪峰git教程
1、Git初始化配置:
git config --global user.email xxxxx@xx.com # 邮箱
git config --global color.ui true # 语法高亮
git config --list # 查看配置
2、Git流程: 工作区 --> 缓存区 --> 代码仓库
3、Git版本管理:
git init 初始化git项目目录
git status 查看当前目录git状态
git add file 把指定文件提交到stage区域
git add . 把所有修改过的文件提交到stage区域
git commit -m "comment" 把stage区域的文件提交到Registory中
git log 查看commit日志
git log --pretty=oneline 简化打印日志
git reflog 查看详细的操作日志,包括提交、回滚
git reset --hard HEAD^ 回滚到上一个版本
git reset --hard 232323 回滚到指定版本
git diff file 查看上一次add后,工作区文件内容的变化
git reset HEAD file 将Stage缓存区的的修改撤销(unStage),重新放回工作区
git checkout -- file 丢弃工作区的修改或删除
git rm file 从版本库中删除文件,需要使用git commit
4、git registory连接方式
注意:上传代码前需要将本机ssh-public-key添加到github账号
使用https方式连接:
git remote add origin https@github.com:vincenshen/LearnGit.git
使用SSH方式连接:
git remote add origin git@github.com:vincenshen/LearnGit.git
代码上传:
git push -u origin master (第一次上传,后面就可以省略到 -u)
下载代码:
git clone git@github.com:vincenshen/LearnGit.git
修改git registory地址
$ cat .git/config
[core]
repositoryformatversion = 0
filemode = false
bare = false
logallrefupdates = true
symlinks = false
ignorecase = true
[remote "origin"]
#url = https://github.com/vincenshen/First_Git_Project.git
url = git@github.com:vincenshen/First_Git_Project.git # 增加这一行
fetch = +refs/heads/*:refs/remotes/origin/*
ssh-keygen.exe 生成rsa_key
将pulic key复制到github上账户的settings --> ssh key --> new ssh key
5、分支管理
git branch 查看分支
git checkout -b branch-name 创建分支,并切换到分支
git checkout branch-name 切换到分支
git checkout master 切换到master
bug分支管理:
git stash 将工作区修改内容保存到临时工作区
git stash apply 恢复stash区的内容
git stash pop 恢复stash去的内容,并删除stash
总结:修复bug时,我们会通过创建新的bug分支进行修复,然后合并,最后删除;
当手头工作没有完成时,先把工作现场git stash
一下,然后去修复bug,修复后,再git stash pop
,回到工作现场。
删除分支:
git branch -d branch-name 删除分支
git branch -D branch-name 强行删除分支
6、合并分支
1、git pull origin master 去远程获取最新的master代码
2、git merge branch-name 合并分支(需要在master中去合并分支)
3、git push origin master 将合并后的代码push到远程master
7、解决冲突
如果在dev分支修改并commit,然后在master修改并commit. 就会出现以下情况:
这种情况下,Git无法执行“快速合并”,只能试图把各自的修改合并起来,但这种合并就可能会有冲突,我们试试看:
git merge dev002:
这种情况下,Git无法执行“快速合并”,只能试图把各自的修改合并起来,但这种合并就可能会有冲突.
git status:
果然冲突了!Git告诉我们,readme.txt文件存在冲突,必须手动解决冲突后再提交。git status
也可以告诉我们冲突的文件
我们可以直接查看readme.txt的内容:
Git is a version control system.
Git is free software.
Git is a distributed version control system.
<<<<<<< HEAD
Hello World! Master by Rick.
=======
add branch dev002
>>>>>>> dev002
Git用<<<<<<<
,=======
,>>>>>>>
标记出不同分支的内容,我们修改如下后保存:
Git is a version control system.
Git is free software.
Git is a distributed version control system.
Hello World! Master by Rick.
再次提交:
git add.
git commit -m "conflict fixed"
现在,master
分支和feature1
分支变成了下图所示:
用带参数的git log
也可以看到分支的合并情况:
$ git log --graph --pretty=oneline
* a344668691a6e66b4b14246d1b4e6d1250940274 conflict fixed
|
| * c3c74eccc08601ca175daf3c28135db83e44ef33 create in branch dev002
| * 9d494f7ea902ed9f751bcdce5fd6d430cb690edb change readme
* | 08b9c42dae7bfcc7c5f743c7a981b7fbbdf12d5c change by rick
* | 4036b0f06db83002b3bb228b840bdc333a8265db master
|/
* 0053ade85e938aff96fe25ec94e5d1c3cd218bef Merge branch 'dev001'
|
| * 3e9eeea215af70066c0ad63119e68bb8ca9168db change Readme
* | 8bd4b503b0dae48ceeb87526d6a5c7a98e6b283c delete file
|/
* 6a1f9db9c8ea8c2885402bc6d4a8b548211451dc add new file
* a6bf20cb5e8cf4e3e2b4d9ef49213cb721adff85 add distributed
* efcdecf3d67f2b49344242ce6ec8c5ba6adfd906 write a readme file
解决冲突后,就可以使用 git push origin master 将最新代码上传到Registory.
8、分支管理策略
通常,合并分支时,如果可能,Git会默认用Fast forward
模式,但这种模式下,删除分支后,会丢掉分支信息。
如果要强制禁用Fast forward
模式,Git就会在merge时生成一个新的commit,这样,从分支历史上就可以看出分支信息。
首先分支任然正常操作: git add . git commit -m "branch" git checkout master
准备合并dev
分支,请注意--no-ff
参数,表示禁用Fast forward
:
$ git merge --no-ff -m "merge with no-ff" dev001
Merge made by the 'recursive' strategy.
readme.txt | 1 +
1 file changed, 1 insertion(+)
因为本次合并要创建一个新的commit,所以加上-m
参数,把commit描述写进去。
合并后,我们用git log
看看分支历史:
$ git log --graph --pretty=oneline* 7825a50 merge with no-ff
|
| * 6224937 add merge
|/
* 59bc1cb conflict fixed
...
可以看到,不使用Fast forward
模式,merge后就像这样:
分支策略
在实际开发中,我们应该按照几个基本原则进行分支管理:
首先,master
分支应该是非常稳定的,也就是仅用来发布新版本,平时不能在上面干活;
那在哪干活呢?干活都在dev
分支上,也就是说,dev
分支是不稳定的,到某个时候,比如1.0版本发布时,再把dev
分支合并到master
上,在master
分支发布1.0版本;
你和你的小伙伴们每个人都在dev
分支上干活,每个人都有自己的分支,时不时地往dev
分支上合并就可以了。
所以,团队合作的分支看起来就像这样:
小结
Git分支十分强大,在团队开发中应该充分应用。
合并分支时,加上--no-ff
参数就可以用普通模式合并,合并后的历史有分支,能看出来曾经做过合并,而fast forward
合并就看不出来曾经做过合并。
9、.gitignore 忽略上传文件
https://github.com/github/gitignore 可以去这个project下载python专用ignore或者在创建repostroy时自动生成该文件。
只需要将文件名或者文件夹名添加到该gitignore文件中,在push的时候就会自动忽略。
10、多人协作
-
查看远程库信息,使用
git remote -v
; -
本地新建的分支如果不推送到远程,对其他人就是不可见的;
-
从本地推送分支,使用
git push origin branch-name
,如果推送失败,先用git pull
抓取远程的新提交; -
在本地创建和远程分支对应的分支,使用
git checkout -b branch-name origin/branch-name
,本地和远程分支的名称最好一致; -
建立本地分支和远程分支的关联,使用
git branch --set-upstream branch-name origin/branch-name
; -
从远程抓取分支,使用
git pull
,如果有冲突,要先处理冲突。 - 如果
git pull
提示“no tracking information”,则说明本地分支和远程分支的链接关系没有创建,用命令git branch --set-upstream branch-name origin/branch-name
。
11、标签管理
git中有两种标记版本的方式,一个是 branch 一个是 tag
发布一个版本时,我们通常先在版本库中打一个标签(tag),这样,就唯一确定了打标签时刻的版本。将来无论什么时候,取某个标签的版本,就是把那个打标签的时刻的历史版本取出来。所以,标签也是版本库的一个快照。
Git的标签虽然是版本库的快照,但其实它就是指向某个commit的指针(跟分支很像对不对?但是分支可以移动,标签不能移动),所以,创建和删除标签都是瞬间完成的。
Git有commit,为什么还要引入tag?
“请把上周一的那个版本打包发布,commit号是6a5819e...”
“一串乱七八糟的数字不好找!”
如果换一个办法:
“请把上周一的那个版本打包发布,版本号是v1.2”
“好的,按照tag v1.2查找commit就行!”
所以,tag就是一个让人容易记住的有意义的名字,它跟某个commit绑在一起。
-
命令
git tag <name>
用于新建一个标签,默认为HEAD
,也可以指定一个commit id; -
git tag -a <tagname> -m "blablabla..."
可以指定标签信息; -
命令
git tag
可以查看所有标签。
-
命令
git push origin <tagname>
可以推送一个本地标签; -
命令
git push origin --tags
可以推送全部未推送过的本地标签; -
命令
git tag -d <tagname>
可以删除一个本地标签; -
命令
git push origin :refs/tags/<tagname>
可以删除一个远程标签。
12、代码merge管理工具
beyond compare