学习 Pro Git 一书的学习笔记。
采用教材:Pro Git 中文版
一、起步
关于版本控制
- 本地版本的控制 rcs 保存并管理文件补丁(patch)
- 集中化的版本控制系统 CVS SubVersion Perfoce, 有集中的服务器管理版本,本地每次获得最新版本代码。
- 分布式版本控制系统
Git 历史
2005年一直免费试用的 分布式版本控制系统 BitKeeper 的商业公司停止了对 Linux 的免费授权, Linus 就带领社区撸了一个分布式版本管理系统。
git 基础概念
- 文件快照,直接保存文件,而不是差异比较
- 本地操作 可以不用连接网络仓库 疯狂提交代码
- 时刻保证数据完整性
文件的三个状态
- 已提交
- 已修改
- 已暂存
git 安装和配置
安装
源码安装,或者编译包安装。
配置:
配置和查看 git 环境:
git config 实际上调用的是 git-config 命令,但是至今输入git-config 找不到这个命令
git config —sytem 配置系统环境 系统所有用户通用的配置
git config —global 配置当前用户环境 在 ~/.gitconfig 目录下配置。
git config 设置当前项目的配置 在.git/config目录下记录
git config —list 查看所有配置信息
获得帮助信息。
git help config
git config –help
man git-config
二、Git 基础
git init 初始化仓库
git add *.java
git add README
git commit -m “first commit”
克隆现有的项目
git clone
检查当前文件状态。
git status
有没有跟踪的文件 或者有修改 的文件会在这里显示。
$ vim README
$ git status
On branch master
Untracked files:
(use “git add
README
nothing added to commit but untracked files present (use “git add” to track)
同样 如果仓库clean 也会显示出来。
$ git status
On branch master
nothing to commit, working directory clean
跟踪新文件
git add README
再次执行 git status
1 | $ git status |
git add 添加文件到暂存区
暂存已修改的文件 已经改被跟踪的文件 再次修改,
添加到缓存区后 ,再次修改, 会看到两个该文件显示出来
$ vim benchmarks.rb
$ git status
On branch master
Changes to be committed:
(use “git reset HEAD
new file: README
modified: benchmarks.rb
Changes not staged for commit:
(use “git add
(use “git checkout –
modified: benchmarks.rb
顺便学习到的 命令
废弃本次修改
(use “git checkout –
从缓冲区中撤回
(use “git reset HEAD
忽略部分文件。
编译好的的文件,日志文件, 编辑器生成的临时备份文件 等等不需要上传到代码仓库
可以在 .gitignore 文件中配置忽略文件
最好一开始就变就好,免得不需要的文件被提交。
gitignore文件规则:
- 空行或者# 开头的会被git忽略。
- 可以使用标准的 glob 模式匹配。
- 匹配模式最后跟反斜杠(/)说明要忽略的是目录。
- 要忽略指定模式以外的文件或目录,可以在模式前加上惊叹号(!)取反。
所谓的 glob 模式是指 shell 所使用的简化了的正则表达式。星号(*)匹配零个或多个任意字符;[abc] 匹配任何一个列在方括号中的字符(这个例子要么匹配一个 a,要么匹配一个 b,要么匹配一个 c);问号(?)只匹配一个任意字符;如果在方括号中使用短划线分隔两个字符,表示所有在这两个字符范围内的都可以匹配(比如 [0-9] 表示匹配所有 0 到 9 的数字)。
我们再看一个 .gitignore 文件的例子:1
2
3
4
5
6
7
8
9
10
11
12
13
14
15# 此为注释 – 将被 Git 忽略
# 忽略所有 .a 结尾的文件
*.a
# 但 lib.a 除外
!lib.a
# 仅仅忽略项目根目录下的 TODO 文件,不包括 subdir/TODO
/TODO
# 忽略 build/ 目录下的所有文件
build/
# 会忽略 doc/notes.txt 但不包括 doc/server/arch.txt
doc/*.txt
# ignore all .txt files in the doc/ directory
doc/**/*.txt
A **/ pattern is available in Git since version 1.8.2.
采用
git commit 提交。
加上-v可以显示更多的详细的改变信息。
git commit -v
处理的文本编辑器 # 开头的会被好忽略,首行空着用来输入提交记录。
也可以用过 git commit -m “提交说明” 的方式直接提交。
加上 -a 参数可以跳过 git add的步骤。
如果文件都是一件被 add 过的话
git commit -a -m “不用 git add 的提交。 “
移除文件
本地磁盘删除文件
rm filename
查看 git status
得到 Changes not staged for commit:
$ git status
On branch master
Changes not staged for commit:
(use “git add/rm
(use “git checkout –
deleted: grit.gemspec
no changes added to commit (use “git add” and/or “git commit -a”)
所以需要在git 中移除文件
git rm finame
加上 -f f是 force的缩写,可以删除 修改过并且已经放到暂存区域的文件。
从暂存区删除 ,但是本地仓库保留。
这个适用于不小心把一个写大的文件加入到了仓库跟踪中,可以用这样的办法仅仅去掉跟踪。
git rm –cached video.mp4
移动文件
git mv file_from file_to
1 | TODO 实验,名字从小写改成大写。 之前的操作似乎是不敏感的, 尝试用 git mv 操作。 |
查看提交历史
git log
不加参数看全部的提交记录,
git log -p 附带每次提交的差异比较
-2 表示查看最近2条记录。
–word-diff 单词层面的比较。
得到结果:
会有如下: git [-init-]{+in0t+}
[- -]中的是删除的单词, {+ +} 中是新插入的单词。
加上 -U1 可以让上下文的行数从 默认3行变为1行。
其他的参数
–stat,仅显示简要的增改行数统计
–pretty 稍微简约一些的展示方式。
1 | commit d2af3ae2b9e7b08f5f734ce81ac0cee21e4a7c38 |
–oneline 每个提交展示在一行
1 | d2af3ae test 2nd word diff |
–graph 简单的图形化展示 展示演变
1 | git log --pretty=oneline |
format 可以指定显示格式 方便写程序提取分析
1 | $ git log --pretty=format:"%h - %an, %ar : %s" |
搜索提交记录查看日志
git log –grep=”题型”
git log –grep=”题型” –grep=”商务” –all-match
同时满足两个条件 需要加上–all-match
查看指定目录或者文件的历史记录
git log – build.gradle
–author=JerryZhang 指定作者 查看提交记录
图形化工具 gitk 查看。
撤销操作
提交后发现,少了几个文件,或者提交信息写错了,可以撤销重新提交
直接修改提交信息:git commit –amend
忘记文件:直接添加文件后,输入 git commit –amend
1 | $ git commit -m 'initial commit' |
取消已经暂存的文件,这个在git status 查看的时候就有提醒。
git reest HEAD filename
取消对文件的修改, 这个在 git status查看时也有提醒。
git checkout – filename
远程仓库的使用
clone 的仓库执行 git remote 后至少可以看到一名为 origin (默认远程库名)的远程仓库。
git remote -v
可以显示对于的克隆地址
1 | ➜ ProGitBlog git:(master) git remote -v |
如果有多个远程仓库,此时会全部列出
1 | $ git remote -v |
添加远程仓库
git remote add [shortname] [url]:
$ git remote add pb git://github.com/paulboone/ticgit.git
$ git remote -v
origin git://github.com/schacon/ticgit.git
pb git://github.com/paulboone/ticgit.git
可以用 pb 指代 paulboone 用户的 ticgit 仓库了。
从远程仓库抓取信息。
git fetch 可以抓取本地没有 远程有的信息。
git fetch pb
抓取后可以看到所有 pb 远程的所有信息。
git fetch 只抓取数据 没有合并。
git pull 抓取数据并且合并到当前的工作分支
git push [remote-name] [branch-name]
推送数据到远程分支 , 默认是 orgin仓库, master分支
查看远端仓库信息
git remote show origin
1 | ➜ ProGitBlog git:(master) git remote show origin |
列出了所有跟踪中的远端分支,
Local ref configured for ‘git push’: 默认的push 分支,
Local branch configured for ‘git pull’: pull自动合并的分支
Stale tracking branches (use ‘git remote prune’) 本地被跟踪,但是远端已经删除的分支
New remote branches (next fetch will store in remotes/origin) 远程有,还没同步的本地的分支
远程仓库的删除和重命名
git remote rename 修改仓库的简称
git remote rename pb paul pb 改为 paul
移除
$ git remote rm paul
打标签
发布某个版本,打一个标签。
列出所有标签
git tag
可以加上约束条件,列出符合条件的tag (只列出2.2相关的tag)
➜ platform git:(feature/3.1.0(Iron_Man)) ✗ git tag -l ‘2.2*’
2.2.0
2.2.1
2.2.2
2.2.3
2.2.4
新建标签
分两种:轻量级的(lightweight)和 含附注的(annotated)
轻量级,仅仅是一个提交对象引用;含附注的可以带有信息, 有自己的说明,邮箱,标签名字
一般都是含附注的
创建一个tag :
git tag -a v1.4 -m “my version 1.4”
git show [tagname]
查看标签信息,
1 | tag v0.1 |
签署标签
如果你有自己的私钥,还可以用 GPG 来签署标签. -s signed的首字母
$ git tag -s v1.5 -m ‘my signed 1.5 tag’
1 | todo 执行失败 不明白做什么用的 |
轻量级标签
git tag v1.4-lw
直接创建 不加参数。
验证标签
可以使用 git tag -v [tag-name] (译注:取 verify 的首字母)的方式验证已经签署的标签。此命令会调用 GPG 来验证签名,所以你需要有签署者的公钥,存放在 keyring 中,才能验证:
$ git tag -v v1.4.2.1
从某次提交创建标签
$ git tag -a v1.2 9fceb02
后面跟上这次提交对象的校验和(或前几位字符就可以)
分享标签。
标签推到远端仓库
git push origin [tagname]
一次性推送所有tag到远端
$ git push origin –tags
1 | ➜ ProGitBlog git:(master) git push origin --tags |
其他人克隆后也可以看到这些标签
技巧和窍门
自动补全:
git源代码中的contrib/completion/git-completion.bash文件
改名字(加上点后)。
cp git-completion.bash ~/.git-completion.bash
配置到自己的环境变量文件中:
source ~/.git-completion.bash
两次tab可以不全命令或者参数
别名:1
2
3
4
5
6$ git config --global alias.co checkout
$ git config --global alias.br branch
$ git config --global alias.ci commit
$ git config --global alias.st status
$ git config --global alias.unstage 'reset HEAD --'
$ git config --global alias.last 'log -1 HEAD'
别名启用外部命令:
自己写了写脚本,加上! 就可以执行
设置用 git visual 启动 gitk:
$ git config –global alias.visual ‘!gitk’
第三章:Git 分支模型
几乎都支持分支,分支可以让你离开主线工作,做其他事情,然后再回来,这个过程大多很昂贵。
Git 切换分支快速,方便。有人把 Git 的分支模型称为“必杀技特性”