-
-
Notifications
You must be signed in to change notification settings - Fork 14
Expand file tree
/
Copy pathfiles.go
More file actions
113 lines (94 loc) · 2.29 KB
/
Copy pathfiles.go
File metadata and controls
113 lines (94 loc) · 2.29 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
package main
import (
"archive/tar"
"compress/gzip"
"io"
"os"
"path/filepath"
log "github.com/sirupsen/logrus"
)
// closeWithLog closes an io.Closer and logs any error with the given context
func closeWithLog(c io.Closer, context string) {
if err := c.Close(); err != nil {
log.WithField("context", context).WithError(err).Warn("Error closing resource")
}
}
// decompressGzip decompresses a gzip file to a destination path
func decompressGzip(src, dst string) error {
srcFile, err := os.Open(src)
if err != nil {
return err
}
defer closeWithLog(srcFile, "source file")
gzReader, err := gzip.NewReader(srcFile)
if err != nil {
_, err := srcFile.Seek(0, 0)
if err != nil {
return err
}
dstFile, err := os.Create(dst)
if err != nil {
return err
}
defer closeWithLog(dstFile, "destination file")
_, err = io.Copy(dstFile, srcFile)
return err
}
defer closeWithLog(gzReader, "gzip reader")
dstFile, err := os.Create(dst)
if err != nil {
return err
}
defer closeWithLog(dstFile, "destination file")
_, err = io.Copy(dstFile, gzReader)
return err
}
// createTar creates a gzip-compressed tar archive from a source directory
func createTar(srcDir, destPath string) error {
file, err := os.Create(destPath)
if err != nil {
return err
}
defer closeWithLog(file, "tar.gz file")
gzWriter, err := gzip.NewWriterLevel(file, gzip.BestCompression)
if err != nil {
return err
}
defer closeWithLog(gzWriter, "gzip writer")
tw := tar.NewWriter(gzWriter)
defer closeWithLog(tw, "tar writer")
return filepath.Walk(srcDir, func(path string, info os.FileInfo, err error) error {
if err != nil {
return err
}
relPath, err := filepath.Rel(srcDir, path)
if err != nil {
return err
}
if relPath == "." {
return nil
}
header, err := tar.FileInfoHeader(info, "")
if err != nil {
return err
}
header.Name = relPath
if err := tw.WriteHeader(header); err != nil {
return err
}
if info.IsDir() {
return nil
}
return copyFileToTar(tw, path)
})
}
// copyFileToTar copies a single file to a tar writer, ensuring the file is closed immediately after copying
func copyFileToTar(tw *tar.Writer, path string) error {
f, err := os.Open(path)
if err != nil {
return err
}
defer closeWithLog(f, "file")
_, err = io.Copy(tw, f)
return err
}