GMTC《在线教育小程序云开发工程化实践》演讲全文

2022-06-29 14:45:33 浏览数 (1)

GMTC·2019近日在深圳隆重召开。腾讯在线教育IMWeb团队的高级工程师袁龙在大会上发表了《在线教育小程序云开发工程化实践》的演讲,介绍了腾讯在线教育在小程序工程化,小程序CI、CD,以及云开发在多端开发的探索与实践经验。演讲内容整理如下。

一、腾讯在线教育业务背景

首先介绍下腾讯在线教育下的3个主要业务。

- 面向对成人职业化、兴趣化学习的腾讯课堂

- 面向小学、初高中K12领域的企鹅辅导

- 面向少儿英语学习的ABCmouse

这三块业务在各个端都有产品落地,来满足不同端用户的需求,当然也包括小程序。

我们的小程序有工具型的,主要对业务进行引流,比如腾讯课堂打卡小程序,企鹅速算小程序。也有平台内容型小程序来承载业务,如腾讯课堂小程序。

二、小程序工程化实践

刚才介绍到了我们业务会有很多小程序,那么我们是如何进行小程序工程化实践的,又遇到了哪些问题呢。

首先看下我们小程序相关的需求场景。由于业务迭代快,我们单个小程序都是多需求并行的,同一个小程序会有多个需求同时开发。

这是大概的开发方式,开发同学各自开发,然后预览二维码,上传代码到小程序后台。大家可以看下,这样会有什么问题。其实对比我们平时的Web开发方式不难看出,这里开发环境不统一,除了操作系统、Nodejs版本,还有我们的小程序开发者工具。

我们曾经有一次在小程序发布后,就收到了反馈小程序某个页面打不开了。因为当次发布并不涉及打不开的页面,最后排查发现是上传代码同学更新了开发者工具后导致的,降级了开发者工具后重新构建上传得以解决。

除了开发环境不统一,在后面的流程中其实还有很多问题。

  • 小程序发布前遗漏Npm构建,可能导致依赖的包没有同步更新。
  • 预览二维码有时效性,特别是多需求的时候,切体验版也没有那么方便。
  • 发布环节没有周知,可能会有夹带代码出去。

基于以上问题,我们做些思考,最终打造小程序的Devops工作流来解决这些问题。今天主要给大家介绍下后面的构建、测试、发布以及协作。

首先看下构建和发布。从图中可以看到,这两个环节里`构建Npm`和`上传代码`是依赖微信开发者工具的,微信开发者工具也提供了CLI调用和Http调用的能力。

为了更好的将这些能力和我们的需求进行整合,我们基于微信开发者工具的CLI,开发了我们小程序的构建工具Imweapp。这款工具的使用流程如图所示,包括了发布前主干分支合并的检查,依赖Npm包版本合法性的校验,以及构建Npm,自动获取上传需要版本号和描述机型上传。

有了这款工具后,我们上传小程序代码前就更有保障了。

为了更好的保障我们小程序的质量,我们也做了自动化测试的尝试。小程序的自动化测试分为UI测试和单元测试。

我们先来看下UI测试,我们使用`miniprogram-automator`和`jest`来进行UI测试。

图上是腾讯课堂小程序的课程详情页,这里需要测试验证的项包括点击播放,切换目录,播放状态检测,底部按钮状态检测等。

这是我们的测试示例,我们可以看到每条用例的执行情况

我们在进行UI测试的过程中也踩了不少坑,有很多需要注意的地方

  • 自定义组件类名前会加上组件名前缀
  • 页面跳转、视频播放等操作需要等待后校验
  • 原生组件节点判断可以获取wxml后寻找规律,比如我们获取播放状态就是获取的`video`组件的wxml来判断的
  • wx.request等API需要自行Mock来打通流程

再来说下小程序的单元测试,我们使用`miniprogram-simulate`和`jest`来进行单元测试。

这里主要对组件结构的渲染结果,以及组件的实例方法进行验证

我们在进行单元测试的时候也踩了不少坑

  • 自定义组件wxs文件引入解析错误(现已修复)
  • wx部分API没有实现,需要自行Mock
  • 自定义组件引入Npm形式的组件暂不支持解析。

我们再回顾下前面开发流程里的另外两个问题,我们开发的构建工具只是做了发布前的Check以及构建工作,我们的构建环境其实还没有统一。

为了将我们的Devops流程做的更完善,彻底解决各个环节的问题,我们梳理了小程序Devops的架构,如图所以,分为三个部分:

左边使我们的发布平台,拥有完整的发布流程,包括了关联需求,发布前检查,CodeReview单据,发布评审单据,发布内容周知等。

右边是我们借助公司CI平台实现的小程序的CI与CD。我们部署了一台Mac机器,利用Imweapp自动化工具和小程序IDE来实现小程序的自动化构建和发布,并推送构建发布结果。

右下的客服机器人服务作为消息中心,负责推送我们构建后的二维码,以及构建发布情况进行群周知,主要是用来做消息推送。同时我们也在其基础上增加了需求群绑定项目分支,设置预览页面,触发构建等能力。

这整个架构落地到实际开发过程中,大致如下

我们可以看到触发机制里有@机器人这种操作,那么具体是怎么做的呢,又有哪些效果。

我们触发机器人,给机器人发送对应指令,就可以实现需求和群的绑定,设置预览页面路径,在群里触发构建等操作,并且我们也做了登录重试的操作,如果构建机上微信开发者工具的登录态失效,我们会回传登录二维码,扫码登录后重试之前的构建流程。

目前小程序团队也在开发用于小程序CI的相关包,独立于微信开发者工具,能更方便的接入CI,可以期待一下。

我们的这套Devops流程也在公司内积极推广,公司内已有十多个团队,三十多个小程序接入使用。

三、小程序云开发实践

解决了小程序工程化的问题,面对频繁的业务需求,特别是前端开发效率一直高于后端的场景下,我们能否有更多的发挥空间呢,小程序先入为主,我们打算尝试使用云开发。

简单介绍下云开发

云开发是腾讯云为移动开发者提供的一站式后端云服务,可用于多种客户端,目前支持到了小程序端和Web端。云开发目前主要提供了云数据库,云存储,云函数三大基础能力,构成了较完善的后端能力。

看一下我们实际的业务场景,因为我们是已有的业务,后台基础服务已经成熟,我们希望能在多个小程序间共用云函数等资源,包括和Web共用,但是小程序内置的SDK调用方式满足不了我们现有的需求。

既然使用不了云开发,我们重新梳理下目前前端业务和后台服务间的调用链路,我们的请求从前端到网关,在经过我们的CGI接口,再调用具体的底层服务,我们可以加入Node BFF层来承载部分CGI接口的能力。

如果自行搭建中间层,不免会面临下图这么多问题,这块工作量大,并且对于大部分前端同学来说可能也没有那么专业。

其实,最近很火的Serverless就能解决我们上面的问题

我们先看下Serverless

Serverless无服务器架构,包括了触发器,云函数平台,以及Bass服务。

当云函数平台接收到Event事件时,将会启动一个容器来运行函数代码,如果此时接收到了新的事件,并且也没有可用的空闲容器,则启动另一个函数实例来处理这个事件。

使用云函数,配合API网关,就能解决我们前面SDK调用的问题,满足我们的业务场景。

既然打算接入Serverless了,那么如何将我们现有的Nodejs服务迁移到Serverless,或者说怎样采用开发Nodejs应用的方式来进行Serverless开发呢。

我们看下两者的对比,网关入参结构不一致,这里我们需要进行代理层的适配,是否需要添加路由适配,以及迁移后是否涉及业务逻辑调整

从下图可以看到,我们除了要适配代理层,调用返回的Response也需要进行适配。云开发提供了serverlessplus包来解决这个问题

我们将serverlessplus和我们基于Koa开发的服务框架IMServer进行了结合,推出了imserve-serverless,用于业务的Serverless开发

这是一个使用例子,接入非常方便

让我们再看下云函数的执行过程,如图所示

我们可以看到当实例不存在时,将会走所谓的冷启动过程,冷启动涉及容器的启动,代码的下载,以及网络的打通等,会增加函数的执行时间。

如何优化冷启动呢

首先我们可以添加预处理,将耗时的操作放在函数入口外,比如服务地址解析,数据库连接等,来减少函数执行耗时。

其次,我们在函数里对服务调用时,走VPC(Virtual Private Cloud)网络来减少网络层耗时,可以看到我们改进后函数执行耗时减少了近50%,稳定在100ms左右。

如果函数逻辑比较重,路由很多,可能导致代码体积较大,在冷启动过程中会导致下载代码耗时增加。这里我们可以将逻辑较重的Controller拆分到不同的云函数里,提供统一的(鉴权)入口进行调用,以此来优化函数加载的效率,减少冷启动时间。

不过这样多了一层函数代理层,可以根据实际效果来进行选择

如图,我们还是希望使用云开发,通过SDK调用,如何解决多端复用的问题

回顾下我们之前的问题,使用内置SDK不能实现多个小程序调用同一个云开发环境

我们和云开发团队深度合作,推出了用于小程序端的WebSDK,多小程序调用得以实现

由于我们已经采用API网关调用的方式将函数上线了,现在切换到SDK调用,需要进行一些适配。

在调用方需要封装headers以及带上路由参数,函数改动就比较小,对request解析调整下就好。

除了开发,云函数的部署我们也需要规范起来。小程序开发者工具提供了云函数的部署能力,右键菜单进行部署,不过采用这种方式也存在一些问题:

  • 手动选择云开发环境,容易出错,造成现网事故
  • 依赖的内网包不能选择在线安装,只能本地上传,有些包也有需要依赖平台编译,开发环境和云函数环境不一致就有问题(可以采用Docker挂载安装的方法来解决特定环境依赖的安装)

云开发提供了CLI工具来用户云函数的操作,包括登录、初始化、函数部署、函数触发等等。有了这款工具,我们的函数完全可以另起项目单独开发,和小程序项目分开管理。

CLI提供了非常灵活的配置,可以配置超时时间,私有网络,是否在线安装依赖等。我们将配置进行抽离,不同云开发环境使用不同的配置文件,并规范化云函数工程项目。

借助CLI,我们也打造一套云函数的发布流程,统一了函数的构建环境。在开发阶段,提交代码通过Git Hook触发部署到测试云开发环境,预发布和发布阶段也部署到对应的云开发环境,并且我们在发布阶段做了代码的归档,函数如需回滚,我们使用归档的代码重新发布就好。

团队在Serverless和云开发落地的两个小程序,腾讯课堂小程序的API网关调用已迁移到SDK调用,并在对应的H5上也有落地使用。

最后总结一下,这次主要给大家分享了我们团队是如何做小程序工程化的,以及目前非常火的Serverless,还有非常方便我们服务落地的云开发,云开发也是未来的开发趋势。

希望这次分享能给大家带来一些思考,对业务带来一些帮助。

谢谢大家!

IMWeb 团队隶属腾讯公司,是国内最专业的前端团队之一。

我们专注前端领域多年,负责过 QQ 资料、QQ 注册、QQ 群等亿级业务。目前聚焦于在线教育领域,精心打磨 腾讯课堂、企鹅辅导 及 ABCMouse 三大产品。

扫码关注 腾讯IMWeb前端团队

0 人点赞