Git 是当前流行的分布式版本控制管理工具,最初由 Linux Torvalds (Linux 之父) 创造,于 2005 年发布。

官网地址:https://git-scm.com/

Git诞生:https://www.liaoxuefeng.com/wiki/896043488029600/896202815778784

版本控制

什么是 版本控制?我为什么要关心它呢?

版本控制是一种记录一个或若干文件内容变化,以便将来查阅特定版本修订情况的系统。 我们通常对保存着软件源代码的文件作版本控制,但实际上,你可以对任何类型的文件进行版本控制。

如果你是位图形或网页设计师,可能会需要保存某一幅图片或页面布局文件的所有修订版本(这或许是你非常渴望拥有的功能),采用版本控制系统(VCS)是个明智的选择。 有了它你就可以将某个文件回溯到之前的状态,甚至将整个项目都回退到过去某个时间点的状态,你可以比较文件的变化细节,查出最后是谁修改了哪个地方,从而找出导致怪异问题出现的原因,又是谁在何时报告了某个功能缺陷等等。

使用版本控制系统通常还意味着,就算你乱来一气把整个项目中的文件改的改删的删,你也照样可以轻松恢复到原先的样子。 但额外增加的工作量却微乎其微。

版本控制系统应具备功能

协同修改:多人并行不悖的修改 服务器端的同一个文件。 数据备份:不仅保存目录和文件的当前状态,还能够保存每一个提交过的历史状态。 版本管理:在保存每一个版本的文件信息的时候要做到不保存重复数据,以节约存储空 间,提高运行效率。这方面SVN 采用的是增量式管理的方式,而Git 采取了文 件系统快照的方式。 权限控制:对团队中参与开发的人员进行权限控制。对团队外开发者贡献的代码进行审核——Git 独有。 历史记录:查看修改人、修改时间、修改内容、日志信息。将本地文件恢复到某一个历史状态。 分支管理:允许开发团队在工作过程中多条生产线同时推进任务,进一步提高效率。

集中式与分布式的不同

Git 采用与 CSV/SVN 完全不同的处理方式,前者采用分布式,而后面两个都是集中式的版本管理。

先说集中式版本控制系统,版本库是集中存放在中央服务器的,而干活的时候,用的都是自己的电脑,所以要先从中央服务器取得最新的版本,然后开始干活,干完活了,再把自己的活推送给中央服务器。中央服务器就好比是一个图书馆,你要改一本书,必须先从图书馆借出来,然后回到家自己改,改完了,再放回图书馆。

集中式版本控制系统最大的毛病就是必须联网才能工作,如果在局域网内还好,带宽够大,速度够快,可如果在互联网上,遇到网速慢的话,可能提交一个10M的文件就需要5分钟,这还不得把人给憋死啊。

那分布式版本控制系统与集中式版本控制系统有何不同呢?首先,分布式版本控制系统根本没有 “中央服务器”,每个人的电脑上都是一个完整的版本库,这样,你工作的时候,就不需要联网了,因为版本库就在你自己的电脑上。既然每个人电脑上都有一个完整的版本库,那多个人如何协作呢?比方说你在自己电脑上改了文件 A,你的同事也在他的电脑上改了文件 A,这时,你们俩之间只需把各自的修改推送给对方,就可以互相看到对方的修改了。

和集中式版本控制系统相比,分布式版本控制系统的安全性要高很多,因为每个人电脑里都有完整的版本库,某一个人的电脑坏掉了不要紧,随便从其他人那里复制一个就可以了。而集中式版本控制系统的中央服务器要是出了问题,所有人都没法干活了。

在实际使用分布式版本控制系统的时候,其实很少在两人之间的电脑上推送版本库的修改,因为可能你们俩不在一个局域网内,两台电脑互相访问不了,也可能今天你的同事病了,他的电脑压根没有开机。因此,分布式版本控制系统通常也有一台充当 “中央服务器” 的电脑,但这个服务器的作用仅仅是用来方便 “交换” 大家的修改,没有它大家也一样干活,只是交换修改不方便而已。

SVN与Git的最主要的区别

SVN是集中式版本控制系统,版本库是集中放在中央服务器的,而干活的时候,用的都是自己的电脑,所以首先要从中央服务器哪里得到最新的版本,然后干活,干完后,需要把自己做完的活推送到中央服务器。集中式版本控制系统是必须联网才能工作,如果在局域网还可以,带宽够大,速度够快,如果在互联网下,如果网速慢的话,就纳闷了。

Git是分布式版本控制系统,那么它就没有中央服务器的,每个人的电脑就是一个完整的版本库,这样,工作的时候就不需要联网了,因为版本都是在自己的电脑上。既然每个人的电脑都有一个完整的版本库,那多个人如何协作呢?比如说自己在电脑上改了文件A,其他人也在电脑上改了文件A,这时,你们两之间只需把各自的修改推送给对方,就可以互相看到对方的修改了。

Git 三大区域

  • 工作区(Working Directory)
  • 暂存区(Staging Area)
  • 版本库(Repository)

使用Git的时候有3个工作区的概念:Git 仓库、工作目录以及暂存区域。其中工作目录比较好理解,就是我们开发时修改文件的那些目录,Git 仓库就是我们项目目录下面的 .git目录中的内容,而暂存区域是保存已经被Git标记过,将要提交保存到Git数据库中的文件的地方

文件从我们创建到编辑完提交Git帮我们记录,一共要经历3种状态:已修改(modified)、 已暂存(staged)已提交(committed)

  • 刚刚开始时编辑文件,这个时候文件是处于 已修改(modified) 状态,文件是在工作目录
  • 修改完文件,我们执行git add,这个时候文件就变为 已暂存(staged)状态,文件信息进入暂存区域,内容被保存到Git数据库中
  • 然后我们执行git commit,文件就变为已提交(committed)状态,创建了一个提交记录保存到了Git 仓库

Git命令行管理版本

想要让Git对一个目录进行版本控制需要以下几个步骤:

  • 进入要管理的文件夹
  • 执行初始化命令
  • 管理目录下的文件状态
  • 管理指定文件
  • 生成版本
  • 查看版本记录

创建版本库

什么是版本库呢?版本库又名仓库,英文名repository,你可以简单理解成一个目录,这个目录里面的所有文件都可以被Git管理起来,每个文件的修改、删除,Git都能跟踪,以便任何时刻都可以追踪历史,又或者在将来某个时刻可以 还原 某个指定版本

创建一个版本库非常简单,首先,选择一个合适的地方,创建一个空目录,也不一定必须在空目录下创建Git仓库,选择一个已经有东西的目录也是可以的

创建目录

  1. $ mkdir gitRepository

可以使用dos命令创建也可以右键新建文件夹,创建一个空文件夹。

进入创建的目录

  1. $ cd gitRepository/

查看当前目录的位置

  1. $ pwd
  2. /e/gitRepository

执行初始化命令

通过git init命令把这个目录变成Git可以管理的仓库:

  1. $ git init
  2. Initialized empty Git repository in E:/gitRepository/.git/

Git就把仓库建好了,而且告诉你是一个空的仓库(empty Git repository),当前目录下多了一个.git的目录,这个目录是Git来跟踪管理版本库的,没事千万不要手动修改这个目录里面的文件,不然改乱了,就把Git仓库给破坏了。

如果你没有看到.git目录,那是因为这个目录默认是隐藏的,用ls -ah命令就可以看见。或者在资源管理器中设置隐藏的项目即可查看。

Git基础教程 - 图1

管理和查看文件状态

查看文件状态

  1. git status

管理文件:

  1. git add 文件名 # 管理指定文件
  2. git add . # 管理指定全部修改过的文件

管理后的文件会从 红色 绿色

生成版本

  1. git commit -m '描述信息'

简单解释一下git commit命令,-m后面输入的是本次提交的说明,可以输入任意内容,当然最好是有意义的,这样你就能从历史记录里方便地找到改动记录。

嫌麻烦不想输入-m "xxx"行不行?确实有办法可以这么干,但是强烈不建议

git commit命令执行成功后会告诉你,1 file changed:1个文件被改动(我们新添加的readme.txt文件);2 insertions:插入了两行内容(readme.txt有两行内容)。

查看版本记录

在实际工作中,我们脑子里怎么可能记得一个几千行的文件每次都改了什么内容,不然要版本控制系统干什么。版本控制系统肯定有某个命令可以告诉我们历史记录,在Git中,我们用git log命令查看:

  1. git log

git log命令显示从最近到最远的提交日志。如果嫌输出信息太多,看得眼花缭乱的,可以试试加上--pretty=oneline参数:

  1. $ git log --pretty=oneline
  2. edc39f3a3bb12b154914e9338862f56934247beb (HEAD -> master) 第三次提交
  3. bd58d63cba06cf63a83b75b9302a445a8693d4d3 第二次添加
  4. d47037d191d3b7f3a2867bab4c9289fe180b984a gitTest1第一次添加
  5. c0a8218e729190384186d65ce6b356165e5d7b5e 第一次创建三个文件

版本回退

现在,你已经学会了修改文件,然后把修改提交到Git版本库

像这样,你不断对文件进行修改,然后不断提交修改到版本库里,就好比玩RPG游戏时,每通过一关就会自动把游戏状态存盘,如果某一关没过去,你还可以选择读取前一关的状态。有些时候,在打Boss之前,你会手动存盘,以便万一打Boss失败了,可以从最近的地方重新开始。Git也是一样,每当你觉得文件修改到一定程度的时候,就可以“保存一个快照”,这个快照在Git中被称为commit。一旦你把文件改乱了,或者误删了文件,还可以从最近的一个commit恢复,然后继续工作,而不是把几个月的工作成果全部丢失。

首先Git必须知道当前版本是哪个版本,在Git中用HEAD表示当前版本,上一个版本就是HEAD^,上上一个版本就是HEAD^^,当然往上100个版本写100个^比较容易数不过来,所以写成HEAD~100

回退到之前的版本

当前版本回退到上一个版本,就可以使用git reset命令,这样我们就回退到指定的版本了

  1. git log
  2. git reset --hard 版本号

回退到之后的版本

假如你回退到了某个版本,突然又想想恢复到新版本应该怎么办?

在Git中,总是有后悔药可以吃的。当你用git reset --hard HEAD^回退到指定版本时,再想恢复到未回退版本,就必须找到未回退版本的commit id。Git提供了一个命令git reflog用来记录你的每一次命令:

  1. git reflog
  2. git reset --hard 版本号

版本号没必要写全,前几位就可以了,Git会自动去找。当然也不能只写前一两位,因为Git可能会找到多个版本号,就无法确定是哪一个了。

  • HEAD指向的版本就是当前版本,因此,Git允许我们在版本的历史之间穿梭,使用命令git reset --hard commit_id
  • 穿梭前,用git log可以查看提交历史,以便确定要回退到哪个版本。
  • 要重返未来,用git reflog查看命令历史,以便确定要回到未来的哪个版本。

Git分支

分支概述可参考:https://www.liaoxuefeng.com/wiki/896043488029600/896954848507552

分支命令的使用

  1. 查看分支
  1. git branch
  1. 创建分支
  1. git branch 分支名称
  1. 切换分支
  1. git checkout 分支名称
  1. 分支合并(可能差生冲突)

分支合并的同时先切换分支在合并

  1. git merge 要合并的分支
  1. 删除分支
  1. git branch -d 分支名称

远程仓库

GitHub

引用文章地址:https://www.liaoxuefeng.com/wiki/896043488029600/896954117292416

  1. 创建仓库

Git基础教程 - 图2

点击create repository ,进入下面的页面创建仓库完成

Git基础教程 - 图3

  1. 在GitHub上添加远程库

给远程仓库起别名

  1. git remote add origin 远程仓库地址

向远程推送代码

  1. git push -u origin 分支
  1. 从GitHub远程库克隆

要克隆一个仓库,首先必须知道仓库的地址,然后使用git clone命令克隆。

克隆远程仓库代码

  1. git clone 远程仓库地址

切换分支

  1. git checkout 分支名
  1. 案例

Git基础教程 - 图4

码云

rebase 使用

rebase在git中是一个非常有魅力的命令,使用得当会极大提高自己的工作效率;相反,如果乱用,会给团队中其他人带来麻烦。

它的作用简要概括为:可以对某一段线性提交历史进行编辑、删除、复制、粘贴;因此,合理使用rebase命令可以使我们的提交历史干净、简洁!

提示:不要通过rebase对任何已经提交到公共仓库中的commit进行修改

合并多个commit为一个完整commit

当我们在本地仓库中提交了多次,在我们把本地提交push到公共仓库中之前,为了让提交记录更简洁明了,我们希望把如下分支B、C、D三个提交记录合并为一个完整的提交,然后再push到公共仓库。

Git基础教程 - 图5

现在我们在测试分支上添加了四次提交,我们的目标是把最后三个提交合并为一个提交,这里我们使用命令:

  1. git rebase -i [startpoint] [endpoint]

其中-i的意思是--interactive,即弹出交互式的界面让用户编辑完成合并操作,[startpoint] [endpoint]则指定了一个编辑区间,如果不指定[endpoint],则该区间的终点默认是当前分支HEAD所指向的commit(注:该区间指定的是一个前开后闭的区间)。
在查看到了log日志后,我们运行以下命令:

将某一段commit粘贴到另一个分支上

多人协同开发工作流

什么是Git工作流?

Git工作流你可以理解为工作中团队成员遵守的一种代码管理方案

GitFlow工作流

GitFlow工作流程使用两个分支代替了单个主分支去记录项目的历史。 master 分支存储正式的发布历史记录,develop 分支充当功能的集成分支。使用版本号标记 master 分支中的所有提交也很方便。

Forking工作流

自定义Git

配置文件

Git 使用简单的 .ini 文件作为配置文件,配置文件中记录了很多 Git 命令使用的各种选项和设置,Git 支持不同级别的配置文件,下面按照优先级从高到低的顺序对它们进行介绍:

当前仓库的配置文件:当前仓库/.git/config

  1. git config --local user.name 'userName'
  2. git config --local user.name 'userName@qq.com'

全局配置文件:~/.gitconfig 文件 :当前用户的配置文件。可以通过传递—global 选项使Git 读或写这个特定的文件。

  1. git config --global user.name 'userName'
  2. git config --global user.name 'userName@qq.com'

系统配置文件:/etc/gitconfig 文件:包含了适用于系统所有用户和所有库的值。如果你传递参数选项’—system’ 给 git config,它将明确的读和写这个文件。注意:需要有root权限

  1. git config --system user.name 'userName'
  2. git config --system user.name 'userName@qq.com'

应用场景

  1. git remote add origin 地址 默认添加在本地配置文件中(--local

Git免密登陆

URL中体现

  1. 原来的地址:https://github.com/xiaohaijia/GitTest.git
  2. 修改后的地址:https://用户名:密码@github.com/xiaohaijia/GitTest.git
  3. git remote add origin https://用户名:密码@github.com/xiaohaijia/GitTest.git
  4. git push origin master

SSH实现

生成公钥和私钥(默认放在 ~/.ssh目录下,id_rsa.pub公钥,id_rsa私钥)

  1. $ ssh-keygen
  1. $ cat ~/.ssh/id_rsa.pub

拷贝公钥内容到GitHub

Git基础教程 - 图6

Git基础教程 - 图7

Git基础教程 - 图8

Git基础教程 - 图9Git基础教程 - 图10配置成功

Git基础教程 - 图11

在Git本地配置ssh地址

  1. git remote add origin git@github.com:xiaohaijia/GitTest.git

以后使用

  1. git push origin master

Git忽略文件

让Git不在管理当前目录下的某些文件

git如果需要忽略某个文件夹,可以在初始化之后,在仓库根目录下创建一个.gitignore文件,添加需要忽略的文件和文件夹即可

不需要从头写.gitignore文件,GitHub已经为我们准备了各种配置文件,只需要组合一下就可以使用了。所有配置文件可以直接在线浏览:https://github.com/github/gitignore不需要从头写`.gitignore`文件,GitHub已经为我们准备了各种配置文件,只需要组合一下就可以使用了。所有配置文件可以直接在线浏览:[https://github.com/github/gitignore](https://github.com/github/gitignore)

忽略文件的原则是:

  1. 忽略操作系统自动生成的文件,比如缩略图等;
  2. 忽略编译生成的中间文件、可执行文件等,也就是如果一个文件是通过另一个文件自动生成的,那自动生成的文件就没必要放进版本库,比如Java编译产生的.class文件;
  3. 忽略你自己的带有敏感信息的配置文件,比如存放口令的配置文件。

GitHub任务管理

  • issuess
    Issues(问题单)是一种伟大的工作方式,它用于对项目进行跟踪、增强和排错。它们就像电子邮件一样 —— 除了它们可以与团队的其他成员进行分享和讨论。大多数软件项目都会有某种错误跟踪器,GitHub 的错误跟踪器称为“Issues”,并且在每个仓库中都有自己的 Issues 部分。
  • wiki
    项目的文档