Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I zip a directory containing sub directories or files in Golang?

Tags:

zip

go

I know it will have to do with the zip package I just have no idea how I would implement such a thing.

like image 985
anonrose Avatar asked Jun 16 '16 21:06

anonrose


People also ask

Can you zip a folder with subfolders?

On the General tab in Properties, click the button Advanced. In the next window, tick the check box Compress contents to save disk space under the Compress or Encrypt attributes section. There, you need to choose "Apply changes to this folder only" or "Apply changes to this folder, subfolders and files".

How do I zip a folder in Golang?

To zip a file or a directory in Go using the standard library, use zip. Writer type from the archive/zip package. Creating a compressed archive using this method involves going through all the files you want to include, generating a local file header for each one, and writing its contents to the resulting ZIP file.

Can zip files contain both files and directories?

ZIP is an archive file format that supports lossless data compression. A ZIP file may contain one or more files or directories that may have been compressed. The ZIP file format permits a number of compression algorithms, though DEFLATE is the most common.


1 Answers

To do it manually, you could modify the code linked above:

ExampleZipWriter

To give you a simple example, that has many flaws, but might be easily understood:

func ZipWriter() {
    baseFolder := "/Users/tom/Desktop/testing/"

    // Get a Buffer to Write To
    outFile, err := os.Create(`/Users/tom/Desktop/zip.zip`)
    if err != nil {
        fmt.Println(err)
    }
    defer outFile.Close()

    // Create a new zip archive.
    w := zip.NewWriter(outFile)

    // Add some files to the archive.
    addFiles(w, baseFolder, "")

    if err != nil {
        fmt.Println(err)
    }

    // Make sure to check the error on Close.
    err = w.Close()
    if err != nil {
        fmt.Println(err)
    }
}

We use this to iterate on files recursively to generate folders too:

func addFiles(w *zip.Writer, basePath, baseInZip string) {
    // Open the Directory
    files, err := ioutil.ReadDir(basePath)
    if err != nil {
        fmt.Println(err)
    }

    for _, file := range files {
        fmt.Println(basePath + file.Name())
        if !file.IsDir() {
            dat, err := ioutil.ReadFile(basePath + file.Name())
            if err != nil {
                fmt.Println(err)
            }

            // Add some files to the archive.
            f, err := w.Create(baseInZip + file.Name())
            if err != nil {
                fmt.Println(err)
            }
            _, err = f.Write(dat)
            if err != nil {
                fmt.Println(err)
            }
        } else if file.IsDir() {

            // Recurse
            newBase := basePath + file.Name() + "/"
            fmt.Println("Recursing and Adding SubDir: " + file.Name())
            fmt.Println("Recursing and Adding SubDir: " + newBase)

            addFiles(w, newBase, baseInZip  + file.Name() + "/")
        }
    }
}
like image 135
LeTigre Avatar answered Oct 01 '22 21:10

LeTigre