之前就有同学提问,如何让自己的小程序代码不被别人恶意反编译呢?社区里也有很多类似的投诉,辛辛苦苦做的小程序UI设计都被别人抄了去,一直没有很好的解决办法。
我们知道了小程序的本质其实就是一个混合模式应用,基本原理和流式应用类似,小程序的页面样式业务逻辑最终都会被打包成JS代码。所以这个代码安全问题的核心就变成了如何给JS代码加密,如果你有小程序开发经验的话那应该知道微信开发者工具本身提供了代码保护功能,但是这个只是起了基础的保护作用,碰上JS高手实际上作用并不大。
对于JS代码的保护,必须要混淆和加密共用。单独的JS源代码加密,是行不通的,更不可能有所谓的JS不可逆加密。普通页面的JS代码在浏览器端执行时,必须转解密还原成原始代码,才能被浏览器的JS引擎识别和运行。在解密后,会存在完整的原始JS代码。手机端小程序的JS代码是运行在JSCore中的,必须还原成原始代码才能被JS引擎所识别,还原之后有多种方法可将原始的JS代码显示出来,而混淆只是增加了还原的成本。因为小程序代码是明文存放在微信的CDN服务器上进行分发的,所以如果使用了代码保护或者使用第三方框架比如uniapp、mpvue等进行开发会借助webpack打包器进行压缩混淆操作,那么小程序反编译之后得到的实际上是混淆状态的明文代码,只是易读性差了些。有的同学会问了,为什么微信不对小程序代码进行加密呢?其实这个也很好理解,小程序的目的就是为了即用即走,快速打开,承载的大多是轻量级的业务,而如果代码加密那必然就会有解密,小程序的代码在被注入运行环境之前运行之前肯定要进行解密还原成明文,而还原势必会对打开速度存在影响,所以安全与性能之间确实很难取舍。现实的问题是,目前已经有几百万的小程序在线上运行了,如果这个时候再引入加解密的机制必然会是一项复杂的工程。
那么如何最大限度地保护我们的代码呢?
代码混淆
既然加密做不到,那只能在混淆上多做点文章了,可以用webpack之类地打包器对代码进行混淆保护,觉得麻烦的话可以在微信开发者工具上传代码时勾选代码保护,总还是有一点作用的。当然混淆方案大致有两类,正则替换和语法树替换,语法树替换的混淆方案更加安全,有兴趣的可以自行查阅。
信息脱敏
小程序打开时会把明文代码下载到本地,所以博主建议不要把敏感信息,比如各种secrect,密钥之类放在前端了(这是把大门钥匙扔在门口的行为),另外核心业务逻辑尽量放到后台去执行,虽然前端JS也可以做,但是你可以告诉和你对接的后端同学,为了保证系统的安全性,重要的业务逻辑操作还是在后端处理之后返回给前端比较安全。
云开发
云开发很火,可以提议给公司的领导层,你的leader去推动这个事情,这个和上面的核心业务后端化是一个逻辑,重要的东西可以用云函数去实现,这样别人几乎不可能拿到你的核心代码了,而且运维也不用操心。云函数的通讯都是基于微信的私有链路加密的,几乎不存在破解的可能,所以可以放心使用,多去尝试云函数化。云开发的appid和资源进行绑定的,而且必须走微信私有协议。用别的appid也没办法调用私有资源,除非你主动环境共享(也只限制同一主体)就目前情况,被无感盗用几率为0。
需要注意的是 project.config.json 里要配置好 cloudfunctionRoot ,不配置的话反编译会包含云函数代码。
接口加密
这一点是一位读者朋友提出的,属于协议层的方法了。
通过服务和js的一种协议自动生成。生成的密钥最好也是动态的。比如token转16进制 再通过二进制位移,服务端再通过一样的逻辑去反推密钥。再解密数据。这些密钥生成的逻辑代码要混淆的够好。破解的难度就越高。
说到这里,大家应该都明白了,小程序前端加密意义不大,能做的是尽可能地混淆,最大程度降低可读性,增加别人还原你代码的成本,这个其实也能挡住不少恶意人士了。