Пакет archive/zip
Пакет archive/zip предоставляет функции для работы с ZIP-архивами.
С его помощью можно создавать новые архивы, добавлять в них файлы,
а также читать и извлекать содержимое существующих архивов.
Основными типами пакета являются Writer для создания архивов
и Reader для чтения архивов.
Создание ZIP-архива
Для создания ZIP-архива используется тип Writer.
Функция zip.NewWriter создает новый экземпляр
для записи в файл или в любой другой поток.
Синтаксис
func NewWriter(w io.Writer) *zip.Writer
Функция NewWriter принимает интерфейс io.Writer
и возвращает указатель на zip.Writer.
Пример
Создадим ZIP-архив и добавим в него два файла:
package main
import (
"archive/zip"
"bytes"
"fmt"
)
func main() {
buf := new(bytes.Buffer)
zipWriter := zip.NewWriter(buf)
file1, err := zipWriter.Create("file1.txt")
if err != nil {
fmt.Println(err)
return
}
_, err = file1.Write([]byte("Content of file 1"))
if err != nil {
fmt.Println(err)
return
}
file2, err := zipWriter.Create("file2.txt")
if err != nil {
fmt.Println(err)
return
}
_, err = file2.Write([]byte("Content of file 2"))
if err != nil {
fmt.Println(err)
return
}
err = zipWriter.Close()
if err != nil {
fmt.Println(err)
return
}
fmt.Printf("Archive size: %d bytes", buf.Len())
}
Результат выполнения кода:
"Archive size: 232 bytes"
Метод Create создает новый файл в архиве и возвращает
интерфейс io.Writer для записи его содержимого.
После добавления всех файлов необходимо вызвать метод Close,
чтобы завершить запись архива.
Чтение ZIP-архива
Для чтения ZIP-архива используется функция zip.OpenReader,
которая открывает архив из файла, или функция zip.NewReader,
которая читает архив из байтового потока.
Синтаксис
func OpenReader(name string) (*zip.ReadCloser, error)
func NewReader(r io.ReaderAt, size int64) (*zip.Reader, error)
Функция OpenReader принимает имя файла и возвращает
указатель на zip.ReadCloser, который нужно закрыть
после использования. Функция NewReader принимает
интерфейс io.ReaderAt и размер архива.
Пример
Прочитаем архив из байтового буфера и выведем список файлов:
package main
import (
"archive/zip"
"bytes"
"fmt"
"io"
)
func main() {
buf := new(bytes.Buffer)
zipWriter := zip.NewWriter(buf)
file, _ := zipWriter.Create("file1.txt")
file.Write([]byte("Content"))
zipWriter.Close()
zipReader, err := zip.NewReader(bytes.NewReader(buf.Bytes()), int64(buf.Len()))
if err != nil {
fmt.Println(err)
return
}
for _, file := range zipReader.File {
fmt.Println(file.Name)
}
}
Результат выполнения кода:
"file1.txt"
Извлечение файлов из архива
Для извлечения файла из архива необходимо открыть его
с помощью метода Open и прочитать содержимое.
Синтаксис
func (f *File) Open() (io.ReadCloser, error)
Метод Open возвращает интерфейс io.ReadCloser
для чтения содержимого файла.
Пример
Извлечем файл из архива и выведем его содержимое:
package main
import (
"archive/zip"
"bytes"
"fmt"
"io"
)
func main() {
buf := new(bytes.Buffer)
zipWriter := zip.NewWriter(buf)
file, _ := zipWriter.Create("data.txt")
file.Write([]byte("Hello, World!"))
zipWriter.Close()
zipReader, _ := zip.NewReader(bytes.NewReader(buf.Bytes()), int64(buf.Len()))
for _, f := range zipReader.File {
reader, err := f.Open()
if err != nil {
fmt.Println(err)
continue
}
defer reader.Close()
content, err := io.ReadAll(reader)
if err != nil {
fmt.Println(err)
continue
}
fmt.Printf("%s: %s", f.Name, string(content))
}
}
Результат выполнения кода:
"data.txt: Hello, World!"
Добавление файлов с настройками
Для более тонкой настройки добавляемых файлов используется
метод CreateHeader, который позволяет задать
метаданные файла, такие как время модификации и права доступа.
Синтаксис
func (w *Writer) CreateHeader(fh *FileHeader) (io.Writer, error)
Метод CreateHeader принимает указатель на структуру
FileHeader и возвращает интерфейс для записи содержимого.
Пример
Добавим файл с пользовательскими метаданными:
package main
import (
"archive/zip"
"bytes"
"fmt"
"time"
)
func main() {
buf := new(bytes.Buffer)
zipWriter := zip.NewWriter(buf)
header := &zip.FileHeader{
Name: "config.json",
Method: zip.Deflate,
Modified: time.Now(),
}
writer, err := zipWriter.CreateHeader(header)
if err != nil {
fmt.Println(err)
return
}
_, err = writer.Write([]byte(`{"key": "value"}`))
if err != nil {
fmt.Println(err)
return
}
zipWriter.Close()
fmt.Printf("Archive created, size: %d bytes", buf.Len())
}
Результат выполнения кода:
"Archive created, size: 113 bytes"
Смотрите также
-
тип
zip.Writer,
который используется для создания ZIP-архивов -
тип
zip.Reader,
который используется для чтения ZIP-архивов -
тип
zip.File,
который представляет отдельный файл в архиве -
функцию
zip.OpenReader,
которая открывает ZIP-архив из файла