Git快速入门

@byee

目录

  • Git简介
  • Git基础
  • Git基本操作
  • 多人协作开发

1.Git 是什么鬼?

  • Git分布式版本管理工具

2.版本管理

--版本控制是一种记录若干文件内容变化,以便将来查阅特定版本修订情况的系统

  • 集中化的版本控制系统(CVCS)  eg:CVS
  • 分布式版本控制系统(DVCS)      eg:   Git

Git简介

集中版本控制系统

优点:

  1. 不同系统的开发者协同工作
  2. 保存所有文件的修订版本

 

缺点:

  1. 联网才能工作
  2. 若中央服务器出现故障,影响比较大

分布式版本控制系统

优点:

  1. 每个主机保存完整代码仓库镜像
  2. 提交多个远程仓库
  3. 安全
  4. 分支管理

 

Git 基础

CVS记录差异

Git 直接纪录快照

 

1.保存记录方式

Git 基础

工作区和暂存区

工作流程:

 

1.在工作目录修改文件

 

2.对修改后的文件进行快照,保存在暂存区

 

3.提交更新,将保存在暂存区的文件快照永久转储到Git仓库中

Git 基础

Git对象模型

SHA:

所有的项目历史文件都是通过一个40个字符的(40-digit)“对象名”来索引的,类似:

6ff87c4664981e4397625791c8ea3bbb5f2279a3

该字符是通过对“对象”内容做SHA1哈希计算得来的(SHA1是密码学的哈希算法)。这就意味这不同内容的对象就不可能有相同的“对象名”

好处:

  • Git只需要比较对象名,就可以判断两个对象是否相同
  • Git还可以通过检查对象内容的SHA1值的哈希值和“对象名”是否相同,来判断对象内容是否正确或修改

Git 基础

Git对象模型

对象:

每个对象(Object)包括三个部分:类型、大小和内容

类型:"blob","tree","commit"和"tag"

  • blob:用来存储文件数,通常是一个文件
  • tree:可以理解成目录,它包含一些"tree"(子目录)或"blob"(文件)
  • commit:一个"commit"就指向一个tree,它用来标记某一个特定时间点的状态。它包括一些元数据,如:时间戳、最近一次提交的作者、指向上次提交(commit)的指针等
  • tag:标记某一个提交的

Git 基础

Git对象模型

1.blob对象:通常用来存储文件的内容

git show 6ff87c4664  //使用git show命令来查看内容

 Note that the only valid version of the GPL as far as this project
 is concerned is _this_ particular version of the license (ie v2, not
 v2.2 or v3.x or whatever), unless explicitly otherwise stated.
...

//一个"blob"对象就是一块二进制数据,它没有指向任何东西或有任何其他属性,甚至连文件名都没有
因为blob对象内容全部都是数据,如两个文件在一个目录树(或是一个版本仓库)中有同样的数据内容,那么它们将会共享同一个blob对象。
Blob对象和其所对应的文件所在路径、文件名是否改被更改都完全没有关系。

Git 基础

Git对象模型

2.tree对象:

git show 6ff87c4664  //使用git show命令来查看内容 或者使用git ls-tree 让你看到更多细节

$ git ls-tree fb3a8bdd0ce
100644 blob 63c918c667fa005ff12ad89437f2fdc80926e21c    .gitignore
100644 blob 5529b198e8d14decbe4ad99db3f7fb632de0439d    .mailmap
100644 blob 6ff87c4664981e4397625791c8ea3bbb5f2279a3    COPYING
040000 tree 2fb783e477100ce076f6bf57e4a6f026013dc745    Documentation
100755 blob 3c0032cec592a765692234f1cba47dfdcc3a9200    GIT-VERSION-GEN
100644 blob 289b046a443c0647624607d471289b2c7dcd470b    INSTALL
100644 blob 4eb463797adc693dc168b926b6932ff53f17d0b1    Makefile
100644 blob 548142c327a6790ff8821d67c2ee1eff7a656b52    README
...

Git 基础

Git对象模型

3.Commit对象:


$ git show -s --pretty=raw 2be7fcb476
commit 2be7fcb4764f2dbcee52635b91fedb1b3dcf7ab4
tree fb3a8bdd0ceddd019615af4d57a53f43d8cee2bf
parent 257a84d9d02e90447b149af58b271c19405edb6a
author Dave Watson <dwatson@mimvista.com> 1187576872 -0400
committer Junio C Hamano <gitster@pobox.com> 1187591163 -0700

    Fix misspelling of 'suppress' in docs

    Signed-off-by: Junio C Hamano <gitster@pobox.com>

// 你可以看到一个提交(commit)由以下部分组成:
1.一个tree
2.父对象
3.作者
4.提交者
5.注视 

Git 基础

Git对象模型

4.tag对象:

$ git cat-file tag v1.5.0
object 437b1b20df4b356c9342dac8d38849f24ef44f27
type commit
tag v1.5.0
tagger Junio C Hamano <junkio@cox.net> 1171411200 +0000

GIT 1.5.0
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.6 (GNU/Linux)

iD8DBQBF0lGqwMbZpPMRm5oRAuRiAJ9ohBLd7s2kqjkKlq1qqC57SbnmzQCdG4ui
nLE/L9aUXdWeTFPron96DLA=
=2E+0
-----END PGP SIGNATURE-----

Git 基础

Git对象模型

commit流程

$>tree
.
|-- README
`-- lib
    |-- inc
    |   `-- tricks.rb
    `-- mylib.rb

2 directories, 3 files

Git 基础

Git目录和工作目录

git目录

$>tree -L 1
.
|-- HEAD         # 这个git项目当前处在哪个分支里
|-- config       # 项目的配置信息,git config命令会改动它
|-- description  # 项目的描述信息
|-- hooks/       # 系统默认钩子脚本目录
|-- index        # 索引文件
|-- logs/        # 各个refs的历史信息
|-- objects/     # Git本地仓库的所有对象 (commits, trees, blobs, tags)
`-- refs/        # 标识你项目里的每个分支指向了哪个提交(commit)。

工作目录:

Git"工作目录"存储着你现在检出(checkout)的文件.当你在项目不同分支切换时,工作目录里的文件经常会被替换和删除。所有历史信息都保存在'git目录'中。

Git 基础操作命令

1.生成一个仓库

//获得一个Git仓库,由两种方法:
    1.从已有的Git仓库中,clone
    2.新建一个仓库

//1.clone仓库
    // git://协议较为快速和有效
git clone git://git.kernel.org/pub/scm/git/git.git
    //或者
git clone http://www.kernel.org/pub/scm/git/git.git

//该命令执行结果:会在本目录下生成一个文件夹,
例如. git clone http://git.kernel.org/linux/kernel/git/torvalds/linux-2.6.git 
会建立一个目录叫'linux-2.6')


//2. 初始化一个新的仓库
  mkdir demo
  cd demo
  git init
//Git 会输出Initialized empty Git repository in .git/ 这样就代表着 仓库被新建成功

Git 基础操作命令

2.工作流程

git add files 把当前文件放入暂存区域。
git commit 给暂存区域生成快照并提交。
git reset -- files 用来撤销最后一次git add files,你也可以用git reset 撤销所有暂存区域文件。
git checkout -- files 把文件从暂存区域复制到工作目录,用来丢弃本地修改。
git status //显示当前项目的一个状态

Git 基础操作命令

3.分支&合并

//一个仓库可以维护很多开发分支,现在我们来创建一个叫dev的分支

//新建一个dev分支 新建文件demo1.txt 编辑 并提交
git branch dev //git branch -----list, create, or delete branches
touch 

//切换到dev分支 查看demo1.txt  修改再提交
git checkout dev // git checkout --Checkout a branch or paths to the working tree 

//回到master 分支 并执行 合并 (无冲突和有冲突)
git checkout master
//git merge ---dev Join two or more development histories together

冲突:同一个文件在不同分支或者远程和本地分支按不同的方式修改了

如何解决冲突:

发生冲突,则需要你手动解决完冲突后,将该文件添加到索引区/暂存区(index),然后进行一次提交

Git 基础操作命令

3.0分支&合并(图示)

Git 基础操作命令

3.0分支&合并(图示)

Git 基础操作命令

3.0分支&合并(图示)

Git 基础操作命令

3.0分支&合并(图示)

Git 基础操作命令

3.1分支的撤销

//撤销分支:
 如果你觉得合并之后的状态是一团乱麻,想把当前的修改都放弃,
你可以使用git reset命令回到之前的状态 
如:git reset //Reset current HEAD to the specified state
若加上--hard 参数 reset HEAD, index and working tree
$ git reset --hard HEAD

//你已经把合并之后的代码提交,但是还是想把他们撤销
$ git reset --hard ORIG_HEAD //执行某些情况下,会比较危险。如:如果你把一个已经被另一个分支合并的分支给删了,那么 以后在合并相关的分支时会出错。
快速向前合并:
通常,一个合并会产生一个合并提交(commit),把两个父分支里的每一行都合并起来
但是,如果当前分支和另一个分支没有内容上的差异(即冲突),git就会执行一个"快速向前(fast-forward)"操作,git不会创建新的提交,只是将当前分支指向合并进来的分支

Git 基础操作命令

4.日志操作

//日志操作

      git log //Show commit logs

     git log [<options>]
       options :
      -p        //显示patchs
     --stat     //显示每个提交(commit)中哪些文件被修改了
    --pretty= online //你可以按你的要求来格式化日志输出。‘--pretty'参数可以使用若干表现格式,如‘oneline short',
                        //例如:$ git log --pretty=format:'%h was %an, %ar, message: %s'  
                                $ git log --pretty=format:'%h : %s' --graph
                                $ git log --pretty=format:'%h : %s' --topo-order --graph

  

Git 基础操作命令

5.Diff

//Diff 操作 git diff 是一个难以置信的有用的工具,可以找出你项目上任意两点间 的改动,
或是用来查看别人提交进来的新分支。
git --Show changes between commits, commit and working tree, etc

      
      $ git diff master..test
//上面这条命令只显示两个分支间的差异
    $ git diff 
//上面命令,回显示在当前的工作目录和上次提交与本地索引间的差异

//显示你当前的索引和上次提交间的差异:
$ git diff --cached 

$ git diff HEAD //显示你工作目录与上次提交时之间的所有差别

//更多的比较选项
$ git diff dev   //查看当前的工作目录与另外一个分支的差别

$ git diff dev -- ./lib  你也以加上路径限定符,来只 比较某一个文件或目录

Git 多人协作

Git 多人协作

仓库

源仓库:

1.汇总参与该项目的各个开发者的代码

2.存放趋于稳定和可发布的代码

 

开发者仓库:

fork源仓库,每个开发者仓库是完全独立的,互不干扰。

开发流程:

开发功能-> 提交到自己的仓库->开发完成->向源仓库发送pull request (pr)------分布式开放工作

 

Git 多人协作

分支模型

1.永久性分支:

    - master branch  :主分支

    - develop branch  : 开发分支

 

2. 临时性分支

    - feature branch :功能分支

    - release branch :预发布分支

    - hotfix branch     : bug修复分支

Git 多人协作

//功能开发
step 1: 切换到develop分支

    >>> git checkout develop
step 2: 分出一个功能性分支

    >>> git checkout -b feature-discuss
step 3: 在功能性分支上进行开发工作,多次commit,测试以后...

step 4: 把做好的功能合并到develop中

    >>> git checkout develop

    # 回到develop分支

    >>> git merge --no-ff feature-discuss
    # 把做好的功能合并到develop中

    >>> git branch -d feature-discuss
    # 删除功能性分支

    >>> git push origin develop
    # 把develop提交到自己的远程仓库中
这样,就完成一次功能的开发和提交。

Git 多人协作

release:

预发布分支,当产品即将发布的时候,要进行最后的调整和测试,这时候就可以分出该分支,测试完成之后,就可以将该分支卡发布,并删除。

hotfix:

表示产品已经发布,但是出现重大bug,需要修复,就可以分该分支,bug修复之后,将该分支合并到master分支上

Git 多人协作

工作流(workflow)

1.源仓库的构建

2.开发者fork源仓库

3.将开发者自己的仓库clone到本地

4.构建功能分支进行开发

5.向管理员提交pr

6.管理员测试、合并

Git 多人协作

4.构建功能分支进行开发

 

>>> git checkout develop
    # 切换到`develop`分支

    >>> git checkout -b feature-discuss
    # 分出一个功能性分支

    >> touch discuss.js
    # 假装discuss.js就是我们要开发的功能

    >> git add .
    >> git commit -m 'finish discuss feature'
    # 提交更改

    >>> git checkout develop
    # 回到develop分支

    >>> git merge --no-ff feature-discuss
    # 把做好的功能合并到develop中

    >>> git branch -d feature-discuss
    # 删除功能性分支

    >>> git push origin develop
    # 把develop提交到自己的远程仓库中

Git 多人协作

6.管理员测试、合并

 

//管理员的一般测试、合并流程

1.对代码进行review
2.在它的本地测试新建一个测试分支,测试某人pr的代码
如:
 >> git checkout develop
    # 进入他本地的develop分支

    >> git checkout -b livoras-develop
    # 从develop分支中分出一个叫livoras-develop的测试分支测试我的代码

    >> git pull https://github.com/livoras/git-demo.git develop
    # 把我的代码pull到测试分支中,进行测试
    
2.1 如果测试成功


 >> git checkout develop
    >> git merge --no-ff livoras-develop
    >> git push origin develop
Made with Slides.com