01
前言
SUMMARY
在2017年12月27日,微信小程序官方发布了一篇名为《小程序开放更多链接能力》的文章。在仔细阅读并深思熟虑之后,我将这段见解分享到了朋友圈,这也算是对未来小程序应用场景的一次大胆猜测。这几年间,小程序应用如雨后春笋般涌现,而当初这段言之准确的预测早已变成了现实。随着小程序技术的不断成熟,不仅满足了众多开发者的需求,也为用户带来了极大的便利。作为最早接触小程序的一批开发者之一,经过数年的辛勤耕耘,我今天想和大家分享一下高途微信小程序开发技术的演进历程。
“小程序开放能力日趋增强,再加上微信本身承载的用户体系,流量不是问题。关键是如何结合公司自身业务,找到适合小程序生态的场景,打造一款"好用"的轻量级"微信APP"。2018,小程序在前端领域能否掀起一波浪潮,拭目以待!!!”
02
微信小程序发展历程
微信小程序自2016年上线以来,经历了迅猛的发展阶段。从2017年全面开放给所有开发者,并推出小游戏,到2018年整体能力的升级,再到2019年引入直播、公布PC版本,并提供云开发能力,小程序技术不断演进的同时也不断丰富了用户体验。截至2020年,小程序的日活用户已达3亿+,而到2021年更是飙升至4.5亿+。随着2021年开发助手的推出,微信小程序继续成为开发者和用户双赢的平台。在2022-2023年,微信小程序持续创新,致力于满足不断增长的需求,巩固其在移动应用领域的关键地位。然而,值得注意的是,随着用户规模的急剧扩大,官方重心也从开发者逐渐转向用户,因此在策略和规范方面变得更为严格。微信小程序通过不断优化和创新,已经发展成一个庞大而多元化的生态系统,为开发者和用户提供了丰富的功能和便捷的应用体验。
我们的第一个小程序
选择微信小程序作为我们创新型产品的平台有几个关键的考虑因素。首先,微信小程序依托微信庞大的用户生态,具备巨大的流量和传播优势。这为我们的产品提供了广泛的曝光和用户获取的机会。其次,小程序相较于原生APP,不仅在多端适配方面表现出色,而且在开发成本上也具备显著的优势。这对于创新业务而言,降低了试错的成本,让我们能够更快速地验证和迭代创意。同时,微信小程序提供了接近原生体验的用户界面,相比于H5开发,具备更高的性能和更好的用户交互,为用户提供更加流畅的产品体验。综合而言,选择微信小程序为创新产品提供了强大的用户基础、低成本高效率的开发环境,以及接近原生的用户体验,使得我们能够更好地聚焦在创新和用户体验上。
迎合热点出用户产品
自2017年小程序向开发者开放以来,市场迅速涌现了各种各样的小程序应用。在这个新技术兴起并应用的过程中,我们在2017年年底也决定在小程序领域进行一次尝试。当时的决策主要考虑了几个关键因素:首先,微信庞大的用户生态体系为我们提供了巨大的流量机会着实诱人;其次,小程序作为一种轻量级应用,无需繁琐的安装和卸载过程,用户即刻可用,具有出色的用户体验。
在2017年年底,正值答题类游戏风靡一时,抖音、快手等平台纷纷推出了各自的答题挑战,用户们每天积极参与,争取赢取大奖和现金奖励。因此,结合我们自身的教育特色,我们紧急开发了一款以古诗词场景为背景的答题挑战赛小程序,并将全新发布的iPhone作为奖品,成功推向用户市场。实际上,这个小程序为我们带来了超出预期的价值,在短短半年多的时间里,累计用户和日活都有着不错的数据表现,让我们有幸体验到了率先“吃螃蟹”的成功滋味。
中规中矩做技术实现
在早期,小程序开发技术生态尚未如今般完善,市面上的开发框架也相对较少。回顾那个时候,我记得曾经调研过wepy,但考虑到其刚刚问世,成熟度尚不够高,最终在技术选型上决定采用原生微信小程序。由于大家通常在已经相当成熟的三大框架生态中进行开发,与之对比,微信小程序技术生态当时确实还不够成熟。因此,在那个阶段我们也面临了不少问题,比如不支持npm包、自定义组件实现过程繁琐,甚至连预编译样式都不受支持。这些问题带来了一些困扰,对开发效率也造成了一定程度的影响。
2017年的微信小程序就像一个刚刚出生的婴儿,此时期望它能够自由奔跑似乎有些不切实际。作为一项新兴技术,我们需要以更包容的心态对待它,认识到它存在许多不足之处,但也在不断改进。作为开发者,我们更应该积极解决问题,推动整个技术生态的进步。在那个时期,原生小程序自身的一些缺陷得到了官方团队的积极迭代升级优化,他们的响应速度也非常迅捷。在项目工程化方面,我们通过利用现有的技术生态,努力搭建了一套适应当下开发的小型框架,以解决开发效率问题。无法支持预编译样式?我们就通过Gulp监听文件变化进行转换。不支持ES6?我们就通过Webpack插件进行转换。总的来说,面对困难,我们总有办法解决,我们致力于让原生小程序的开发体验更接近大家熟悉的三大框架,剩下的则交给时间和官方团队,让小程序生态不断变得更加完善。
事实证明,随着时间的推移,小程序生态日益完善。小程序官方在基础能力上进行了多次版本迭代,引入了Component后,微信小程序真正实现了组件化开发;分包加载的引入解决了项目体量和代码多的难题;新增的实时音视频组件扩展了小程序的应用场景;而云开发的支持使得开发者能够更全面地处理前后端事务;性能方面通过底层能力的优化为用户带来了更卓越的体验。在技术生态方面,广大开发者积极贡献力量,市场涌现了许多优秀的开源框架和组件库,使得整个小程序开发者社区受益匪浅。
在成功推出答题竞赛类小程序后,我们陆续开发了一系列小程序,涵盖打卡、背单词等多个领域。然而,与第一款小程序取得的成功相比,这几个小程序在用户量和日活数据上都经历了较大的下滑。随着业务的转型,我们的工作重心也从小程序转移到平台能力建设,甚至在相当长的一段时间里,我们都没有再上线新的小程序。但作为忠实的小程序开发者,我们仍然持续关注着小程序基础能力的迭代更新和生态建设。
重返小程序阵地
在初期考虑到多端小程序的需求,我们选择了Taro作为技术框架。然而,随着业务的深入发展,同时丢弃了多端的诉求,Taro的优势逐渐消失,反而为我们引入了一些麻烦。通过多个小程序项目的实践,我们得出了结论:在纯粹考虑微信小程序的情况下,原生开发才是最佳选择!原生开发者生态丰富,没有其他的额外负担,加之原生框架不断迭代优化,开发效率和项目工程化方面也不再成为问题。
2018年和2019年是小程序稳步发展的两年,随着时间的推移,我们的业务也日益蓬勃。回顾到2020年,平台的能力建设趋于稳定,我们同时享受到了微信裂变带来的巨大流量红利。一方面,我们希望进一步依托微信生态,通过一些工具型产品获取更多流量;另一方面,我们也期望推出一些轻量级的用户产品,借助微信传播提升我们品牌的知名度和口碑。
产品规划
伴随着微信小程序取得的巨大成功,其他几家平台也陆续推出了自己的小程序,百度小程序、支付宝小程序、抖音小程序……
技术选型
在小程序的开发实践中,我们经历了从Taro到微信原生小程序的转变。
考虑的因素
1、满足当前需求且支持迭代
我们首先考虑的是选用的技术框架能够满足当前项目的需求,并且能够支持未来的迭代和扩展。这有助于确保项目长期稳定发展。
2、技术栈的入门门槛较低
我们希望选用的技术栈具有较小的入门门槛,以便团队成员能够迅速上手。同时,我们将当前的技术栈作为参考,避免过大的学习和适应成本。
3、有强大的研发团队和活跃的社区
为了确保在开发过程中能够获得及时的支持和解决问题,我们选择了拥有强大研发团队和活跃社区的技术框架。这有助于快速解决可能出现的技术难题。
综合考虑这些标准,我们最终选择了Taro作为开发框架。Taro不仅符合我们的技术要求,还具有跨平台的能力,使得我们能够更灵活地应对未来可能的变化。这次技术选型为项目的顺利开展奠定了基础,并在后续的开发过程中取得了良好的效果。
选择Taro的原因
1、多端支持和引流需求
考虑到未来可能在百度小程序上进行引流,选择支持多端的框架是有远见的决策。Taro和Uni-app都是当时比较热门的框架,能够满足这一需求,并且拥有活跃的社区支持。
2、技术栈一致性
团队主要使用React作为技术栈,选择Taro是符合技术栈一致性的选择。这不仅有助于降低学习成本,也使得组内成员能够更加高效地共享和复用代码。
3、组件复用和H5兼容性
由于一部分组件可以和H5复用,选择Taro这样支持React的小程序框架是合适的。这样不仅提高了开发效率,也保证了一致的用户体验。
总体来说,当初的选型考虑到了未来可能的业务扩展和团队的技术优势,是基于全面考虑的决策。在实践中遇到的问题是正常的,尤其是技术生态在不断变迁。现在重新审视选择,可以根据实际情况进行调整,例如解决Taro本身的bug或者考虑其他更适合当前需求的框架。继续保持对技术栈的敏感性和灵活性,以适应项目的发展。
问题暴露
随着对Taro实际的深入使用,在实践中也暴露了一些问题:
1、Taro存在的bug
我们遇到了Taro本身存在的bug,表现为相同的配置在微信原生小程序上能够正常运行,但在Taro上出现问题。为了完成开发,我们不得不采用一些hack的方法去解决这些问题。
2、性能优化方面的挑战
在性能优化方面,由于框架本身的一些限制,我们发现很难实现显著的提升。
3、Taro3版本的问题
Taro3的前两个版本出现了包体积骤增的问题,导致从Taro2迁移到Taro3的成本较高。
4、百度小程序未再提上日程
原计划的百度小程序并没有再次提上日程,我们一直专注在微信小程序场景,Taro多端的能力并没有发挥出对应的价值。
用回原生
在实际开发中遇到的问题促使我们重新审视技术选型。为了确保小程序项目能够在稳定性和最终产品体验方面实现快速迭代,我们作出了重新回到原生小程序的决定。这一选择意味着我们需要重新评估小程序在过去两年中的迭代和发展,以更好地适应项目的需求。
构建小程序矩阵的想法萌芽
微信小程序提供的快速开发小程序的架构模式下,逻辑层的App和Page分别负责程序和页面的注册。尽管这种模式对于简单的小程序应用实现了快速开发,但对于业务流程较为复杂的项目,却带来了一些问题。
1、初始化项目模板简陋
使用微信小程序开发工具初始化项目时,项目的内容结构相对简单。然而,每次启动项目开发前,都需要进行一些必要的配置,通常需要花费1-2个工作日的时间。为了避免重复这部分工作,我们认为有必要将一些基础配置进行沉淀,形成一个项目初始化模板。
2、数据状态管理混乱
(1)全局对象混乱:由于App作为全局对象,许多全局数据都需要配置在这里。将它们都写在app.js中容易导致代码混乱。在实际开发中,我们需要对这部分进行分层处理,以提高代码的可维护性。
(2)缺乏状态管理:小程序并没有提供状态管理功能,开发者需要调研第三方工具。在每个项目开始时,都需要根据业务形态评估状态管理部分。积累关于状态管理的业务实践经验是十分有价值的。
3、构建发布管理问题
小程序作为轻量级的前端框架,提供了一套便捷的构建和发布管理。通过开发者工具和小程序后台管理系统,可以方便地进行小程序的构建和发布审核。然而,在实际开发中,可能会遇到一些代码管理的问题,比如提交时忘记合并master,导致代码丢失;构建代码没有记录;多人协作容易出现问题等。在发布环节,也存在缺失灰度发布能力的问题。
4、数据上报管理问题
数据上报作为每个项目的基础能力,包含性能的上报、业务上报和用户流程的上报。在每个小程序的开发中都需要重复开发这部分功能,每个参与者也都有一定的学习成本。因此,我们需要提出相应的工具或方法来解决这个问题。
除此之外,基于当时的业务判断,我坚信未来会涌现许多工具类小程序。结合我们的业务,我们有望构建自己的小程序矩阵。要让房子盖得高,地基就必须打得牢固。因此,基于以上背景,我们决定启动自己的小程序基础能力建设,首要任务是创建一个微信小程序的模板项目。该模板的目标是让开发人员能够一键生成项目,实现零配置就能解决上面提及的这些问题,使他们更专注于业务开发,提高开发效率。
小程序矩阵的架构设计
DESIGN
我们一直秉持着迭代更新的理念,让小程序矩阵的架构随着业务不断迭代升级。在一个个项目落地验证的过程中,整个架构也逐步丰富完善,尤其在流程化和提效方面取得了显著成效,基于CLI工具,我们能一键生成项目模版,且具备项目所需的基础功能库,可以直接进入业务开发,基于组件的沉淀,项目提效在20%+。基于我们多业务线的特色,我们已经具备了快速孵化同类型小程序的能力。
经历了2017年的初步接触、2020年的工程化探索,以及2021-2023年的实践总结,我们在小程序的基础建设方面已经实现了整个流程的覆盖。
项目初始化:我们提供了脚手架工具,使得获取一个小程序的开发模板变得简便。
开发阶段:我们的小程序模板不仅提供了基础的数据管理能力,通用的工具库和组件库,还针对页面级别进行了扩展。这使得使用者可以专注于业务流程的开发,而不必花费过多时间在基础功能的搭建上。
提测:我们提供了CI工具,规范了构建流程,以确保代码的质量。
上线:我们与轻舟(内部自研平台,用来规范前后端发布上线,整合日志查询,告警等功能)合作,引入了灰度发布的策略,以确保上线的稳定性。
监控:前端代码的异常监控,目前采用微信小程序的we分析。我们通过设置异常的阈值,将相关负责人添加到告警群,通过系统层面的自动对接,以便开发者及时响应和解决异常情况。
性能优化:我们引入了Habo(内部数据上报工具)做基础性能指标数据的统计和setData的耗时统计,同时也做了核心场景的主动上报,为问题的定位提供了日志辅助,在实践中,我们也沉淀了性能优化的一些通用方案。
Version 1.0
在2020年,我们在组内成立了一个虚拟的技术小组,专注解决微信小程序所面临的问题,并制定了一些工程化方面的处理策略。
我们实现了一个强大的脚手架,通过自定义的mp-cli init命令获取小程序项目的模板。该模板包含了初始化项目时必要的封装,并提供了编译配置,支持别名、热更新以及自定义插件。针对小程序项目的上线发布流程,我们在脚手架中内置了自动化发布功能。
同时,我们规划了小程序的组件库,对其进行了分层配置,包括业务层和公共组件层。我们制定了公共组件开发和提交的标准,以确保组件的高质量和可维护性。
为了更好地监控和改进性能,我们引入了小程序的性能统计工具。我们制定了性能统计的指标,并结合Habo对小程序的Page和Component进行了改造,实现了性能指标的自动打点上报。
随着第一版脚手架的落地,我们在小程序方面的架构探索初见成效。目前,mp-cli已成功应用于几十个小程序中, 解决了项目初始化模板简陋的问题。可以让使用者通过一个命令就可以创建一个带有模板的小程序项目。简化了小程序开发的前置准备工作。
Version 2.0
在多个项目中实践脚手架后,我们发现了一些问题。通过结合具体的业务场景,我们对脚手架提出了更高的要求,并在实践中不断摸索解决方法。这个过程让我们更深入地理解了不同项目的需求差异,也推动了脚手架的不断优化和升级。同时也沉淀了一些我们在微信小程序开发场景下的最佳实践。
小程序的数据传递和状态管理
我们在日常的开发中遇到的数据问题,一般分为如下几种:
(1)支持当前页面数据展示和状态变化
(2)多界面共享的数据
(3)数据一旦改变触发其他地方状态变化
针对第一种情况:我们通常使用小程序提供的data和setData来解决,需要注意的是尽量遵循“非必要不使用”的原则,因为setData的更新流程问题,具体原因在这里就不展开讨论。
针对第二种情况:常见的解决方法是将数据存储在globalData中或者本地缓存中。最初我们直接调用app.globalData或小程序提供的本地存储API,但随着代码的增多,变得难以维护,每次存取数据都需要查找对应的key值。在上线阶段,小程序会在prod和test环境之间切换验证,而没有区分环境的用户信息存储可能导致一些奇怪的问题。因此,我们开始设计并封装了globalData和本地缓存的方法。
在数据缓存层针对API进行封装:
(1)存储的变量区分环境
(2)存入的变量进行合法性校验
(3)设置定时存储功能
为了避免存取时要复制key的情况,可设置一个配置变量,在这里定义过的key,可自动生成对应的set和get方法。这样用户在使用时,只用在一个地方定义变量即可。可以更好的管理缓存数据。
针对第三种情况:常用方案有两种
(1)事件通知机制event bus
(2)使用mobx等第三方库进行状态管理。
其中使用事件通知的方案,需要在页面初始化的时候进行监听,在页面卸载时要注意移除监听。如果代码中有很多监听事件时代码就变得难以维护,此时需要考虑引入状态管理的方案来对代码进行改进。
针对数据场景的分析和方案设计,我们可以解决小程序场景下的数据管理问题。不同的业务场景都有适用的数据管理方案,使使用者能够根据业务特征选择合适的方法。这既解决了数据管理的问题,也规范了开发模式。
CI 构建
在小程序的开发,提测,问题修改和上线的整个环节中,存在一些繁琐的操作,缺乏像H5开发流程那样的规范。
小程序提供的开发流程:主要的痛点如下:
(1)代码提交依赖开发工具
(2)当有2个以上人开发区提交的时候,就会需要到小程序后台频繁的切换体验版
(3)每次的提交的测试版本没有记录
(4)上线后需要手动合并代码,容易导致代码忘记合并的情况
为此我们在脚手架时就针对这个环节了做了优化
修改后的方式:
(1)摆脱了开发工具的束缚,通过执行命令进行构建发布(或者使用Jenkins的方式)
(2)无需切换到体验版,统一为微信小程序的CI机器人版本
(3)每次的构建会同步到灵犀(内部沟通工具),每次的修改提交都有记录,还可以起到一定的提醒作用;
(4)该方案未解决合并代码的痛点
(5)如果采用Jenkins构建方式,每个小程序对应的开发者需要自行创建Jenkins的流水线
最终方案
接入轻舟,完善小程序的整个发布流程;实现规范化管理。
小程序的灰度策略
小程序提供的灰度发布策略有两种:按微信号灰度和按比例进行灰度。
这两种方式都是前端灰度,前提是后端已经上线,通常用于验收环节或者前端较大改动需要在线上灰度验证的情况
然而,在实际开发中,可能会出现一些复杂的情况。例如,如果后端已经上线,现有的线上用户必须更新到最新版本才能正常使用,但由于小程序需要审核,会产生一些时间差。在这种情况下,我们需要设计新的灰度方案来处理线上回归和弥补时间差。
目前,我们与轻舟团队合作,开发了小程序的新灰度方案。小程序会在接口请求的header中添加灰度标记(小程序的版本号mp-version),后端上线时会根据小程序的版本信息设置灰度策略。在小程序进行线上验证和提交审核期间,真实用户访问的仍然是之前版本对应的后端服务。一旦小程序审核通过,后端将取消灰度。这时可能出现以下情况:
1.未打开小程序的用户再次打开时可以更新到最新的小程序代码(微信的更新机制,退出后30分钟会清除缓存,新版本发布后通常在24小时内发布。体感一般在10分钟内)。
2.针对正在使用的用户,前端将添加版本校验通知,提示用户更新版本。因此,小程序的灰度策略应根据业务场景选择不同的方案。
未来可期
关于小程序架构的建设,我们还在不断地完善,以下是一些正在进行中的工作:
Habo埋点自动化检测
数据的埋点上报统一使用Habo进行,而Habo也有小程序的版本。目前,小程序数据上报的校验主要依赖开发人员和测试在测试环节录入gid并在罗盘上进行校验来完成。然而,这种方式存在依赖人工操作,可能导致遗漏或未覆盖到的情况,从而引发数据问题。
与H5版本不同,H5的数据上报中,合法性校验是在轻舟上线环节制定的准出策略中进行的。由于小程序目前尚未接入轻舟,因此在小程序的数据埋点检测方面,我们正在规划接入轻舟的方案,以提高数据埋点的自动化程度和准确性。
通用的模板组件
在进行小程序性能统计时,为了实现统一的埋点,我们采用了装饰器模式,对Page函数和Component函数进行了重写。在保持原有功能不变的前提下,我们添加了一些内置的功能,例如上报小程序从项目创建到界面加载的耗时统计。
基于这一设计,我们考虑在此基础上进行扩展。通过将路由拦截配置、分享配置、事件监听的注册和删除等功能放置在扩展函数中,我们在Page和业务层之间创建了一个中间层。这样便于我们添加一些共用的方法和属性。
组件库升级
我们已发布了组件库的一个版本,然而由于时间较长,一些组件可能不太适用,同时也有一些新的组件需要加入。因此,我们正在进行组件库的新版本升级和改造,主要体现在以下两个方面:
针对小程序端通用能力的组件,我们进行了单独打包。
例如,鉴于微信小程序最近关于隐私协议和手机号获取收费的问题,我们单独封装了授权隐私协议组件以及获取手机号的组件(支持多种获取方式)。这两个组件已经在多个小程序项目中使用,为我们快速满足审核需求提供了解决方案。
我们将业务相关的组件从原有的组件库中拆分出来。
由于之前设置的业务组件不再符合当前的需求,我们决定采用单独设置组件包的方式,让组件库专注于通用的基础组件。这样有助于更好地满足业务的发展和变化。
工具库函数升级
在第一个版本中,我们没有设置工具库,但在最新的规划中,我们决定添加一个工具函数库。在开发设计这个库时,我们主要关注以下两个方面:
系统功能:
这一部分主要涵盖小程序的常用API能力封装,包括小程序的设备信息、小程序调用原生能力的授权情况、小程序的版本升级等。我们致力于提供一套系统功能的工具函数,以便开发者能够更轻松地处理这些常见需求。
业务常用函数:
这一部分是在日常业务开发中积累的经验,包括防抖、时间格式的处理、数据类型的判断、深拷贝等。这些函数旨在解决在业务开发中常见的问题,提高开发效率。
目前,这部分工具库仍在开发阶段。我们的目标是将在小程序开发中积累的经验沉淀下来,为当前参与开发的伙伴提供解决方案,为将来加入的伙伴提供参考模板。我们希望通过这个工具库,让小程序的开发变得更加顺畅,让大家不再面对"刀耕火种"的挑战。
小程序矩阵初具规模
万事开头难,在过去的几年时间里,我们在小程序领域持续深耕。虽然前进的速度或许不算快,但我们一直坚定地朝着正确的方向努力。截至目前,我们已经成功开发并交付了超过20个小程序,涉及打卡、做题、背单词、问答对话等多个功能领域,甚至尝试进入了我们不熟悉的直播场景。今年,借助AI的浪潮,我们迅速搭建了几个AIGC类的工具。在看到这些成果的时刻,我们深知一切的努力都是值得的。坚持做难而正确的事情,需要有耐心,更需要对未来充满信心。
03
结语
对于个体用户而言,微信小程序让我们可以更加方便地获取生活服务节省了时间和成本,提高了生活质量。同时微信小程序也提供了各种娱乐服务,为用户提供了更加丰富的娱乐生活。对于公司或创业者而言,微信小程序则提供了一个低成本、高效率的项目平台,可以通过开发微信小程序来实现自己的idea。
小程序的技术浪潮早已掀起,目前已经进入平稳发展期,在多年的实战中历练,我们也在自己的业务场景下摸索出了一套适合我们自己的技术架构,未来我们也还有很长的路要走,我们也希望这套架构能够越来越完善,我们致力于结合实际业务场景,孵化更多有实用价值的小程序应用,为业务的腾飞助力。同时也欢迎对小程序感兴趣的伙伴加入,一起为“这座房子”添砖加瓦!
作者:周玉娟、聂建辉
来源:微信公众号:高途技术
出处
:https://mp.weixin.qq.com/s/AZtylZ7-59BvLrSzDgoDYQ