in commands/helpers/archive/tarzstd/tarzstd_archiver.go [46:127]
func (a *archiver) Archive(ctx context.Context, files map[string]os.FileInfo) error {
sorted := make([]string, 0, len(files))
for filename := range files {
sorted = append(sorted, filename)
}
sort.Strings(sorted)
zw, err := zstd.NewWriter(a.w, zstd.WithEncoderLevel(zstd.EncoderLevel(levels[a.level])))
if err != nil {
return err
}
defer zw.Close()
tw := tar.NewWriter(zw)
defer tw.Close()
for _, name := range sorted {
fi := files[name]
if fi.Mode()&irregularModes != 0 {
continue
}
path, err := filepath.Abs(name)
if err != nil {
return err
}
if !strings.HasPrefix(path, a.dir+string(filepath.Separator)) && path != a.dir {
return fmt.Errorf("%s cannot be archived from outside of chroot (%s)", name, a.dir)
}
rel, err := filepath.Rel(a.dir, path)
if err != nil {
return err
}
if ctx.Err() != nil {
return ctx.Err()
}
var link string
if fi.Mode()&os.ModeSymlink != 0 {
link, err = os.Readlink(path)
if err != nil {
return err
}
}
hdr, err := tar.FileInfoHeader(fi, link)
if err != nil {
return err
}
hdr.Name = rel
if fi.IsDir() {
hdr.Name += "/"
}
if err := tw.WriteHeader(hdr); err != nil {
return err
}
if !fi.Mode().IsRegular() {
continue
}
f, err := os.Open(path)
if err != nil {
return err
}
if _, err = io.Copy(tw, f); err != nil {
f.Close()
return err
}
f.Close()
}
if err := tw.Close(); err != nil {
return err
}
return zw.Close()
}