Search code examples
node.jselectronimagemin

Imagemin in Electron App Not Compressing Images


I'm trying to compress a single PNG image in an Electron application using this code

  const files = await imagemin([filePath], {
    destination: destinationPath,
    plugins: [
      imageminPngquant({
        quality: [0.2, 0.4],
        speed: 1
      })
    ]
  });
  debuglog(files);

filePath contains a full path to a PNG file, e.g.

C:\Users\name\Downloads\images\needle.png

This file does exist, and the path is correct: when I put the same path into Windows explorer, the png opens.

destinationPath contains a path to the same directory in which the .png file resides (in other words, I want to overwrite the original file), e.g.

C:\Users\name\Downloads\images

When I run this, the original file remains unchanged, and the variable "files" returned by the function call contains an empty array.

What am I doing wrong? Is there a way to get debug output that tells me what exactly imagemin is doing?

Update: here's a concrete example. The code looks like this:

  console.log("compressPNG");
  console.log(filePath);
  console.log(path);
  var files = await imagemin([filePath], {
    destination: path,
    plugins: [
      imageminPngquant({
        quality: [0.2, 0.4],
        speed: 1
      })
    ]
  });
  console.log(files);

This produces the following log output:

Log output from running the image compression code


Solution

  • This bug report indicates that you need to convert backward slashes (\) to forward slashes (/).

    According to one of the commenters, the package globby that imagemin relies on expects filepaths with forward slashes (/) as the delimiter.

    Here is a complete example:

    const imagemin = require("imagemin");
    const imageminPngquant = require("imagemin-pngquant");
    
    let input_path = "C:\\path\\to\\file.png";
    let output_dir = "C:\\output\\directory";
    
    // Replace backward slashes with forward slashes      <-- Option A
    input_path = input_path.replace(/\\/g, "/");
    output_dir = output_dir.replace(/\\/g, "/");
    
    (async () => {
      var files = await imagemin([input_path], {
        destination: output_dir,
        // glob: false,                                   <-- Option B
        plugins: [
          imageminPngquant({
            quality: [0.2, 0.4],
            speed: 1
          })
        ]
      });
      console.log(files);
    })();
    

    Alternatively, setting glob: false should also help accept Windows filepaths, as it circumvents use of the globby module.