目录
1 版本控制系统概述
1.1 开发中的实际场景
在项⽬开发过程中,项⽬每开发到⼀个节点就会对当前项⽬进⾏备份,这个备份就是项⽬的⼀个版本;当我们继续 开发⼀个阶段后,再次进⾏备份,就⽣成新的版本——多个版本的集合就是项⽬的版本库。
在项⽬版本管理中,我们可以使⽤⼿动进⾏管理,但是会存在⼀些问题。
- 需要⼿动维护版本的更新⽇志,记录每个版本的变化;
- 需要⼿动查找历史版本,当历史版本⽐较多的时候,查找⼯作很繁琐;
- 当我们需要回退到某个版本时,只能够⼿动的通过IDE⼯具⼿动打开。
1.1.1 代码备份
张三负责的模块就要完成了,就在即将发布之前的⼀瞬间,电脑突然蓝屏,硬盘光荣牺牲!⼏个⽉来的努⼒付之东 流。
1.1.2 代码还原[版本控制]
这个项⽬中需要⼀个很复杂的功能,⽼王摸索了⼀个星期,终于有了眉⽬,可是这被改得⾯⽬全⾮的代码,已经回 不到从前了。需要⼿动维护版本的更新⽇志,记录每个版本的变化。
1.1.3 协同开发
张三和李四先后从⽂件服务器上下载了同⼀个⽂件UserMapper.java。张三在UserMapper.java⽂件中的第30⾏声 明了⼀个findUserAll()⽅法,先保存到了⽂件服务器上;李四在UserMapper.java⽂件中的第50⾏声明了⼀个 findUserById(Integer id)⽅法,也随后保存到了⽂件服务器上;于是,findUserAll()⽅法就只存在于张三的记亿 中。
1.1.4 多版本同步开发不同期上线
⽼王是⼀位项⽬经理,根据产品经理的要求,需要同步开发多个功能,但是会在不同的时间节点上线,针对同⼀⼯ 程和项⽬,应该怎么解决这个问题?
1.1.5 追溯问题代码[编写⼈和编写时间]
⽼王是⼀位项⽬经理,每次因为项⽬进度挨骂之后,他都不知道该扣哪个程序员的⼯资。就拿这次来说吧,有个 Bug经过20个⼩时的调试,才找到问题所在,是因为相关属性没有在应⽤初始化时赋值!可是张三、李四、王五都 不承认是⾃⼰⼲的。
1.2 版本控制系统
版本控制系统能追踪项⽬,从开始到结束的整个过程。对编程⼈员⽽⾔,版本控制技术是团队协作开发的桥梁,助 ⼒于多⼈协作同步进⾏⼤型项⽬开发。软件版本控制系统的核⼼任务:查阅项⽬历史操作记录、实现协同开发。
常⻅的两种版本控制类型:集中式版本控制⼯具、分布式版本控制⼯具。
1.2.1 集中式版本控制⼯具
集中式版本控制⼯具,版本仓库是集中存放在中央服务器的,Team⾥每个⼈⼯作时,从中央服务器下载代码。每 个⼈个⼈修改后,提交到中央版本仓库。提交(commit)代码需要联⽹。如SVN⼯具。
1.2.2 分布式版本控制⼯具
分布式版本控制系统可以没有“中央服务器”,每个⼈的电脑上都是⼀个完整的版本仓库,这样⼯作的时候,不需要 联⽹。因为版本仓库就在你⾃⼰的电脑上。多⼈协作只需要各⾃修改,开发完成即可,推送给对⽅(联⽹),推送 的时候是将整个版本仓库推过去。如Git⼯具。
2 Git概述
2.1 Git简介
Git — The stupid content tracker,傻⽠内容跟踪器。Linus Torvalds是这样介绍Git的。
Git是⼀个开源的分布式版本控制系统,可以有效、⾼速地处理从很⼩到⾮常⼤的项⽬的版本管理。Git是Linus Torvalds为了帮助管理Linux内核开发⽽开发的⼀个的版本控制软件,最后开源了Git。
Git的主要特点⻅下:
- 速度快、简单的设计
- 完全分布式
- 对⾮线性开发模式的强⼒⽀持(允许成千上万个并⾏开发的分⽀)
- 有能⼒⾼效管理类似Linux内核⼀样的超⼤规模项⽬
- Git是⼀个开源的分布式版本控制系统,⽤于敏捷⾼效的处理任何⼤⼩项⽬的版本管理。 核⼼功能:
- 项⽬的版本管理
- 团队协同开发
2.2 Git⼯作流程
Git本地仓库与远程仓库之间的交互流程图:
Git操作介绍⻅下表:
操作 | 作⽤ |
clone | 克隆,从远程仓库中克隆代码到本地仓库,第⼀次操作 |
push | 推送,代码完成后,需要和团队成员共享代码时,将代码推送到远程仓库 |
pull | 拉取,从远程库拉代码到本地库,⾃动进⾏合并(merge),最后放到⼯作区 |
3.3 Git基本概念
我们先来理解下Git⼯作区、暂存区和版本库概念。下⾯这个图展示了⼯作区、版本库中的暂存区和版本库之间的 关系:
Git架构中⼏个核⼼模块功能介绍⻅下表:
模 块 | 含义 |
⼯ 作 区 | 就是你在电脑⾥能看到的⽬录,即存放项⽬代码的⽬录,就是项⽬的根⽬录 |
暂 存 区 | 英⽂叫stage或index。就是版本库⽤于临时存储更新的缓存空间,⼀般存放在.git⽬录下的index⽂件 (.git/index)中,所以我们把暂存区有时也叫作索引(index) |
本 地 仓 库 | 在本地主机上的⼀个代码库,可以独⽴存在,也可以与远程仓库进⾏关联 |
版 本 库 | 存放项⽬历史版本的⽬录。⼯作区有⼀个隐藏⽬录.git,这个不算⼯作区,⽽是Git的版本库。就是执 ⾏ git init 指令之后,在⼯作空间⽂件夹⽣成的.git⽬录 |
远 程 仓 库 | 在局域⽹或互联⽹上的⼀个主机,存放代码库的主机或平台,⽐如GitHub、Gitee |
分 ⽀ | 代码存放在仓库,默认是主分⽀(master),可以在主分⽀基础上创建很多⼦分⽀,⽐如develop (开 发)、bugfix(bug修复)等 |
⼀个⽂件夹包含.git隐藏⽬录(Git⼯作⽬录),说明此⽂件⽬录使⽤了Git版本管理。在.git隐藏⽬录中存储了很多 配置信息、⽇志信息和⽂件版本信息、暂存区信息等。Git⽂件夹中有很多⽂件,其中有⼀个index⽂件就是暂存 区,也可以叫做stage。暂存区是⼀个临时保存修改⽂件的地⽅。
3 Git下载和安装
3.1 Git下载
访问 https://git-scm.com ⽹址根据不同的操作系统下载对应的Git版本。
3.2 Git安装
3.2.1 Window系统Git安装
Git的安装极为简单,除了选择安装位置以外(安装在⾮中⽂⽬录下),其他步骤都是傻⽠式操作保持默认即可, ⽆需做其他配置。
3.2.2 Git检查
1.Git安装完成后,输⼊以下命令可以查看Git是否安装成功,以及安装的版本。
git --version
2.检查Git的安装路径。
where git
4 Git配置
4.1 Git基本配置
安装完成Git后,正式使⽤Git前,是需要进⾏⼀些全局设置的,如⽤户名、邮箱。 主要通过 git config 命令进⾏ 设置。
1.配置⽤户名。该名字是你上传代码的⽤户名。
git config --global user.name 'zhangsan'
2.配置⽤户邮箱。该邮箱是其他作者联系你的邮箱,和你的代码托管中⼼没有任何关系,随便写,就是⼀个身份。
git config --global user.email 'zhangsan@163.com'
说明:其中,参数 --global ⽤于指定全局配置,不使⽤该参数,则为当前所在仓库配置。
3.配置⼤⼩写敏感。
git config --global core.ignorecase false
4.查看Git配置信息。
git config --list
4.2 构建本地仓库
要使⽤Git对我们的代码进⾏版本控制,⾸先需要构建本地仓库。构建本地仓库通常有两种⽅式:
- 在本地初始化⼀个Git仓库
- 从远程仓库克隆⼀个仓库(将在远程仓库章节中演示)
初始化本地Git仓库的操作步骤⻅下:
1.在电脑的任意位置创建⼀个空⽬录作为我们的本地Git仓库。例如在桌⾯创建⼀个【local_repository】⽬录作为 本地仓库。
2.进⼊local_repository⽬录中:
- Windows系统:在该⽬录⽂件夹下的空⽩位置处,点击右键选择【Git Bash Here】打开窗⼝。
- macOS系统:通过终端窗⼝使⽤ cd 命令进⼊到该⽬录中。
3.执⾏命令 git init 命令,初始化本地Git仓库。
git init
4.如果在当前⽬录中看到.git⽂件夹(此⽂件夹为隐藏⽂件夹)则说明初始化本地Git仓库成功。
ls -ah
说明:该命令执⾏完后会在当前⽬录⽣成⼀个.git⽬录。
4.3 本地仓库的操作
4.3.1 Git基本操作
Git常⽤的是以下6个命令:git clone、git push、git add、git commit、git checkout、git pull,后⾯我们会详细 介绍。
说明:
workspace | ⼯作区 |
staging area | 暂存区/缓存区 |
local repository | 版本库或本地仓库 |
remote repository | 远程仓库 |
Git常⽤命令操作:
命令 | 作⽤ |
git clone | 克隆,从远程仓库中克隆代码到本地仓库 |
git add | 添加,将⼯作区修改的代码添加到缓存区 |
git commit | 提交,将缓存区代码提交到本地仓库 |
git push | 推送,将本地仓库中的代码推送到远程仓库 |
git pull | 拉取,拉取远程仓库的代码到⼯作区 |
4.3.2 查看当前⽂件状态
git status -s
说明:如果添加参数 -s 则表示使⽤更简洁的信息输出当前⽂件的状态。输出的⽇志信息中的"??"表示“未跟踪 的⽂件”。
4.3.3 将⽂件添加到版本库
如果要将⼀个⽂件纳⼊到版本库管理,⾸先要将其添加到暂存区,然后才能提交到仓库中。
1.将⽂件添加到暂存区,使⽤ git add 命令。
# 添加单个⽂件到暂存区(只将⼯作空间中的某个⽂件add到暂存区)
git add readme.md
# 将当前⽬录下所有修改添加到暂存区,除按照规则忽略的之外(将⼯作空间中所有⽂件都add到暂存区)
git add .
注意:这边空⽂件夹是不会被添加到暂存区中的。
2.将暂存区中的⽂件提交到仓库中,使⽤ git commit 命令。
# 如果暂存区有⽂件,则将其中的⽂件提交到仓库(将暂存区内容提交到版本库)
git commit
# 带评论提交,⽤于说明提交内容、变更、作⽤等
git commit -m 'your comments'
注意:这边直接⽤ git commit 提交,会先弹出添加评论的⻚⾯。
4.3.4 查看提交历史记录
有的时候,是会需要查看⾃⼰代码做过哪些提交,来回顾⾃⼰完成的部分;或者需要寻找某个具体的提交来查看当 时的代码。这⾥需要⽤到。
# 显示所有提交的历史记录
git log
# 单⾏显示提交历史记录的内容
git log --pretty=oneline
0bef08fe0e96a119e60e33d4ed306fc0ad9259b3 (HEAD -> master) update readme.md
d9678543842dbaa2f9ef35acbd2f7e44a45fe5ee init readme.md
# 每个版本信息只显示⼀⾏
git log --oneline
4.3.5 版本回退
# 回退到commit_id指定的提交版本
git reset --hard 'commit_id'
4.3.6 删除⽂件
在⽂件未添加到暂存区之前,想删除⽂件可以直接物理删除。如果⽂件已经被提交到暂存区,则需要通过 git rm 来删除。
# 删除已经被提交过的readme.md
git rm readme.md
# 提交⽣效
git commit -m '删除readme.md'
注意:使⽤ git rm 命令只能删除已经提交到版本库中的⽂件。其他状态的⽂件直接⽤这个命令操作是会出 错的。
如果⽂件被误删,可以通过本地仓库进⾏恢复。
git checkout readme.md
5 Git分⽀管理
⼏乎所有的版本控制系统都以某种形式⽀持分⽀。使⽤分⽀意味着你可以把你的⼯作从开发主线上分离开来进⾏重 ⼤的Bug修改、开发新的功能,以免影响开发主线。
5.1 分⽀管理介绍
在开发中,⼀般有如下分⽀使⽤原则与流程:
分⽀ | 描述 |
master | 主分⽀。线上分⽀,中⼩规模项⽬作为线上运⾏的应⽤对应的分⽀ |
test | 测试分⽀。从master创建的分⽀,⼀般作为测试部⻔的测试分⽀,进⾏预发测试。测试完 成后,需要合并到master分⽀,进⾏上线,中⼩规模项⽬可省略此分⽀ |
develop | 开发分⽀。从test创建分⽀,如果开发没有test分⽀,是从master创建的分⽀,⼀般作为开 发部⻔的主要开发分⽀。如果没有其他并⾏开发不同期上线要求,都可以在此版本进⾏开 发。阶段开发完成后,需要合并到test分⽀继续测试,如果没有test分⽀,可直接合并到 master分⽀ |
hotfix/bugfix | 从master派⽣的分⽀,⼀般作为线上bug修复使⽤,修复完成后需要合并到master、test、 develop分⽀ |
5.2 分⽀管理操作
5.2.1 查看分⽀
1.查看本地分⽀信息。
git branch
2.查看相对详细的本地分⽀信息。
git branch -v
3.查看包括远程仓库在内的分⽀信息。
git branch -av
注意:在git branch的输出内容中,有⼀个分⽀,前⾯带有 * 号,这标识我们当前所在的分⽀。
5.2.2 创建分⽀
当我们要修复⼀个Bug或者开发⼀个新特性,甚⾄是在初学的时候怕打乱原来的代码,都可以新建⼀个分⽀来避免 对原来代码的影响。
# 新建⼀个名称为dev的分⽀
$ git branch dev
# 查看本地分⽀信息
$ git branch
5.2.3 切换分⽀
1.切换分⽀
当我们创建完分⽀以后,我们需要切换到新建的分⽀;否则,所有的修改还是在原来的分⽀上,事实上,所有的改 动只能影响到当前所在的分⽀。
# 新建完dev分⽀以后,通过checkout命令切换到dev分⽀
$ git checkout dev
# 查看本地分⽀信息
$ git branch
2.创建并切换分⽀
这个命令合并了前两个独⽴的命令,平常使⽤中⼀般这样使⽤。
# 新建dev分⽀,并切换到该分⽀上
git checkout -b dev
5.2.4 合并分⽀
当我们修复完成⼀个Bug或者开发完成⼀个新特性,我们就会把相关的Bug或特性上的修改合并回原来的主分⽀ 上,需使⽤ git merge 命令来完成分⽀的合并。
1.合并分⽀操作
⾸先需要切换回最终要合并到的分⽀上,如master主分⽀。
# 切换回master主分⽀
$ git checkout master
# 将dev分⽀中的修改合并回master主分⽀
$ git merge dev
# 在master主分⽀下,查看⼯作区中的所有⽂件,发现test.md此时可⻅了
$ ls -a
2.合并分⽀代码冲突
代码冲突是指,在多个⼈对同⼀个⽂件的同⼀⾏进⾏了修改操作。
- 张三:UserServiceImpl的第20⾏进⾏了代码添加,添加了addUser⽅法。
- 李四:UserServiceImpl的第20⾏进⾏了代码修改,添加了updateUser⽅法。
5.2.5 删除分⽀
当之前创建的分⽀,完成了它的使命,如Bug修复完,分⽀合并以后,这个分⽀就不在需要了,就可以删除它。
# 删除dev分⽀
$ git branch -d dev
6.SSH密钥
6.1.1SSH密钥⽣成
1.Windows系统SSH密钥⽣成
1.在Windows系统下,我们可以使⽤Git Bash.exe来⽣成密钥,或者右键菜单打开【Git Bash Here】选项。
2.在窗⼝中输⼊以下命令,⽣成公钥和私钥。
ssh-keygen -t rsa
3.执⾏命令完成后,在 C:\Users\⽤户名\.ssh\ ⽬录下⽣成如下名称的公钥和私钥。
- id_rsa:表示私钥
- id_rsa.pub:表示公钥
2.macOS系统SSH密钥⽣成
1.在macOS系统下,打开【终端】窗⼝。
2.在终端窗⼝中输⼊以下命令,然后⼀路回⻋使⽤默认配置,⽤于⽣成公钥和私钥。
ssh-keygen -t rsa
3.在SSH密钥⽣成过程中的⽇志⾥可以发现,⽣成的公钥和私钥存放在 /Users/⽤户名/.ssh/ ⽬录下。
cd /Users/yuanxin/.ssh
ls -a
6.1.2 SSH密钥配置
密钥⽣成后需要在GitHub上配置密钥,本地才可以顺利访问。
1.点击右上⻆的图像,点击【Settings】选项。
2.点击【SSH and GPG keys】选项,然后点击【New SSH key】按钮,进⾏SSH密钥的配置。
3.将id_rsa.pub⽂件中的全部内容复制到【key】对应的⽂本框中,同时指定SSH keys的Title值。
4.在上述窗⼝中点击【Add SSH key】按钮后,将⾃动跳转到下⾯的⾯。截⽌此步,完成GitHub的SSH密钥配置。
7 远程仓库的操作
7.1 查看远程仓库
如果想查看已经配置的远程仓库服务器,可以运⾏ git remote 命令。它会列出指定的每⼀个远程服务器的简写。 如果已经克隆了远程仓库,那么⾄少应该能看到origin,这是Git克隆的仓库服务器的默认名字。
# 命令形式(在本地仓库⽬录下的命令终端执⾏)
git remote -v
说明:origin表示仓库服务器的默认名称。
7.2 添加远程仓库
如果已经有了⼀个本地仓库,然后打算将它发布到远程仓库,供其他⼈协作,那么需要使⽤ git remote add 命 令。
# 为本地仓库添加远程仓库
# origin表示远程仓库名称,名字⾃定义
# your_git_remote_repo表示远程仓库地址
$ git remote add origin your_git_remote_repo
1.在GitHub的remote_repo远程仓库中,找到【SSH】协议获取该远程仓库的地址。
2.在命令⾏中输⼊以下命令将本地仓库添加到远程仓库。
git remote add origin copy的路径
3.再次查看远程仓库,可以看到origin的信息。
$ git remote -v
origin git@github.com:yuan00xin/remote-repo.git (fetch)
origin git@github.com:yuan00xin/remote-repo.git (push)
7.3 推送本地的内容到远程仓库
7.3.1 推送本地的内容到远程仓库实现
当本地仓库中代码完成提交,就需要将代码等推送到远程仓库,这样其他协作⼈员就可以从远程仓库同步内容了。
# 第⼀次推送时使⽤,可以简化后⾯的推送或者拉取命令使⽤
git push -u origin master
# 将本地master分⽀推送到origin远程分⽀(origin表示远程仓库名称,是在添加远程仓库时⾃定义的)
git push origin master
7.4 从远程仓库获取最新内容
在多⼈协作过程中,当⾃⼰完成了本地仓库中的提交,想要向远程仓库推送前,需要先获取到远程仓库的最新内 容。可以通过git fetch和git pull来获取远程仓库的内容。
git pull origin master
git fetch origin master
git fetch和git pull之间的区别:
- git fetch:是仅仅获取远程仓库的更新内容,并不会⾃动做合并。
- git pull:在获取远程仓库的内容后,会⾃动做合并,可以看成git fetch之后git merge。
7.4 移除⽆效的远程仓库
如果因为⼀些原因想要移除⼀个远程仓库。使⽤以下命令形式:
git remote rm <shortname>
注意:此命令只是从本地移除远程仓库的记录,并不会真正影响到远程仓库。
7.5 从远程仓库克隆
如果你想获得⼀份已经存在了的Git仓库的拷⻉,这时就要⽤到git clone命令。Git克隆的是该Git仓库服务器上的⼏ 乎所有数据(包括⽇志信息、历史记录等),⽽不仅仅是复制⼯作所需要的⽂件。当你执⾏git clone命令的时候, 默认配置下远程Git仓库中的每⼀个⽂件的每⼀个版本都将被拉取下来。
如果你本地没有仓库,希望从已有的远程仓库上复制⼀份代码,那么你需要使⽤git clone命令。
# 通过SSH协议,克隆Github上Git仓库的源码
git clone git@github.com:...
# 通过HTTPS协议,克隆Github上Git仓库的源码
git clone https://github.com/...
注意:git clone后⾯的仓库地址,可以⽀持多种协议,如HTTP、SSH等。
7.6 从远程仓库拉取
git pull 远程仓库名称 分⽀名称