1 | const path = require('path');
|
2 | const fs = require('fs');
|
3 | const id = 'SizePlugin';
|
4 | const table = require('table').table;
|
5 |
|
6 |
|
7 | function flatten(ary){
|
8 | var ret = [];
|
9 | ary.map(function(el){
|
10 | if (Array.isArray(el)) {
|
11 | ret = ret.concat(el)
|
12 | } else {
|
13 | ret.push(el)
|
14 | }
|
15 | });
|
16 | return ret;
|
17 | }
|
18 |
|
19 |
|
20 | function getSize(ary){
|
21 | let defaultSize = 0;
|
22 | ary.forEach(function(el){
|
23 | defaultSize += el.size;
|
24 | });
|
25 | return defaultSize;
|
26 | }
|
27 |
|
28 | class SizePlugin {
|
29 | apply(compiler){
|
30 | compiler.hooks.done.tap(id, (compilation) => {
|
31 | var map = {}, tree = {}, pages = [], Identifiers = {};
|
32 | var assetsInfo = compilation.toJson().assets;
|
33 |
|
34 | compilation.toJson().modules.forEach(function(module){
|
35 |
|
36 |
|
37 | if (/\/node_modules\//.test(module.id)) {
|
38 | return;
|
39 | }
|
40 |
|
41 | let fileId = module.id.split(/\/source\//)[1];
|
42 |
|
43 | if (/(pages|app)\/?/.test( fileId ) && /\.js$/.test(fileId) ) {
|
44 | pages.push(fileId);
|
45 | }
|
46 |
|
47 |
|
48 | var reasons = module.reasons
|
49 | .map(function(el){
|
50 | if (el.moduleId) {
|
51 | return el.moduleId.split(/\/source\//)[1];
|
52 | } else {
|
53 | return '';
|
54 | }
|
55 | });
|
56 | reasons = Array.from( new Set(reasons) );
|
57 |
|
58 |
|
59 | if (reasons.length > 1) {
|
60 | Identifiers[fileId] = 1;
|
61 | } else {
|
62 | Identifiers[fileId] = 0;
|
63 | }
|
64 |
|
65 |
|
66 |
|
67 | map[fileId] = {
|
68 | id: fileId,
|
69 | reasons: reasons,
|
70 | assets: module.assets
|
71 | }
|
72 |
|
73 | });
|
74 |
|
75 |
|
76 | pages.forEach(function( pagePath ){
|
77 | for(let i in map) {
|
78 | if (map[i].reasons.includes(pagePath)) {
|
79 | tree[pagePath] = tree[pagePath] || [];
|
80 | tree[pagePath].push(i);
|
81 | if (!tree[pagePath].includes(pagePath)) {
|
82 | tree[pagePath].push(pagePath);
|
83 | }
|
84 | }
|
85 | }
|
86 | })
|
87 |
|
88 |
|
89 | let ret = {};
|
90 | fs.readdirSync(path.join(process.cwd(), 'source', 'pages'))
|
91 | .filter(function(el){
|
92 | return /^\w+/.test(el);
|
93 | })
|
94 | .forEach(function(plat){
|
95 | ret[plat] = {
|
96 | plat: plat,
|
97 | dep: [],
|
98 | common: []
|
99 | }
|
100 | })
|
101 |
|
102 |
|
103 | for( let i in tree ) {
|
104 |
|
105 | let fileDeps = tree[i].map(function(dep){
|
106 | var depAssets = map[dep].assets;
|
107 | return depAssets.map(function(el){
|
108 | let target = assetsInfo.find(function(item){
|
109 | return item.name == el;
|
110 | });
|
111 | return {
|
112 | name: target.name,
|
113 | size: target.size,
|
114 | onwer: dep
|
115 | }
|
116 | });
|
117 | });
|
118 |
|
119 | fileDeps = flatten(fileDeps);
|
120 |
|
121 | if (!/app\.js/.test(i)) {
|
122 | let plat = i.split('/')[1];
|
123 | ret[plat].dep = ret[plat].dep.concat(fileDeps);
|
124 | } else {
|
125 |
|
126 | fileDeps = fileDeps.filter(function(el){
|
127 | return !/^pages\//.test(el.name) && !/React\w+\.js$/.test(el.name)
|
128 | });
|
129 | ret.app = ret.app || {
|
130 | plat: 'app',
|
131 | dep: [].concat(fileDeps)
|
132 | }
|
133 | }
|
134 |
|
135 | }
|
136 |
|
137 | let output = [];
|
138 | for(let plat in ret) {
|
139 | let dep = ret[plat].dep, tem = [], commonFiles = [], files = [];
|
140 |
|
141 | dep = dep.filter(function(el){
|
142 | return !/React\w+\.js$/.test(el.name);
|
143 | });
|
144 |
|
145 | dep.forEach(function(el){
|
146 |
|
147 | if (Identifiers[el.name] == 1) {
|
148 | commonFiles.push(el);
|
149 | }
|
150 |
|
151 | if (/React\w+\.js$/.test(el.name)) {
|
152 | if (!tem.length) {
|
153 | tem.push(el);
|
154 | }
|
155 | } else {
|
156 | files.push(el);
|
157 | }
|
158 | })
|
159 |
|
160 |
|
161 | files = files.concat(tem);
|
162 |
|
163 |
|
164 | let tableItem = [];
|
165 | let allSize = (getSize(files)/1000).toFixed(2);
|
166 | let commonPercent = (getSize(commonFiles)/1000).toFixed(2) / allSize;
|
167 | commonPercent = commonPercent.toFixed(2) * 100;
|
168 |
|
169 | tableItem.push(
|
170 | plat,
|
171 | Math.round( ( getSize(files)/1000).toFixed(2) ) + ' Kb',
|
172 | commonPercent + ' %'
|
173 | );
|
174 |
|
175 | output.push(tableItem);
|
176 | }
|
177 |
|
178 | var data = [
|
179 | ['业务平台', 'size', '公共资源占比']
|
180 | ].concat(output)
|
181 |
|
182 |
|
183 |
|
184 |
|
185 |
|
186 |
|
187 |
|
188 |
|
189 |
|
190 |
|
191 |
|
192 |
|
193 |
|
194 |
|
195 |
|
196 | console.log(table(data));
|
197 |
|
198 | })
|
199 | }
|
200 | }
|
201 |
|
202 |
|
203 | module.exports = SizePlugin; |
\ | No newline at end of file |