概述
Git 是一个开源的分布式版本控制系统, 是 Linus Torvalds 为了帮助管理 Linux 内核开发而开发的一个开放源码的版本控制软件。
Git没有中央版本库的概念,每个客户端都可成为版本库,内部采用全量方式对文件的每次提交建立快照并存储(若文件内容变化产生重新存储)。
Git存储的文件命名规则采用SHA-1算法对文件内容计算而来,计算结果是一个40字符的串字符串,前2位表示文件夹名,后面38位表示对象名,所以每个文件对应的对象只要内容不一样,对象不会重复。
Git将文件内容是按元数据方式存储,不像其他版本管理工具采用文件和增量(例如SNV、CVS)。
下面从如下几个方面介绍下其相关理论:
1、基本概念
2、对象模型
3、内部组织
4、文件状态
5、工作流
6、通信协议
1、基本概念
HEAD: 当前版本的指针,当切换本地版本的时候会快速指向指定版本文件
master:Git默认创建的主分支
origin: Git默认创建的远程仓库的名称
工作区:本地电脑里的目录。
暂存区(stage 或 index):一般存放在 .git 目录下的 index 文件(.git/index)中,所以有时也叫作索引(index)。
本地版本库:工作区有一个隐藏目录 .git,这个不算工作区,而是 Git 的版本库。
远程版本库:存在于另一台电脑上的Git版本库,一般都是服务器(Git服务器),服务器上只有裸库,没有工作区。
注意:为了区别本地和远程版本库,所以本地就叫本地版本库,远程就叫远程版本库,对于Git本身二者一样。在实际生产应用中, 一般大家为了集中管理和共享代码,都会建立一个共享代码库(俗称:远程中央仓库)。
对象:Git内部存储都是以一系列对象为单位进行存储,然后通过一定逻辑规则,将对象联系在一起。
目录树:Git内部的文件组织结构,主要包括如下一些核心目录及文件,例如:
.git:git内部组织。
工作区:平时的工作目录,.git目录也位于该目录下。
.git/hooks:存放一些其他脚本,用于扩展Git的功能,Git引擎会自动执行存放于该目录的相应脚本,用以扩展Git的功能。
.git/info:存放仓库的一些基本信息。
.git/logs:该目录包括每个分支的历史,包括提交的父子关系、分支的重置、分支的合并、分支的重命名等等。
.git/objects:该目录包括所有的对象,包括提交对象,树对象,数据对象。对象的sha1值有40位,前两位作为文件夹名,后38位作为文件名。
.git/refs:该目录包含每个本地分支heads下,每个本地标签tags下,远程仓库信息remotes下(包括所有远程分支及tag)。
config文件:仓库的配置信息
index文件:暂存区的状态,通过该文件,可以生成树对象。
HEAD文件:当前分支信息
2、对象模型:
每个对象(object) 包括三个部分:类型,大小和内容。大小就是指内容的大小,内容取决于对象的类型,有四种类型的对象:"blob"、"tree"、 "commit" 和"tag"。
blob:仅仅表示数据内容,只要内容一致blob就一致,和其关联的目录结构没有任何关系。
tree:表示内容之间的目录层次关系,包含一系列条目,可以包括其他tree、blob。
commit:表示一次提交描述,只指向一个tree,用来标记项目某一个特定时间点的状态,包括tree、parent、作者、提交者、注释。
tag:表示对某个提交做标记,包括object(关联commit的SHA1签名), 对象类型, 标签创建人的名字("tagger"), 还有一条可能包含有签名(signature)的消息
3、内部组织:
Git内部通过一定逻辑规则,将上面的四个简单对象组织在一起形成一套文件系统,底层仍旧使用操作系统的文件系统。
其中:
blob:是最小的逻辑单元
tree:由一些其他tree和blob组成,类似操作系统的目录(tree)和文件(blob)
commit:指向一个tree
tag:指向一个commit,是对某个commit的固定标记
4、文件状态:
Git有四种文件状态,分别是未跟踪(Untracked)、未修改(Unmodify)、已修改(Modified)、暂存状态(Staged)。
Untracked: 未跟踪, 此文件在工作区中, 但并没有加入到git库, 不参与版本控制. 通过git add 状态变为Staged.
Unmodify: 未修改,文件已经入版本库, 但未修改, 即版本库中的文件快照内容与文件夹中完全一致. 这种类型的文件有两种去处, 如果它被修改, 而变为Modified. 如果使用git rm移出版本库, 则成为Untracked文件
Modified: 已修改,文件已修改, 仅仅是修改, 并没有进行其他的操作. 这个文件也有两个去处, 通过git add可进入暂存区成为暂存staged状态, 使用git checkout 则丢弃修改过, 返回到unmodify状态, 这个git checkout即从库中取出文件, 覆盖当前修改
Staged: 暂存状态. 执行git commit则将修改同步到库中, 这时库中的文件和本地文件又变为一致,文件为Unmodify状态. 执行git reset HEAD filename取消暂存, 文件状态为Modified
5、工作流
Git工作流分为下面几种形式:
5.1、集中式工作流
和SVN一样,该形式有一个中央仓库,所有的修改都提交到了Master分支上,这种方式与SVN的主要区别就是开发人员有本地库。Git很多特性并没有用到。
5.2、GitFlow工作流
按Git推荐标准预设一些分支,主要包括:
主干分支master、开发分支develop、修复分支hotfix、预发布分支release、功能分支feature
实际应用可根据需要设计不同的分支,让发布迭代过程更符合实际需要。
5.3、Forking工作流
在 GitFlow 基础上, 充分利用了 Git 的 Fork 和 pull request 的功能以达到代码审核的目的。
6、通信协议
Git支持下面一些通信协议,具体有HTTP、HTTPS、SSH、GIT