-->

裂伤嵌套类和变量uglifyjs(Mangle nested classes and variabl

2019-09-01 17:52发布

我用uglifyjs来缩小级联组文件,它工作正常,但还不够好。 内置LIB使用命名空间,所以类,函数和常数存储在一个根名称空间变量:

(function() {
  var root = { api:{}, core:{}, names:{} };

  /* util.js file */
  root.names.SOME_LONG_NAMED_CONST='Angel';

  /* Person.js file */
  root.core.Person = function(name) { this.name = name };

  /* API.js with the functions we want to expose */
  root.api.perform = function(param_for_api) { /* do something */ }

  window.lib_name.perform = root.api.perform;

})();

这是精缩到不那么最低版本

(function(){var a={api:{},core:{},names:{}};a.names.SOME_LONG_NAMED_CONST="Angel",a.core.Person=function(a){this.name=a},a.api.perform=function(){},window.lib_name.perform=a.api.perform})();

我明白丑化可能认为根var是一个数据结构,必须保持原样,不能改变。 有没有办法让丑化根命名空间裂伤嵌套的名字呢?

Answer 1:

当最小的Javascript你只能改变的变量的名称,该API,核心和名称不变量,但一个对象的属性。 如果这些数据是由极小改变,你将有可能获得意想不到的效果。 如果在你的代码,你会打电话

root["api"].perform = function()...

甚至像

function doIt(section, method, argument) {
    root[section][method](argument);
}
doIt('api','perform', 101);

所有完全合法的JS,但一个极小永远无法弄清楚发生了什么事情。



Answer 2:

我一直在尝试使用--mangle-props UglifyJS2的,可以告诉你:“ 它使一个烂摊子 ”。

正如有人指出:“ 开发者应该决定要什么裂伤性质,不uglifyjs”

我使用这个选项接近问题:

--mangle-props
--mangle-regexp="/_$/"

正则表达式匹配,并在最后一个下划线的任何财产。

你问根命名空间裂伤嵌套名称。 所以,你的代码:

(function() {
  var root = { api:{}, core:{}, names:{} };

  root.names.SOME_LONG_NAMED_CONST_='Angel';

  root.core.Person_ = function(name) { this.name = name };

  root.api.perform_ = function(param_for_api) {  }

  window.lib_name.perform = root.api.perform;
})();

会导致这样的:

(function() {
    var n = {
        api: {},
        core: {},
        names: {}
    };
    n.names.a = "Angel";
    n.core.b = function(n) {
        this.name = n;
    };
    n.api.c = function(n) {};
    window.lib_name.perform = n.api.c;
})();

命令: uglifyjs --beautify --mangle --mangle-props --mangle-regex="/_$/" -- file.js

如果你想裂伤根命名空间的第一级(api, core, names)只是把下划线他们(api_, core_, names_)你是在控制;)

只是一个侧面说明 :当你重整性质由其他JS文件可用,你应该使用相同的命令一起裂伤的所有文件,所以同样的标识将被用于在所有的文件。



Answer 3:

除了@JanMisker的点(这是完全有效的),重写特性是不安全的,因为它们可以暴露于代码微小的范围之外。

虽然自执行的函数有一个范围,如果代码是唯一

(function() {
  var root = { api:{}, core:{}, names:{} };
  root.names.SOME_LONG_NAMED_CONST='Angel';
  alert(root.names.SOME_LONG_NAMED_CONST); // some code that does something
})();

的确,在函数外,就没有办法访问根对象,所以重写属性名称是安全的,下面的代码会导致相同的:

(function() {
  var a = { b:{}, c:{}, d:{} };
  a.d.e='Angel';
  alert(a.d.e);
})();

但是,即使你是你的私人范围内,您可以访问,更重要的是外部范围的变量赋值! 想象一下:

(function() {
  var root = { api:{}, core:{}, names:{} };
  root.api.perform = function(param_for_api) { /* do something */ }
  window.lib_name = root.api;
})();

你不仅暴露功能,但上面有一个函数的对象。 该函数将是从那里的窗口中可见的任何地方可见。

因此,例如写在JavaScript控制台下会产生不同的结果与不缩小:

window.lib_name.perform(asdf);

随着微小你会写:

window.lib_name.f(asdf);

或类似的东西。

请记住,有可能永远是你的微小之外的代码。

这并不是说关键是有绝对的最小的JS,但如果由于某种原因,重要的(例如:外星人绑架你的继女,并让她回来的唯一方法是来缩小这种低于10​​0个字左右),你可以手动替代不期望的长的属性名称为更短的一个,只要确定它不会被任何地方暴露,并且不通过关联数组符号(被访问root['api']



Answer 4:

如@扬Misker在他的回答解释说,物业名称重整是不是一个好主意,因为它可能会破坏你的代码。

但是,您可以变通办法,通过定义属性的名称作为本地变量,并修改所有的.properties为[键],使较小的文件大小:

(function() {
  var API = 'api';
  var CORE = 'core';
  var NAMES = 'names';
  var SLNC = 'SOME_LONG_NAMED_CONST';

  var root = {};
  root[API]={};
  root[CORE]={};
  root[NAMES]={};

  /* util.js file */
  root[NAMES][SLNC] ='Angel';

  /* Person.js file */
  root[CORE].Person = function(name) { this.name = name };

  /* API.js with the functions we want to expose */
  root[API].perform = function(param_for_api) { /* do something */ }

  window.lib_name.perform = root[API].perform;

})();

因为现在所有的属性变成了局部变量,丑化JS会裂伤/缩短变量名和结果,你总文件大小减少:

!function(){var a="api",b="core",c="names",d="SOME_LONG_NAMED_CONST",e={};e[a]={},e[b]={},e[c]={},e[c][d]="Angel",e[b].Person=function(a){this.name=a},e[a].perform=function(){},window.lib_name.perform=e[a].perform}();

然而,减少文件大小并不意味着你会得到真正的服务器上下载更短的时间,因为通常我们的HTTP传输gzip压缩,大部分重复的会被你的http服务器进行压缩和它做了更好的工作比人类。



Answer 5:

丑化(今天)最新发布的具有对象属性忙玲,见v2.4.18。 它还支持保留的文件排除你不想错位既对象属性和变量。 看看这个。

使用--mangle-props的选择和--reserved-file filename1.json filename2.json等....



文章来源: Mangle nested classes and variables with uglifyjs