How to unzip (decompress) zip files in Cordova

How to unzip (decompress) zip files in Cordova

Nowadays mobile devices are capable of almost everything. Zip files allows the user to manipulate a lot of files, while he manipulates only one. Being able to decompress files after they're downloaded from source can be achieved in Cordova too. The approach of this article won't use JavaScript to decompress files as the task may become tedious by doing it with the client language, so we'll recommend you to use native code for it. But don't worry, you will be still programming with JavaScript thanks to a plugin that handles the native code for you !

1. Install the cordova-plugin-zip

In order to extract the content from a zip file into some directory of your device, we recommend you to use the cordova-plugin-zip plugin. This plugins uses in Android the java.util.zip and SSZipArchive in iOS.

Install the plugin executing the following cordova command:

cordova plugin add cordova-plugin-zip

This plugin works for Android and iOS. If you want more information about this plugin, please visit the official repository at Github here.

2. Using the plugin

The plugin exposes a single method on its global variable namely zip.unzip. This method expects up to 4 arguments in the following order:

  • ZipPath: the absolute path to the zip file that will be decompressed.
  • ZipExtractDirectory: the absolute path to the folder where the files should be extracted.
  • StatusCallback: function that receives as unique argument a number that notice wheter the file was succesfully decompressed or not (0 if success and -1 if failed).
  • ProgressCallback: function executed everytime the progress of the decompression changes. Receives as first argument an object with information about the progress.

Remember to wrap before all your code after the deviceready event of the window, otherwise the plugin won't work:

document.addEventListener('deviceready', function(){
    // All your code here ...
}, false);

Once you are sure that the code will be executed, you can proceed to provide the arguments for the unzip function of the library:

// Path to the file
var ZipPath = "file:///storage/emulated/0/some-zipfile.zip";
// Path of the destination folder
var ZipExtractDirectory = "/storage/emulated/0/";

// Handle the result of the process
var StatusCallback = function(status){
    if(status == 0){
        // Everything OK
    }else if(status == -1){
        // Everything is wrong ...
    }
};

// Handle the progress of the decompression
var ProgressCallback = function(progressEvent){
    var percent =  Math.round((progressEvent.loaded / progressEvent.total) * 100);

    // Display progress in the console : 8% ...
    console.log(percent + "%");
};

// Unzip it !
window.zip.unzip(ZipPath, ZipExtractDirectory, StatusCallback, ProgressCallback);

Note that both source and destination arguments can be URLs obtained from the HTML File interface or absolute paths to files on the device, that means that they can either contain file:// or without it.

Example

Using the FileBrowser plugin for Android Cordova, we are going to select a zip file and we'll extract its content in the root folder of the Android storage:

document.addEventListener('deviceready', onDeviceReady, false);
            
function onDeviceReady(){
    // When the user clicks some button to select the file
    document.getElementById("btn").addEventListener("click", () => {
        // Open the single file selector
        window.OurCodeWorld.Filebrowser.filePicker.single({
            success: function(data){
                if(!data.length){
                    // No file selected
                    return;
                }
                
                // data = Array with filepath
                // ["file:///storage/emulated/0/file.zip"]
                // Extract in the root folder of the storage
                processZip(data[0], "/storage/emulated/0");
            },
            error: function(err){
                console.log(err);
            }
        });
    }, false);
}

/**
 * 
 * @param zipSource Path to the zip file
 * @param destination Path where the content should be placed
 */
function processZip(zipSource, destination){
    // Handle the progress event
    var progressHandler = function(progressEvent){
        var percent =  Math.round((progressEvent.loaded / progressEvent.total) * 100);

        // Display progress in the console : 8% ...
        console.log(percent + "%");
    };

    // Proceed to unzip the file
    window.zip.unzip(zipSource, destination, (status) => {
        if(status == 0){
            console.log("Files succesfully decompressed");
        }

        if(status == -1){
            console.error("Oops, cannot decompress files");
        }
    }, progressHandler);
}

Happy coding !

Become a more social person