今天思考下前端源码安全的东西(不是前端安全,只是针对于源码部分)。在我看来,源码安全有两点,一是防止抄袭,二是防止被攻破。实际上讲,前端的代码大可能是没有什么可抄袭性,安全更是形同虚设的(任何前端输入都是不能相信的)。但若是仍是想防止源码被查看,HTML、CSS并不能作什么,最终都会用露出来(最简单用Chrome开发者工具就能够看到),因此只能针对JS作文件的压缩合并和混淆。css
关于抄袭html
其实就前端来说,代码没有什么好抄袭的,大多人都是抄UI设计(这个是躲不了),还有一些富前端的控件和算法,重要之处仍是在于后端,然后端是抄不了的。因此前端文件压缩合并,目的并非防止抄袭,而是为了减小文件体积、加快载入速度,提升程序的执行性能,固然压缩也有混淆的功能。文件混淆是防止其余人查看代码逻辑,可是生成的代码比原代码体积大得多,因此文件若是作了混淆,加载速度和执行速度都会有所降低。前端
关于安全node
全部的用户输入都是不能相信的,若是后端的检查校验还作得很差,那就可能被攻破。前端代码的逻辑若是还被了解清楚,那就是雪上加霜。后端的问题咱们前端管不着,前端的代码安全,简单的能够用压缩解决、再进一步就去混淆,让别人看不懂。算法
HTML压缩express
不多有人去作HTML的压缩(特指去除空白字符和注释),根据其余资料有几个缘由:json
1. HTML文档中,多个空白字符等价为一个空白字符。也就是说换行等空白字符的删除是不安全的,可能致使元素的样式产生差别。后端
2. HTML元素中,有一个pre, 表示 preformatted text. 里面的任何空白,都不能被删除。sass
3. HTML中有可能有 IE 条件注释。这些条件注释是文档逻辑的一部分,不能被删除。安全
也是鉴于上面几个缘由,不提倡压缩HTML,经过gzip压缩就已经能达到很好的效果。
CSS压缩合并
CSS压缩合并很常见,或者说是必作的,能够由后端动态生成或工具提早生成。目的也只是为了提升加载速度,CSS即使的压缩以后,代码也是清晰可见,没有混淆说法。CSS压缩合并的工具不少,通常是用sass、less直接生成压缩后的CSS,若是是直接压缩,用grunt还不错。
JS压缩合并混淆
在生产环境上,压缩合并是必作的。就如上面说的,目的不是为了防止暴露业务逻辑,是为了提升载入速度。在上一篇文章《AngularJS结合RequireJS作文件合并压缩的那些坑》,说了一点JS压缩合并要注意的东西。除了用RequireJS,直接使用grunt来作发布是不错的方式,开发后一键调用grunt。
grunt须要配置两个文件:
package.json:声明应用信息和使用依赖库的版本
{ "name":"BingoTouch", "version":"3.0.0", "engines":{ "node":">= 0.8.0" }, "devDependencies":{ "grunt":"~0.4.0", "grunt-contrib-concat":"~0.3.0", "grunt-contrib-copy" : "~0.4.1", "grunt-contrib-cssmin" : "~0.6.0", "grunt-contrib-uglify":"~0.2.0", "express":"" } }
Gruntfile.js:声明压缩合并的文件
module.exports = function(grunt){ grunt.initConfig({ pkg : grunt.file.readJSON('package.json'), concat : { 'dist/bingotouch.js' : [ 'demo/js/ui.js', 'demo/js/module/ui.GarbageCollection.js', 'demo/js/module/ui.plugins.js'] }, uglify : { target : { files : { 'dist/bingotouch.min.js': 'dist/bingotouch.js' } } } }); grunt.loadNpmTasks('grunt-contrib-concat'); grunt.loadNpmTasks('grunt-contrib-uglify'); grunt.registerTask('default', ['concat','uglify']); }
JS的混淆我到如今为止还没用过,原理都是相似的,混淆是把JS代码变成乱七八糟的字符串,而后用eval执行。
PS:uglify自己有必定的混淆做用,但也只是对变量名的混淆,混淆度并不够。
混淆前:
function hello(){ alert('hello'); }
混淆后:
eval(function(p,a,c,k,e,r){e=String;if(!''.replace(/^/,String)){while(c--)r[c]=k[c]||c;k=[function(e){return r[e]}];e=function(){return'\\w+'};c=1};while(c--)if(k[c])p=p.replace(new RegExp('\\b'+e(c)+'\\b','g'),k[c]);return p}('1 0(){2(\'0\')}',3,3,'hello|function|alert'.split('|'),0,{}))
不一样混淆算法混淆的结果不同,并且混淆后也不是一劳永逸,仍是能够被反混淆的。另外混淆会下降程序执行性能,因此是否须要作混淆得作评估。
总结
我以为作好文件压缩合并,简单的变量名混淆就能够了,并不须要那么完全的混淆。即使是前端被人挖得清清楚楚,只要后端强劲也就没问题了。因此当你想进行代码混淆时候,想一想是为了什么,值不值得。
另外咱们有时可能会作一些富前端的外包,那咱们在交付以前能够对前端脚本进行加密,供演示使用。
1. 在代码里面设置一个代码过时时间,过时后代码就没法使用了。
2. 对js进行压缩混淆。
本文为原创文章,转载请保留原出处,方便溯源,若有错误地方,谢谢指正。