compression-webpack-plugin

repository·main·Indexed 23 days ago

https://github.com/webpack/compression-webpack-plugin

A Webpack plugin that prepares compressed versions of assets (such as gzip, Brotli, or Zstandard) to be served with Content-Encoding to reduce bandwidth usage. It supports asset filtering via test, include, and exclude options, configurable compression thresholds, and the ability to delete original assets after compression.

Tokens
3.8K
Snippets
13
Records
16
Agent score
31%

What's inside compression-webpack-plugin

  1. Customize the output filename

    main

    The filename option determines the target asset filename. It defaults to "[path][base].gz".

    String placeholders

    • [path]: Directories of the original asset, including trailing / (e.g., assets/images/).
    • [file]: Full path of the original asset (e.g., assets/images/image.png).
    • [base]: Base name ([name] + [ext]) (e.g., image.png).
    • [name]: Name of the original asset (e.g., image).
    • [ext]: Extension including the . (e.g., .png).
    • [query]: Query string including ? (e.g., ?foo=bar).
    • [fragment]: URL fragment/hash including # (e.g., #hash).

    Function

    You can provide a function that receives pathData (containing the placeholders above) and returns the target filename.

    // Using string placeholders
    module.exports = {
      plugins: [
        new CompressionPlugin({
          filename: "[path][base].gz",
        }),
      ],
    };
    
    // Using a function
    module.exports = {
      plugins: [
        new CompressionPlugin({
          filename(pathData) {
            if (实质上.test(pathData.filename)) {
              return "assets/svg/[path][base].gz";
            }
            return "assets/js/[path][base].gz";
          },
        }),
      ],
    };
  2. Filter assets with test, include, and exclude

    main

    You can control which assets are processed using test, include, and exclude options. All three accept a string, RegExp, or an array of either.

    • test: Include all assets that pass the test assertion.
    • include: Include all assets matching any of these conditions.
    • exclude: Exclude all assets matching any of these conditions.
    // Example using test
    module.exports = {
      plugins: [
        new CompressionPlugin({
          test: /\.js(\?.*)?$/i,
        }),
      ],
    };
    
    // Example using include
    module.exports = {
      plugins: [
        new CompressionPlugin({
          include: /\/includes/,
        }),
      ],
    };
    
    // Example using exclude
    module.exports = {
      plugins: [
        new CompressionPlugin({
          exclude: /\/excludes/,
        }),
      ],
    };
  3. Delete original assets after compression

    main

    The deleteOriginalAssets option determines if uncompressed assets should be removed. It defaults to false.

    Options:

    • true: All original assets are deleted.
    • "keep-source-map": All original assets are deleted except .map files.
    • (name: string) => boolean: A function that returns true to delete the asset or false to keep it.
    // Delete everything
    module.exports = {
      plugins: [
        new CompressionPlugin({
          deleteOriginalAssets: true,
        }),
      ],
    };
    
    // Keep source maps
    module.exports = {
      plugins: [
        new CompressionPlugin({
          exclude: /.map$/, 
          deleteOriginalAssets: "keep-source-map",
        }),
      ],
    };
    
    // Custom logic: Delete all except images
    module.exports = {
      plugins: [
        new CompressionPlugin({
          deleteOriginalAssets: (assetName) =>
            !assetName.endsWith(".png") && !assetName.endsWith(".jpg"),
        }),
      ],
    };
  4. Configure compressionOptions

    main

    The compressionOptions object provides settings for the compression algorithm. It defaults to { level: 9 } when using a string-based algorithm. If a custom function is used for algorithm, this defaults to {}.

    Available keys include:

    • flush (number)
    • finishFlush (number)
    • chunkSize (number)
    • windowBits (number)
    • level (number)
    • memLevel (number)
    • strategy (number)
    • dictionary (Buffer | TypedArray | DataView | ArrayBuffer)
    • info (boolean)
    • maxOutputLength (number)

    Refer to the zlib documentation for full details.

    module.exports = {
      plugins: [
        new CompressionPlugin({
          compressionOptions: { level: 1 },
        }),
      ],
    };
  5. Set asset size and compression ratio thresholds

    main

    Use threshold and minRatio to prevent compressing small files or files that don't benefit from compression.

    • threshold: Only assets larger than this size (in bytes) are processed. Defaults to 0.
    • minRatio: Only assets that compress better than this ratio are processed (minRatio = Compressed Size / Original Size). Defaults to 0.8.

    Special minRatio values:

    • 1: Process assets only if they are smaller than or equal to the original size.
    • Infinity: Process all assets, even if they are larger than the original size or 0 bytes (useful for pre-zipping for AWS).
    • Number.MAX_SAFE_INTEGER: Process all assets except those with 0 bytes size.
    module.exports = {
      plugins: [
        new CompressionPlugin({
          threshold: 8192,
          minRatio: 0.8,
        }),
      ],
    };
  6. Configure the compression algorithm

    main

    The algorithm option defines the compression method. It defaults to gzip.

    String value

    Pass a string representing a Node.js zlib algorithm (e.g., 'gzip').

    Function value

    You can provide a custom function for compression. The function signature is: algorithm(input, compressionOptions, callback).

    Note: If you use a custom function, the default compressionOptions will be an empty object {}.

    // Using a string algorithm
    module.exports = {
      plugins: [
        new CompressionPlugin({
          algorithm: "gzip",
        }),
      ],
    };
    
    // Using a custom function
    module.exports = {
      plugins: [
        new CompressionPlugin({
          algorithm(input, compressionOptions, callback) {
            return compressionFunction(input, compressionOptions, callback);
          },
        }),
      ],
    };
  7. Use CompressionPlugin in webpack configuration

    main

    To compress your webpack assets, import and add the CompressionPlugin to your webpack.config.js plugins array. By default, it uses gzip compression and generates .gz files.

    const CompressionPlugin = require('compression-webpack-plugin');
    
    module.exports = {
      // ... other webpack config
      plugins: [
        new CompressionPlugin()
      ],
    };
  8. Generate multiple compressed versions of assets

    main

    To support multiple compression formats (e.g., both Gzip and Brotli), instantiate the CompressionPlugin multiple times in your plugins array, each with a different algorithm, filename extension, and test regex.

    const zlib = require("node:zlib");
    
    module.exports = {
      plugins: [
        new CompressionPlugin({
          filename: "[path][base].gz",
          algorithm: "gzip",
          test: /\.js$|\.css$|\.html$/,
          threshold: 10240,
          minRatio: 0.8,
        }),
        new CompressionPlugin({
          filename: "[path][base].br",
          algorithm: "brotliCompress",
          test: /\.(js|css|html|svg)$/,
          compressionOptions: {
            params: {
              [zlib.constants.BROTLI_PARAM_QUALITY]: 11,
            },
          },
          threshold: 10240,
          minRatio: 0.8,
        }),
      ],
    };
  9. Use Zopfli compression

    main

    To use the Zopfli compression algorithm, you must install the @gfx/zopfli library. Note that @gfx/zopfli requires Node.js version 8 or higher. You can implement it by providing a custom algorithm function to the CompressionPlugin that calls zopfli.gzip.

    $ npm install @gfx/zopfli --save-dev
  10. Use Zopfli in webpack.config.js

    main

    Implement Zopfli by importing @gfx/zopfli and passing a custom algorithm function to the CompressionPlugin instance.

    const zopfli = require("@gfx/zopfli");
    
    module.exports = {
      plugins: [
        new CompressionPlugin({
          compressionOptions: {
            numiterations: 15,
          },
          algorithm(input, compressionOptions, callback) {
            return zopfli.gzip(input, compressionOptions, callback);
          },
        }),
      ],
    };