如何在Golang中使用”archive/zip”包压缩符号链接?

huangapple go评论73阅读模式
英文:

How to zip symlinks in Golang using "archive/zip" package?

问题

我需要压缩/解压包含符号链接的文件夹,以便保留结构并将符号链接写入为符号链接。

是否可以使用Golang包"archive/zip"来实现这一点?或者还有其他替代方法吗?

我尝试使用了这段代码,但是'io.Copy()'会复制目标文件的内容,导致我们"丢失"了符号链接。

archive, err := os.Create("archive.zip")
if err != nil {
    panic(err)
}
defer archive.Close()
zipWriter := zip.NewWriter(archive)
localPath := "../testdata/sym"
file, err := os.Open(localPath)
defer file.Close()
if err != nil {
    panic(err)
}
w1, err := zipWriter.Create("w1")
if _, err = io.Copy(w1, file); err != nil {
    panic(err)
}
zipWriter.Close()
英文:

I need to zip/unzip folder that contains symlinks in a way that the structure will be saved and symlinks will be written as symlinks.

Is there a way doing this using Golang package "archive/zip"? or any other alternative way?

I tried to use this code, but 'io.Copy()' copies the target file content and we "lose" the symlink.

archive, err := os.Create("archive.zip")
if err != nil {
	panic(err)
}
defer archive.Close()
zipWriter := zip.NewWriter(archive)
localPath := "../testdata/sym"
file, err := os.Open(localPath)
defer file.Close()
if err != nil {
	panic(err)
}
w1 , err:= zipWriter.Create("w1")
if _, err = io.Copy(w1, file); err !=nil{
	panic(err)
}
zipWriter.Close()

答案1

得分: 1

我使用了这个PR:https://github.com/mholt/archiver/pull/92,并将符号链接的目标写入了writer。

我在Linux和Windows上进行了测试。

archive, err := os.Create("archive.zip")
if err != nil {
    panic(err)
}
defer archive.Close()
zipWriter := zip.NewWriter(archive)
defer zipWriter.Close()
localPath := "../testdata/sym"
symlinksTarget := "../a/b.in"
file, err := os.Open(localPath)
defer file.Close()
if err != nil {
    panic(err)
}
info, err := os.Lstat(file.Name())
if err != nil {
    panic(err)
}
header, err := zip.FileInfoHeader(info)
if err != nil {
    panic(err)
}
header.Method = zip.Deflate
writer, err := zipWriter.CreateHeader(header)
if err != nil {
    panic(err)
}

// 将符号链接的目标写入writer - 对于符号链接,文件的内容就是符号链接的目标。
_, err = writer.Write([]byte(filepath.ToSlash(symlinksTarget)))
if err != nil {
    panic(err)
}

以上是代码的翻译部分。

英文:

I used this PR : https://github.com/mholt/archiver/pull/92
and wrote symlink's target to writer.

I tested it on Linux and Windows.

archive, err := os.Create("archive.zip")
if err != nil {
    panic(err)
}
defer archive.Close()
zipWriter := zip.NewWriter(archive)
defer zipWriter.Close()
localPath := "../testdata/sym"
symlinksTarget = "../a/b.in"
file, err := os.Open(localPath)
defer file.Close()
if err != nil {
    panic(err)
}
info, err := os.Lstat(file.Name())
if err != nil {
	panic(err)
}
header, err := zip.FileInfoHeader(info)
if err != nil {
	panic(err)
}
header.Method = zip.Deflate
writer, err := zipWriter.CreateHeader(header)
if err != nil {
	panic(err)
}

// Write symlink's target to writer - file's body for symlinks is the symlink target.
_, err = writer.Write([]byte(filepath.ToSlash(symlinksTarget)))
if err != nil {
	panic(err)
}

huangapple
  • 本文由 发表于 2021年7月26日 17:25:10
  • 转载请务必保留本文链接:https://go.coder-hub.com/68527458.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定