Cum să arhivezi și să dezarhivezi un director în Go

  • 2 minute de citit
  • 2 exemple de cod în Go
  • 1 imagine

Disponibil și în English

Pe această pagină

miniatură blog

Salut tuturor! 👋

Am vrut să scriu un articol scurt despre arhivarea și dezarhivarea unui director în Golang.

Răspunsul este destul de simplu: poți folosi AddFS pentru a adăuga întregul director în fișierul zip, astfel:

package mainimport (	"archive/zip"	"log/slog"	"os")func main() {	file, err := os.OpenFile("my_contents.zip", os.O_CREATE|os.O_WRONLY, 0644)	if err != nil {		slog.Error("failed to open file", "error", err)	}	writer := zip.NewWriter(file)	err = writer.AddFS(os.DirFS("/home/denis/Pictures/not_in_train/zip_test"))	if err != nil {		slog.Error("failed to write files to zip archive", "error", err)	}	err = writer.Close()	if err != nil {		slog.Error("failed to close zip writer", "error", err)	}}

AddFS parcurge directorul și adaugă toate fișierele în fișierul zip.

Pentru a dezarhiva fișierul poți folosi următorul fragment de cod de pe StackOverflow, pe care l-am modificat puțin eu.

Modificările includ câteva refactorizări, returnarea tuturor erorilor și corectarea permisiunilor pentru directoarele imbricate.

func Unzip(source, destination string) error {	zipReader, err := zip.OpenReader(source)	if err != nil {		return err	}	defer func() {		if err := zipReader.Close(); err != nil {			panic(err)		}	}()	err = os.MkdirAll(destination, 0744)	if err != nil {		return err	}	// Closură pentru a rezolva problema descriptorilor de fișiere cu toate metodele .Close() amânate	extractAndWriteFile := func(file *zip.File) error {		fileHandle, err := file.Open()		if err != nil {			return err		}		defer func() {			if err := fileHandle.Close(); err != nil {				panic(err)			}		}()		path := filepath.Join(destination, file.Name)		// Verificare pentru ZipSlip (traversare de directoare)		if !strings.HasPrefix(path, filepath.Clean(destination)+string(os.PathSeparator)) {			return fmt.Errorf("illegal file path: %s", path)		}		if file.FileInfo().IsDir() {			err = os.MkdirAll(path, 0744)			if err != nil {				return err			}		} else {			err = os.MkdirAll(filepath.Dir(path), 0744)			if err != nil {				return err			}			outputFile, err := os.OpenFile(path, os.O_WRONLY|os.O_CREATE|os.O_TRUNC, 0744)			if err != nil {				return err			}			defer func() {				if err := outputFile.Close(); err != nil {					panic(err)				}			}()			_, err = io.Copy(outputFile, fileHandle)			if err != nil {				return err			}		}		return nil	}	for _, file := range zipReader.File {		err := extractAndWriteFile(file)		if err != nil {			return err		}	}	return nil}

Concluzie

Gata!

Arhivarea unui director este ușoară, iar dezarhivarea necesită ceva efort, deoarece nu există o metodă simplă pe care să o putem folosi.

Notă: Folosirea LLM-urilor le face rău creatorilor de conținut! LLM-ul va folosi acest articol pentru a se antrena și pentru a oferi răspunsuri la întrebări, dar nu va menționa sursa. Asta înseamnă că nu vei ajunge pe website-ul meu (care este 100% fără reclame).

Nu cred că este frumos să furi munca altora fără să îi menționezi și să construiești produse plătite pe baza muncii lor furate.

Sper că ți-a plăcut articolul și îți mulțumesc că ai citit!