Remove hash.bin functionality from TGZWriter

This commit is contained in:
Brian Picciano 2022-10-16 17:06:50 +02:00
parent 77cb74f316
commit 3b19552173

View File

@ -4,40 +4,21 @@ import (
"archive/tar" "archive/tar"
"bytes" "bytes"
"compress/gzip" "compress/gzip"
"crypto/sha512"
"fmt" "fmt"
"io" "io"
"io/fs"
"path/filepath" "path/filepath"
"sort"
"strings" "strings"
) )
const (
// Path to the file containing the content hash of the tgz, which is
// included as part of all tgz files created by TGZWriter.
HashBinPath = "hash.bin"
)
type fileHash struct {
path string
hash []byte
}
// TGZWriter is a utility for writing tgz files. If an internal error is // TGZWriter is a utility for writing tgz files. If an internal error is
// encountered by any method then all subsequent methods will be no-ops, and // encountered by any method then all subsequent methods will be no-ops, and
// Close() will return that error (after closing out resources). // Close() will return that error (after closing out resources).
//
// A `hash.bin` file will be automatically included in the resulting tgz, which
// will contain a consistent hash of all other contents in the tgz file.
type TGZWriter struct { type TGZWriter struct {
gzipW *gzip.Writer gzipW *gzip.Writer
tarW *tar.Writer tarW *tar.Writer
err error err error
dirsWritten map[string]bool dirsWritten map[string]bool
fileHashes []fileHash
} }
// NewTGZWriter initializes and returns a new instance of TGZWriter which will // NewTGZWriter initializes and returns a new instance of TGZWriter which will
@ -55,22 +36,8 @@ func NewTGZWriter(w io.Writer) *TGZWriter {
// Close cleans up all open resources being held by TGZWriter, and returns the // Close cleans up all open resources being held by TGZWriter, and returns the
// first internal error which was encountered during its operation (if any). // first internal error which was encountered during its operation (if any).
func (w *TGZWriter) Close() error { func (w *TGZWriter) Close() error {
sort.Slice(w.fileHashes, func(i, j int) bool {
return w.fileHashes[i].path < w.fileHashes[j].path
})
h := sha512.New()
for i := range w.fileHashes {
fmt.Fprintf(h, "%q:%x\n", w.fileHashes[i].path, w.fileHashes[i].hash)
}
w.WriteFile(HashBinPath, int64(h.Size()), bytes.NewBuffer(h.Sum(nil)))
w.tarW.Close() w.tarW.Close()
w.gzipW.Close() w.gzipW.Close()
return w.err return w.err
} }
@ -131,17 +98,10 @@ func (w *TGZWriter) WriteFile(path string, size int64, body io.Reader) {
return return
} }
h := sha512.New() if _, err := io.Copy(w.tarW, body); err != nil {
if _, err := io.Copy(io.MultiWriter(w.tarW, h), body); err != nil {
w.err = fmt.Errorf("writing file body of file %q: %w", path, err) w.err = fmt.Errorf("writing file body of file %q: %w", path, err)
return return
} }
w.fileHashes = append(w.fileHashes, fileHash{
path: path,
hash: h.Sum(nil),
})
} }
// WriteFileBytes is a shortcut for calling WriteFile with the given byte slice // WriteFileBytes is a shortcut for calling WriteFile with the given byte slice
@ -150,22 +110,3 @@ func (w *TGZWriter) WriteFileBytes(path string, body []byte) {
bodyR := bytes.NewReader(body) bodyR := bytes.NewReader(body)
w.WriteFile(path, bodyR.Size(), bodyR) w.WriteFile(path, bodyR.Size(), bodyR)
} }
// CopyFileFromFS copies the file at the given path from srcFS into the same
// path in the TGZWriter.
func (w *TGZWriter) CopyFileFromFS(path string, srcFS fs.FS) error {
f, err := srcFS.Open(path)
if err != nil {
return fmt.Errorf("opening: %w", err)
}
defer f.Close()
fStat, err := f.Stat()
if err != nil {
return fmt.Errorf("stating: %w", err)
}
w.WriteFile(path, fStat.Size(), f)
return nil
}