当谈到 GitLab CI 的时候,我们都该聊些什么(下篇)
上篇主要介绍了 GitLab WorkFlow 以及 CI/CD 做的事情,并且详细分析 GitLab CI 跟 Runner 信息交互是如何进行的。接下来将为大家讲解 Executor 的实现,再通过两个例子具体展示 GitLab CI 的使用。
Executor
本章主要讲了在Runner 在接收到任务之后,会调用 Executor,Executor 是怎么实现的,重点介绍 Docker Executor 的实现细节
其实 Runner 会去调用对应的 executor,由 executor 来完成接下去的工作。
图 12 是从 GitLabMutliRunner 项目中截取的一部分代码,基本可以说明 executor 的流程。
图 12
第一步:Prepair,做准备工作;
第二步:拉取代码,根据 Job 里的 git_info 字段,Runner 去 GitLab 仓库拉取代码;
第三步:还原缓存,这些缓存是上一次构建留下的;
第四步:下载 artifacts,这是前一个阶段的产生的中间结果;
第五步:执行用户定义的脚本,这里指的是 before_scripts 跟 scripts 两部分;
第六步:执行 after_scripts;
第七步:保存缓存打包 artifacts 等;
第八步:上传 artifacts 供下一阶段使用。
基于这样一个流程,官方提供了 ssh、shell、docker、docker-ssh、virtualbox、kubernates 等执行器,来应对实际使用中的不同场景,本次分享主要也是从 Docker 跟 Docker-ssh 进行展开的。由于Docker 的隔离性强、秒级别启动容器、轻量、回收方便这些特点非常符合集成测试的要求。
首先,如果要使用 Docker executor,CI 配置文件需要做如下调整:
图 13
1.定义 image 字段,该字段指定了本次测试环境使用的 Docker 镜像;
2. services,这个字段定义了本次测试依赖的服务,这里依赖的是 redis 跟 mysql。
Docker executor 的实现
第一步:Prepare,Runner 会先去下载 redis、mysql 等项目依赖的服务,启动映射了目录代码的容器,启动映射了缓存目录的容器。
图 14
第二步:GetSource,Runner 会在启动一个 predefine 的容器,通过 volume from 的方式挂载项目代码路径,再通过 predefine 这个容器去拉取代码。由于目录共享,所以 volumes 里的这个容器数据内容也发生了改变。
图 15
第三步:执行脚本,runner 会启动一个 build 容器,通过 docker link 的方式把依赖的服务连接起来,通过 docker volume from 的方式加载项目代码以及缓存,然后执行 job 中定义的脚本。
图 16
Artifacts
当图片处理项目 Nami 刚接入到 CI 时,是分成 Test 跟 Build 两个阶段处理,Test 阶段需要先编译 Nami,然后启动测试。等测试通过后,执行第二阶段,进行 Docker Build,这时又需要重新再编译依次 Nami,这个过程很费时。后来了解到了 Artifacts 这个功能,可以把这个阶段中产生的文件上传到 GitLab 供下一个阶段来使用,这样以来就不需要二次编译了。
图 17
完成优化后,将整个过程拆成了 3 个阶段,第一个阶段进行编译,第二个阶段使用上一个阶段编译好的结果进行测试,第三个阶段使用第一个阶段编译好的二进制做 Docker Build。这样一来,整个过程中只需要做一次编译,大大缩短了构建耗费的时间。
图 18
另外上传 GitLab 还有一个好处,安装包可以直接通过网页下载回来。
关于 GitLab CI 的实践经验
C/C++ 编译优化
CDN 项目依赖 Nginx,并且增加了公司定制的逻辑,所以每次测试都需要重新编译 Nginx,但是众所周知编译是十分耗时的。为了解决这个问题,我们引入了 CCACHE。CCACHE 是一个编辑器驱动器,第一次编译时 CCACHE 会缓冲 GCC 的 -E 输出,编译选项以及 O 文件到 $HOME/.ccache 下,第二次编译时尽量利用缓冲,必须时更新缓冲。但是这里会有一个问题,测试跑完之后容器立刻就被回收了,怎么把编译缓存保留到下一次测试呢?
这里就需要用到前面提交的 cache 选项了,cache 选项可以把上一次的缓存目录保留到下一次测试中,供下一次测试使用。但是我们需要对 ccache 做一下配置,修改缓存的路径,指定到 /cache 目录下。
$ ccache —set-config=cache_dir=/cache/.ccache
$ ccache -F 0 && ccache -M 0
Localhost 问题
图 19
如果测试中依赖第三方服务的话,docker executor 是通过 docker link 的方式,但是采用这种方式的话,Build 这个容器就无法通过 127.0.0.1 来访问 Redis、Mysql 了。但是研发同学常会把测试环境的配置写成 127.0.0.1,方便本地开发测试。这样一来,接入到 CI 之后就会有不少困扰。针对这个问题,我们给出了两种解决方案。
第一种解决方案是使用别名:在定义 services 的时候,可以定义 alias,来指定该服务的别名,指定好别名之后,Build 容器内就会多一条该别名的解析记录,解析到指定的容器 IP。这种方式下,研发同学只要修改下测试配置就可以把服务跟测试跑起来,不过本地开发的时候,需要增加一条解析记录,把别名解析到 127.0.0.1。
图 20
第二种解决方案是端口转发,这种方式更加简单灵活些。拿 redis 举个例子,如果测试中以来了 redis,需要在 build 容器中安装 3proxy 做端口转发,并且把对 6379 端口的请求,都转发到 redis 对应容器的 6379 上去,通过这种方式来解决访问 127.0.0.1:6379。这种方式更加方便,研发同学不需要去修改测试的配置,但是需要在执行测试之前,去启动 3proxy 并配置端口转发规则。
当谈到 GitLab CI 的时候,我们都该聊些什么(下篇)的更多相关文章
- 当谈到 GitLab CI 的时候,我们该聊些什么(上篇)
"微服务"这个概念近两年非常热,正在慢慢改变 DevOps 的思路.微服务架构把一个庞大的业务系统拆解开来,每一个组件变得更加独立自治.松耦合.但是,同时也伴随着部署单元粒度越来越 ...
- 使用GitLab CI + Capistrano部署CakePHP应用程序
使用GitLab CI + Capistrano部署CakePHP应用程序 摘要:本文描述了如使用GitLab CI + Capistrano部署CakePHP应用程序. 目录 1. 问题2. 解决方 ...
- GitLab CI持续集成配置方案(补)
上篇文章介绍了GitLab CI的持续集成配置方法,本篇文章将主要介绍NUnit的持续集成和遇到的一些坑 1.NUnit单元测试持续集成 下载NUnit.3.4.1.msi,https://githu ...
- GitLab CI持续集成配置方案
目录 1. 持续集成介绍 1.1 概念 1.2 持续集成的好处 2. GitLab持续集成(CI) 2.1 简介 2.2 GitLab简单原理图 2.3 GitLab持续集成所需环境 2.4 需要了解 ...
- GitLab CI
GitLab CI持续集成配置方案 目录 1. 持续集成介绍 1.1 概念 1.2 持续集成的好处 2. GitLab持续集成(CI) 2.1 简介 2.2 GitLab简单原理图 2.3 Git ...
- Gitlab CI 自动部署 asp.net core web api 到Docker容器
为什么要写这个? 在一个系统长大的过程中会经历不断重构升级来满足商业的需求,而一个严谨的商业系统需要高效.稳定.可扩展,有时候还不得不考虑成本的问题.我希望能找到比较完整的开源解决方案来解决持续集成. ...
- Ubuntu Docker 安装和配置 GitLab CI 持续集成
相关文章: Ubuntu Docker 简单安装 GitLab 劈荆斩棘:Gitlab 部署 CI 持续集成 目的:在 Ubuntu 服务器上,使用 Docker 安装和配置 GitLab Runne ...
- Ubuntu & GitLab CI & Docker & ASP.NET Core 2.0 自动化发布和部署(1)
相关博文: Ubuntu 简单安装和配置 GitLab Ubuntu 简单安装 Docker Ubuntu Docker 简单安装 GitLab Ubuntu Docker 安装和配置 GitLab ...
- Ubuntu & GitLab CI & Docker & ASP.NET Core 2.0 自动化发布和部署(2)
上一篇:Ubuntu & GitLab CI & Docker & ASP.NET Core 2.0 自动化发布和部署(1) 服务器版本 Ubuntu 16.04 LTS. 本 ...
随机推荐
- Http协议详解,获取doPost,doGet提交的数据,以及编码问题
一 什么是Http协议 http协议: 浏览器客户端 和 服务器端 之间数据传输的格式规范 二 如何查看Http协议的内容 1)使用火狐的firebug插件(右键->firebug->网 ...
- 团队作业1——团队展示&选题
Deadline: 2017-4-5 22:00PM,以博客发表日期为准 评分基准: 按时交 - 有分,检查的项目包括后文的四个方面 团队博客 团队选题 团队计划 团队成员贡献分分配规则 晚交 - 0 ...
- 201521123092, 《java程序设计》第1周学习总结。
#1.本周学习总结 这一周是我学习java的第一周,刚接触一门全新的编程语言,觉得还是有点困难的,很多基础性的java知识需要一点点学习,我会请教同学以及查询网上的学习资料,认真学好这一门学科. 本周 ...
- cnpack热键
CnPack的热键为ALt+space,当不自动补齐时按下Alt+space则会补齐
- [04] 利用注解生成实体类对应的建表sql语句
1.实现功能 我们已经对注解有了基本的认识,知道了如何自定义注解,如何使用和最基本的处理注解. 本篇主要介绍,如何使用运行时级别的注解,配合反射来自动生成建表的sql语句.如下例: 我们有实体类Stu ...
- Java是如何解析xml文件的(DOM)
Java解析xml文件 在Java程序中读取xml文件的过程也称为"解析xml文件": 解析的目的: 获取 节点名和节点值 获取 属性名.属性值. 四中解析方式: DOM SAX ...
- SimpleRpc-系统边界以及整体架构
系统边界 什么是系统边界?系统边界就是在系统设计之初,对系统所要实现的功能进行界定,不乱添加,不多添加.这么做的好处就是,系统简单明了,主旨明确,方便开发和用户使用.举个例子,一个自动售货机的本职工作 ...
- [js高手之路] 设计模式系列课程 - DOM迭代器(2)
如果你对jquery比较熟悉的话,应该用过 eq, first, last, get, prev, next, siblings等过滤器和方法.本文,我们就用迭代设计模式来封装实现,类似的功能 < ...
- mybatis快速入门(五)
今天写写user表和orders表的mybatis的高级映射,一对一映射和一对多映射 1.创建一个orders.java文件 1.1一对一映射,一条订单对应一个用户 package cn.my.myb ...
- E - 今年暑假不AC HDU - 2037
"今年暑假不AC?" "是的." "那你干什么呢?" "看世界杯呀,笨蛋!" "@#$%^&* ...