Node+GitLab实现小程序CI系统

3,164

为什么要实现自动部署

小程序开发迭代里,有以下几个个头痛的问题,

  • 如何准确并快速的的把小程序上传去后台,并让测试人员进行测试?
  • 测试同事找开发要二维码,效率较低
  • 本地生成的二维码会出现携带本地代码、未及时拉取分支其他改动等问题
  • 小程序的体验发布太依赖开发者,通常只有开发者熟悉微信开发者工具一系列的上传流程,而每次发布的是有页可能因为忘记合并分支,忘记开启构建命令导致一些列不可知的错误,从而导致影响开发进度、发布流程不可控等一系列问题。

针对这些问题我们需要一套可以随时从Git上拉取最新代码选取分支和tag并自动打包构建不同环境上传至小程序后台的系统来解决以上问题。

如何实现?

开发者工具提供了命令行与 HTTP 服务两种接口供外部调用,开发者可以通过命令行或 HTTP 请求指示工具进行登录、预览、上传等操作。
传送门: "developers.weixin.qq.com/miniprogram…"

方案

通过命令行与 HTTP 服务可以想到一下几种思路

  • 通过老牌持续集成工具Jenkins配置shell脚本调用命令行上传部署
  • 通过配置GitLab CI在项目内添加.yml编写CI文件调用命令行上传部署
  • 通过Node调用Http服务配合Gitlab-Api+shell命令为前端提供调用接口,前端调用接口实现自动编译上传部署

本文将针对第三种思路详细阐述实现一个自动化部署系统的步骤和实现过程中的思考。

为什么我不用第一种和第二种?一是因为搞这种现成的配置式的东西弄出来没什么成就感,用第三个思路写顺便可以练练Node,二是因为虽然思路有了,但配置还没玩明白,等我研究明白了再单独写吧。emmmm.....

需要用到的知识点(知识点不会的童鞋先去补课)

  • NodeJS
  • Gulp
  • Git命令
  • GitLab-Api或Github-Api(本文全部使用gitlab-api)
  • Vue+Scss+layui+Html实现前端页面功能

传统流程

你正在认真coding,和某个bug激烈战斗,已经有了头绪正准备一气呵成干掉它。突然被别人打断并告诉你需要为他提供一个测试环境的二维码...
为了这个二维码你做了以下事情

忙活完之后你将分支切换回来,不断回想刚才的思路,脑子里一万个那啥狂奔,但如果直接反手丢给他一个发布系统链接地址,那么他只要按照以下步骤点点点就可以轻易的搞定这件事而不用来冒着被砍的风险来找你:

  1. 输入git地址和小程序开发工具端口地址(配置一次即可)
  2. 选择需要发布的对应分支
  3. 选择构建环境打包
  4. 上传至小程序后台
  5. 登录小程序后台设置体验版获取二维码
  6. 搞定收工,全程无需发布人员操作任何代码相关,只要会点下一步,有发布权限即可

开发过程

流程图

后端功能实现

  • 环境依赖
  • 实现上传小程序后台接口;
  • 实现拉取git项目到本地的接口;
  • 实现获取gitlab项目信息,分支及tag的接口;
  • 实现切换分支及tag接口
  • 实现项目编译打包的接口;
  • 实现拉起开发者工具的接口;

环境依赖

在后端功能的实现上用了以下框架和模块

  • express (node框架)
  • request(网络请求模块)
  • fs (文件处理模块)
  • log4js (输出log日志)
  • process(子进程模块,用来在node中执行shell命令)

1. 拉起开发者工具的接口

mac系统上开发者工具会默认的安装路径是/Applications/wechatwebdevtools.app, 通过process模块执行shell命令open /Applications/wechatwebdevtools.app即可打开开发者工具。

2. 实现上传小程序后台接口

上传接口是这个系统的核心,虽然很简单但要实现这个接口还是需要你对小程序工具的http调用有一定了解,接下来详细说一下如何完成此功能:
上文说到小程序开发者工具提供了命令行与 HTTP 服务两种接口供外部调用,开发者可以通过命令行或 HTTP 请求指示工具进行登录、预览、上传等操作。

第一步(开启http服务)
打开你的开发者工具 设置——>安全设置——>服务端口,因为调用开发者工具提供的http服务一定要拼接本地的端口号,所以后续所有的操作都是要基于开发者工具开启且服务端口开启的状态下进行操作的,默认情况下服务端口是关闭的,http 服务在工具启动后自动开启,HTTP 服务端口号在用户目录下记录,可通过检查用户目录、检查用户目录下是否有端口文件及尝试连接来判断工具是否安装。

第二步(如何拿到开发者工具端口号)
在确保你的开发者工具服务端口开启的情况下,我们可以尝试通过node的fs模块去读取储存的文件信息读取端口号,端口号文件是开发者工具自动生成的,所以它的位置是固定的,但不同系统中的默认位置也不相同。
端口号文件位置:
macOS : ~/Library/Application Support/微信web开发者工具/Default/.ide
微信web开发者工具/User Data/Default/.ide

注意!!!
像是在mac中直接去读取这个默认路径是获取不到的,因为mac中一般会将工具安装在你的当前账户文件夹下,所以如果发现无法读取的情况可以到Uers的文件夹找找看。 比如我的mac上要想访问端口文件完整路径是这样的:
const portPath = '../../Users/admin/Library/Application\ Support/微信web开发者工具/Default/.ide';

读取端口的功能封装,后续会用到

第三步(上传)

接口定义:

  • URL:/upload
  • HTTP 方法:GET

通过调用获取端口号的方法,请求上传接口拼接端口,指定项目上传目录,就是编译出来的dist文件夹目录,将接收的描述和版本号一并拼接发送上传请求即可。

get请求封装

3. 实现拉取git项目到本地的接口

这个接口的实现主要是通过Node接收项目地址然后执行git clone的shell命令实现, 需要用到Node的child_process子进程模块用来执行shell脚本。

代码实现

4. 实现获取gitlab项目信息,分支及tag的接口

Gitlab有一个非常强大的API系统,几乎所有的功能都有相应的API接口,为了使用API,需要从Gitlab中获取私有token。

  1. 登陆你的Gitlab
  2. 点击登陆的帐户,点击settings
  3. 点击Access Tokens
  4. 根据自己的需要创建适合需要的Tokens

成功拿到token之后只需在请求的时候作为query参数传递即可:
项目分支信息API api/v3/projects/ [projectId] /repository/branches
小程序项目tagaAPI api/v3/projects/ [projectId] /repository/tags

5.实现切换分支及tag接口

分支和tag接口实现的思路是一样的,接到前端请求后执行各种git命令完成

  • 切换至项目目录下 cd ./project
  • git branch 拿到本地分支信息
  • 切换分支时通过接收的分支名称比对本地是否存在分支,如分支已存在就删除再切换,不存在就直接切换
  • 通过log4js输出日志,为了页面展示用

代码实现

示例为分支切换的相关代码,tag实现的思路是一样的,只不过要把相关git命令替换即可。

6. 实现项目编译打包的接口

这里需要注意一下,这个接口的实现是非常灵活的,需要根据你当前项目的编译文件进行配置,比如我的项目开发时使用gulp打包编译环境到dist,其编译命令分别为:

  • gulp build:Dev(联调环境)
  • gulp build:Test(测试环境)
  • gulp build:Slave(预发布环境)
  • gulp build:Prod(线上环境)

那么同理,配置好dist输出文件目录,收到请求后执行事先实现好的shell命令即可完成打包这一步,如果你不太了解环境编译打包这块内容,可以参考我上一篇文章"《武装你的小程序——开发流程指南》";

代码实现

目前为止我们已经实现了六个后端功能,并生成了对应路由,分别为:

  • /open 实现拉起开发者工具的接口;
  • /up 上传小程序后台接口;
  • /clone 拉取git项目到本地的接口;
  • /checkoutBranch || /checkoutTag 获取gitlab项目信息,分支及tag的接口;
  • /branches || /tags 获取gitlab项目信息,分支及tag的接口;
  • /branches 项目编译打包的接口;

前端实现

前端页面我就不提供示例代码了,ui框架和开发框架根据大家的喜好决定,因为有了上面这些接口我们就已经可以愉快的对前端页面进行你需要的一些定制了,这个时候需要我们考虑的就是一些前端的交互逻辑了,如何利用好这些接口将起串起来组成条完整的流程,如何利用gitlab的其他api扩展你需要的其他功能,比如加一个提交记录页面...

前面的流程图已经大致画出了我的思路,下面我将我的前端实现思路详细描述一下,供大家参考:

  1. 实现一个启动页面,页面可以输入git地址和本地的端口路径,点击开始按钮调用/clone接口将代码拉取到项目中,同时将端口号路径储存起来后面用。
  2. clone接口返回成功后调用/open接口拉起开发者工具
  3. 实现一个主页面,初始化页面调用/branchs/tag接口获取分支和tag信息,将其展示在页面上。
  4. 点击切换分支获取当前选取的分支名,调用/checkoutBranch 或 /checkoutTag接口传递分支名,后端调用相应的git命令。
  5. 切换分支完成后进入选择环境页,添加描述和版本号选择需要发布的环境,调用/build接口传递环境变量进行构建。
  6. 构建完成显示下一步,调用/up接口传递版本号和描述发送上传请求,上传成功页面将描述,提交人,时间,环境等必要信息展示出来。
  7. 去微信公众平台设置体验版
  8. 完成

END

到这里一个简单的小程序发布系统就完成了,本文只是记录了我的一个开发思路希望能对大家有所启发,有很多地方考虑的还是不够完善但基本能用了,大家可以发散思维实现一个自己的发布系统,也欢迎交流想法和指正我的错误,同时欢迎大家关注公众号前端小苑,我会定期在这里发表原创文章。