说到网络前端开发,我们首先可以想到的是浏览器、HTML、CSS、JavaScript等开发中必不可少的软件工具和编程语言。在这个专业领域,作为开发人员,我们都知道前端的所有数据都是不可信的。因为构成前端业务逻辑和交互界面的所有相关代码都可以直接被用户查看,所以我们不能保证从前端传输到后端的数据没有被用户修改过。那么有没有办法加密前端领域与业务相关的代码(如数据处理逻辑、验证逻辑等。,通常是JavaScript代码),防止用户恶意修改?这篇文章将讨论这方面的内容。
说到加密,自然会想到很多与对称加密、非对称加密、散列加密相关的算法,比如AWS算法、RSA算法、MD5算法等。在传统的B-S架构下,前端通过公钥加密的数据可以通过后端服务器对应的私钥解密获得原始数据,但对于前端业务代码,由于浏览器本身无法识别和运行这些加密源代码,传统的加密算法实际上无法帮助我们解决如何完全黑盒化前端业务逻辑代码的问题。
由于前端业务逻辑代码的实际执行细节无法完全隐藏,我们将通过另一种方式降低代码可读性伪黑盒化前端业务逻辑代码。常用的方法如下:
第三方插件。
众所周知,可用于Web前端开发的第三方插件主要有:AdobeFlash,JavaApplet和Silverlight等等。因为历史原因,这里我们不再深入介绍基于这些第三方插件的前端业务代码加密方案。在这些方面,Adobe将在2020年完全停止对Flash技术的支持,而Chrome,Edge等浏览器也开始逐步阻止或弹出使用Flash程序的网页。类似地,来自微软的Silverlight5也将在2021年停止维护,并完全停止后续新版本功能的开发。尽管Javapplet仍然可以继续使用,但与上世纪90年代末相比,现在已经很少有人使用(不完全统计)。而且,Applet应用的运行成本也大大提高。代码混淆。在现代前端开发过程中,我们最常用的降低源代码可读性的方法之一是使用代码混淆。通常意义上的代码混淆可以压缩原始ASCII代码的体积,用简短无意义的标识符代替其中的变量、常量名称,这一步可以简单理解为去语义化。以我们最常用的Uglify和GCC为例,首先是没有代码混淆的原始ECMAScript5源代码:
与以上两种工具的代码混淆压缩结果相比,UglifyJS不会重写原始代码,所有的压缩工作都是在代码原有结构的基础上进行的。而且GCC对代码的优化更接近编译器,除了常用的变量、常用名称去语义化外,还采用了常用的DCE优化策略,如对常用表达式(constexpr)进行提前求值(0.1*8+1),通过inline减少中间变量的使用等。UglifyJS在处理和优化JavaScript源代码时,以其AST的形式进行分析。例如,在Node.js脚本中处理源代码时,我们通常首先使用UglifyJS.parse方法将JavaScript代码转换成相应的AST形式,然后通过UglifyJS.Compressor方法处理这些AST。最后,我们需要通过print_to_string将处理后的AST结构转换成相应的ASCII可读代码。UglifyJS.Compressor的本质是一种官方封装的Transformer类型,其内部已经封装了许多常用的代码优化策略,而UglifyJS.TreTransformer编写自己的代码优化器。