Android - Unzip a folder? Android - Unzip a folder? android android

Android - Unzip a folder?


I am using a modified version of Beginner's method that extends AsyncTask and can update Observers on the main thread. Byte by byte compression is extremely slow and should be avoided. Instead a more efficient approach is to copy large chunks of data to the output stream.

package com.blarg.webviewscroller;import java.io.BufferedInputStream;import java.io.BufferedOutputStream;import java.io.File;import java.io.FileOutputStream;import java.io.IOException;import java.util.Enumeration;import java.util.Observable;import java.util.zip.ZipEntry;import java.util.zip.ZipFile;import org.apache.commons.io.IOUtils;import android.os.AsyncTask;import android.util.Log;public class UnZipper extends Observable {    private static final String TAG = "UnZip";    private String mFileName, mFilePath, mDestinationPath;    public UnZipper (String fileName, String filePath, String destinationPath) {        mFileName = fileName;        mFilePath = filePath;        mDestinationPath = destinationPath;    }    public String getFileName () {        return mFileName;    }    public String getFilePath() {        return mFilePath;    }    public String getDestinationPath () {        return mDestinationPath;    }    public void unzip () {        String fullPath = mFilePath + "/" + mFileName + ".zip";        Log.d(TAG, "unzipping " + mFileName + " to " + mDestinationPath);        new UnZipTask().execute(fullPath, mDestinationPath);    }    private class UnZipTask extends AsyncTask<String, Void, Boolean> {        @SuppressWarnings("rawtypes")        @Override        protected Boolean doInBackground(String... params) {            String filePath = params[0];            String destinationPath = params[1];            File archive = new File(filePath);            try {                ZipFile zipfile = new ZipFile(archive);                for (Enumeration e = zipfile.entries(); e.hasMoreElements();) {                    ZipEntry entry = (ZipEntry) e.nextElement();                    unzipEntry(zipfile, entry, destinationPath);                }            } catch (Exception e) {                Log.e(TAG, "Error while extracting file " + archive, e);                return false;            }            return true;        }        @Override        protected void onPostExecute(Boolean result) {            setChanged();            notifyObservers();        }        private void unzipEntry(ZipFile zipfile, ZipEntry entry,                String outputDir) throws IOException {            if (entry.isDirectory()) {                createDir(new File(outputDir, entry.getName()));                return;            }            File outputFile = new File(outputDir, entry.getName());            if (!outputFile.getParentFile().exists()) {                createDir(outputFile.getParentFile());            }            Log.v(TAG, "Extracting: " + entry);            BufferedInputStream inputStream = new BufferedInputStream(zipfile.getInputStream(entry));            BufferedOutputStream outputStream = new BufferedOutputStream(new FileOutputStream(outputFile));            try {                IOUtils.copy(inputStream, outputStream);            } finally {                outputStream.close();                inputStream.close();            }        }        private void createDir(File dir) {            if (dir.exists()) {                return;            }            Log.v(TAG, "Creating dir " + dir.getName());            if (!dir.mkdirs()) {                throw new RuntimeException("Can not create dir " + dir);            }        }    }} 

It is used by a class that implements Observer, such as:

private void unzipWebFile(String filename) {    String unzipLocation = getExternalFilesDir(null) + "/unzipped";    String filePath = Environment.getExternalStorageDirectory().toString();    UnZipper unzipper = new UnZipper(filename, filePath, unzipLocation);    unzipper.addObserver(this);    unzipper.unzip();}

Your observer will get an update(Observable observable, Object data) callback when the unzip finishes.


static Handler myHandler;ProgressDialog myProgress;public void unzipFile(File zipfile) {        myProgress = ProgressDialog.show(getContext(), "Extract Zip",                        "Extracting Files...", true, false);        File zipFile = zipfile;        String directory = null;        directory = zipFile.getParent();        directory = directory + "/";        myHandler = new Handler() {                @Override                public void handleMessage(Message msg) {                        // process incoming messages here                        switch (msg.what) {                        case 0:                                // update progress bar                                myProgress.setMessage("" + (String) msg.obj);                                break;                        case 1:                                myProgress.cancel();                                Toast toast = Toast.makeText(getContext(),                                                "Zip extracted successfully", Toast.LENGTH_SHORT);                                toast.show();                                provider.refresh();                                break;                        case 2:                                myProgress.cancel();                                break;                        }                        super.handleMessage(msg);                }        };        Thread workthread = new Thread(new UnZip(zipFile, directory));        workthread.start();}public class UnZip implements Runnable {        File archive;        String outputDir;        public UnZip(File ziparchive, String directory) {                archive = ziparchive;                outputDir = directory;        }        public void log(String log) {                Log.v("unzip", log);        }        @SuppressWarnings("unchecked")        public void run() {                Message msg;                try {                        ZipFile zipfile = new ZipFile(archive);                        for (Enumeration e = zipfile.entries(); e.hasMoreElements();) {                                ZipEntry entry = (ZipEntry) e.nextElement();                                msg = new Message();                                msg.what = 0;                                msg.obj = "Extracting " + entry.getName();                                myHandler.sendMessage(msg);                                unzipEntry(zipfile, entry, outputDir);                        }                } catch (Exception e) {                        log("Error while extracting file " + archive);                }                msg = new Message();                msg.what = 1;                myHandler.sendMessage(msg);        }        @SuppressWarnings("unchecked")        public void unzipArchive(File archive, String outputDir) {                try {                        ZipFile zipfile = new ZipFile(archive);                        for (Enumeration e = zipfile.entries(); e.hasMoreElements();) {                                ZipEntry entry = (ZipEntry) e.nextElement();                                unzipEntry(zipfile, entry, outputDir);                        }                } catch (Exception e) {                        log("Error while extracting file " + archive);                }        }        private void unzipEntry(ZipFile zipfile, ZipEntry entry,                        String outputDir) throws IOException {                if (entry.isDirectory()) {                        createDir(new File(outputDir, entry.getName()));                        return;                }                File outputFile = new File(outputDir, entry.getName());                if (!outputFile.getParentFile().exists()) {                        createDir(outputFile.getParentFile());                }                log("Extracting: " + entry);                BufferedInputStream inputStream = new BufferedInputStream(zipfile                                .getInputStream(entry));                BufferedOutputStream outputStream = new BufferedOutputStream(                                new FileOutputStream(outputFile));                try {                        IOUtils.copy(inputStream, outputStream);                } finally {                        outputStream.close();                        inputStream.close();                }        }        private void createDir(File dir) {                log("Creating dir " + dir.getName());                if (!dir.mkdirs())                        throw new RuntimeException("Can not create dir " + dir);        }}

This is what worked for me thanks people


just "addon" for @rich.e answer:

in doInBackground() after iterating through ZipEtries you should close the file, because sometimes you want do delete the file after unzipping it and it throws an exception if file was not closed:

try {        ZipFile zipfile = new ZipFile(archive);        int entries = zipfile.size();        int total = 0;        if(onZipListener != null)            onZipListener.onUncompressStart(archive);        for (Enumeration<?> e = zipfile.entries(); e.hasMoreElements();) {            ZipEntry entry = (ZipEntry) e.nextElement();            if(onZipListener != null)                onZipListener.onUncompressProgress(archive, (int) (total++ * 100 / entries));            unzipEntry(zipfile, entry, path);        }        zipfile.close();    } catch (Exception e) {        e.printStackTrace();    }