1

I have a small function designed to unzip a file using 'unzipper' and extract to a given location.

when unit testing the function times out, for unit testing I am using jest.

see below code :

    exports.unzipFile = async (folderPath) => {
    return new Promise((resolve, reject) => {
    fs.createReadStream(folderPath)
      .pipe(unzipper.Extract({ path: tmpPath+ path.parse(folderPath).name })).on('close', () => resolve()).on('error', (error) => reject(error))
    })

The function itself works as expected. I have tried some changes to the function but this seems to break the function. I need this function to execute fully as the unzipped file is then relied on later in the program.

The program is written in node 16. Any help would be appreciated thanks

EDIT: this is my current unit test- I have tried various things :

const { PassThrough } = require('stream')
const os = require('os');
const unzipper = require("unzipper")
const fs = require("fs")

let tmpdir, mockReadStream
    
beforeEach(() => {

tmpdir = os.tmpdir() + "/uploadFolder/";
 if (!fs.existsSync(tmpdir)){
     fs.mkdirSync(tmpdir);
 }
 fs.writeFileSync(tmpdir+"tempfile.zip", "file to be used")

mockReadStream = new PassThrough()
})
afterEach(() => {
  // Restore mocks
  jest.clearAllMocks()

})

describe('Test helper.js unzip method', () => {
  test('should be able to unzip file  ', async () => {


         jest.isolateModules(() => {
             helper = require('helper')
         })

     const result = await helper.unzipFile(tmpdir+"tempfile.zip")
    console.log(result)
  })
})
Arnoldddd
  • 13
  • 5
  • So, if the function works as expected, what exactly is the problem you want help with? Can you show an example of code that doesn't work as expected? – jfriend00 Oct 07 '22 at 19:39
  • @jfriend00 hi I am trying to unit test it with Jest and that is the issue. the unit test just times out – Arnoldddd Oct 07 '22 at 19:44
  • Please show the unit test code then. We can't help you solve problems with code we can't see. I would guess that you're not coding the unit test appropriately for the asynchronous operation that it is, but without seeing it we have no idea. – jfriend00 Oct 07 '22 at 19:46
  • Note, you are also not handling ANY errors with your unzip operation so that's a separate problem. You could get errors with `fs.createReadStream()` or with the extraction. – jfriend00 Oct 07 '22 at 19:48
  • @jfriend00 hi please see updated post. I am trying to use a file that I create for the test but I have also tried using an actual zip file from my local directory but same issue – Arnoldddd Oct 07 '22 at 20:12
  • So, where's your `expect()` Jest code that tests your result? And, where's your call to `done()` to tell Jest you completed the asynchronous test? You're probably timing out because the `test()` code never calls the done callback. I've never written a line of Jest code, but I can see in the doc where it says: ***"If done() is never called, the test will fail (with timeout error)"*** – jfriend00 Oct 07 '22 at 21:33

1 Answers1

0

you need to make some minor changes in order to test it

in helper.js

  1. change the signature of the unzipFile function to unzipFile = async (zipFilePath, outputDir)
const unzipper = require("unzipper")
const fs = require("fs")

const unzipFile = async (zipFilePath, outputDir) => {
    return new Promise((resolve, reject) => {
        fs
            .createReadStream(zipFilePath)
            .pipe(unzipper.Extract({ path: outputDir }))
            .on('close', () => resolve())
            .on('error', (error) => reject(error))
    })
}

module.exports = { unzipFile }

then you need to create a simple zip file and add it locally at your test dir

in my example i created a simple zip file 1.txt.zip that contains text file with the string hello

then your test should look like this

const path = require("path");
const shelljs = require("shelljs");
const helper = require("./helper")
const fs = require("fs")
const testFilesDir = path.join(__dirname, "test");
const outPutDir = path.join(__dirname, "output")

console.log(testFilesDir)
beforeAll((done) => {
  shelljs.mkdir("-p", testFilesDir);
  shelljs.mkdir("-p", outPutDir);
  shelljs.cp("-r", path.join(__dirname, "*.zip"), testFilesDir);
  done();
});

afterAll((done) => {
  shelljs.rm("-rf", testFilesDir);
  done();
});


describe('Test helper.js unzip method', () => {
  test('should be able to unzip file  ', async () => {
    await helper.unzipFile(path.join(testFilesDir, "1.txt.zip"), outPutDir)
    const files = fs.readdirSync(outPutDir)
    expect(files.length).toEqual(1);
    expect(files[0]).toEqual("1.txt");
    const text = fs.readFileSync(path.join(outPutDir,"1.txt"),"utf8")
    expect(text).toEqual("hello");
  })
})

enter image description here

Naor Tedgi
  • 5,204
  • 3
  • 21
  • 48