You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

87 lines
2.0 KiB

4 years ago
  1. /*
  2. MIT License http://www.opensource.org/licenses/mit-license.php
  3. Author Tobias Koppers @sokra
  4. */
  5. "use strict";
  6. class AggressiveMergingPlugin {
  7. constructor(options) {
  8. if (
  9. (options !== undefined && typeof options !== "object") ||
  10. Array.isArray(options)
  11. ) {
  12. throw new Error(
  13. "Argument should be an options object. To use defaults, pass in nothing.\nFor more info on options, see https://webpack.js.org/plugins/"
  14. );
  15. }
  16. this.options = options || {};
  17. }
  18. apply(compiler) {
  19. const options = this.options;
  20. const minSizeReduce = options.minSizeReduce || 1.5;
  21. compiler.hooks.thisCompilation.tap(
  22. "AggressiveMergingPlugin",
  23. compilation => {
  24. compilation.hooks.optimizeChunksAdvanced.tap(
  25. "AggressiveMergingPlugin",
  26. chunks => {
  27. let combinations = [];
  28. chunks.forEach((a, idx) => {
  29. if (a.canBeInitial()) return;
  30. for (let i = 0; i < idx; i++) {
  31. const b = chunks[i];
  32. if (b.canBeInitial()) continue;
  33. combinations.push({
  34. a,
  35. b,
  36. improvement: undefined
  37. });
  38. }
  39. });
  40. for (const pair of combinations) {
  41. const a = pair.b.size({
  42. chunkOverhead: 0
  43. });
  44. const b = pair.a.size({
  45. chunkOverhead: 0
  46. });
  47. const ab = pair.b.integratedSize(pair.a, {
  48. chunkOverhead: 0
  49. });
  50. let newSize;
  51. if (ab === false) {
  52. pair.improvement = false;
  53. return;
  54. } else {
  55. newSize = ab;
  56. }
  57. pair.improvement = (a + b) / newSize;
  58. }
  59. combinations = combinations.filter(pair => {
  60. return pair.improvement !== false;
  61. });
  62. combinations.sort((a, b) => {
  63. return b.improvement - a.improvement;
  64. });
  65. const pair = combinations[0];
  66. if (!pair) return;
  67. if (pair.improvement < minSizeReduce) return;
  68. if (pair.b.integrate(pair.a, "aggressive-merge")) {
  69. chunks.splice(chunks.indexOf(pair.a), 1);
  70. return true;
  71. }
  72. }
  73. );
  74. }
  75. );
  76. }
  77. }
  78. module.exports = AggressiveMergingPlugin;