Error messages in mfer/ and internal/cli/ are lowercase except names and acronyms, carry no "failed to" or command-name prefix, and each wrap names only the operation and thing the wrapped error does not already name, so a stacked message names what failed once. Wraps around errors that already name their operation and path (os and afero path errors, url.Error, the builder's path errors, the gpg helpers' own errors) are dropped. gpg's stderr is appended to a gpg failure, and to the error for a signing key gpg did not report, only when gpg wrote some. errHTTPStatus reads "unexpected HTTP status"; both inner-not-set sentinels read "inner message not set". No sentinel, errors.Is result or exit status changes. Model: opus-5-5
This commit is contained in:
+15
-28
@@ -165,8 +165,7 @@ func (s *freshenScanner) walk(path string, info fs.FileInfo, walkErr error) erro
|
||||
// Get relative path
|
||||
relPath, err := filepath.Rel(s.absBase, path)
|
||||
if err != nil {
|
||||
return fmt.Errorf(
|
||||
"freshen: failed to compute relative path for %s: %w", path, err)
|
||||
return err
|
||||
}
|
||||
|
||||
// Handle dotfiles
|
||||
@@ -280,13 +279,8 @@ func (h *freshenHasher) reportProgress(n int64) {
|
||||
// processEntry hashes the entry if needed and adds it to the builder.
|
||||
func (h *freshenHasher) processEntry(e *freshenEntry) error {
|
||||
if !e.needsHash {
|
||||
// Use existing entry
|
||||
err := addExistingToBuilder(h.builder, e.existing)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to add %s: %w", e.path, err)
|
||||
}
|
||||
|
||||
return nil
|
||||
// Use existing entry; the error names the entry
|
||||
return addExistingToBuilder(h.builder, e.existing)
|
||||
}
|
||||
|
||||
// Need to read and hash the file
|
||||
@@ -294,26 +288,21 @@ func (h *freshenHasher) processEntry(e *freshenEntry) error {
|
||||
|
||||
f, err := h.fs.Open(absPath)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to open %s: %w", e.path, err)
|
||||
return err
|
||||
}
|
||||
|
||||
hash, bytesRead, err := hashFile(f, h.reportProgress)
|
||||
_ = f.Close()
|
||||
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to hash %s: %w", e.path, err)
|
||||
return err
|
||||
}
|
||||
|
||||
h.hashedBytes += bytesRead
|
||||
h.hashedFiles++
|
||||
|
||||
// Add to builder with computed hash
|
||||
err = addFileToBuilder(h.builder, e.path, e.size, e.mtime, e.mode, hash)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to add %s: %w", e.path, err)
|
||||
}
|
||||
|
||||
return nil
|
||||
// Add to builder with computed hash; a refused path is named in the error
|
||||
return addFileToBuilder(h.builder, e.path, e.size, e.mtime, e.mode, hash)
|
||||
}
|
||||
|
||||
// writeFreshenedManifest writes the manifest atomically (write to a
|
||||
@@ -325,7 +314,7 @@ func writeFreshenedManifest(
|
||||
|
||||
outFile, err := afs.Create(tmpPath)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to create temp file: %w", err)
|
||||
return err
|
||||
}
|
||||
|
||||
err = builder.Build(ctx, outFile)
|
||||
@@ -334,7 +323,7 @@ func writeFreshenedManifest(
|
||||
if err != nil {
|
||||
_ = afs.Remove(tmpPath)
|
||||
|
||||
return fmt.Errorf("failed to write manifest: %w", err)
|
||||
return fmt.Errorf("build manifest: %w", err)
|
||||
}
|
||||
|
||||
// Rename temp to final
|
||||
@@ -342,7 +331,7 @@ func writeFreshenedManifest(
|
||||
if err != nil {
|
||||
_ = afs.Remove(tmpPath)
|
||||
|
||||
return fmt.Errorf("failed to rename manifest: %w", err)
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
@@ -408,7 +397,7 @@ func (mfa *CLIApp) freshenScan(
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return nil, 0, fmt.Errorf("failed to scan filesystem: %w", err)
|
||||
return nil, 0, fmt.Errorf("scan filesystem: %w", err)
|
||||
}
|
||||
|
||||
// Remaining entries in existingByPath are removed files
|
||||
@@ -477,7 +466,7 @@ func (mfa *CLIApp) loadExistingEntries(
|
||||
Fs: mfa.Fs,
|
||||
})
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to load manifest: %w", err)
|
||||
return nil, fmt.Errorf("load manifest: %w", err)
|
||||
}
|
||||
|
||||
existingFiles := manifest.Files()
|
||||
@@ -503,7 +492,7 @@ func (mfa *CLIApp) freshenManifestOperation(
|
||||
// Find manifest file
|
||||
manifestPath, err := mfa.resolveFreshenManifestPath(cmd)
|
||||
if err != nil {
|
||||
return fmt.Errorf("freshen: %w", err)
|
||||
return err
|
||||
}
|
||||
|
||||
//nolint:contextcheck // mfer loads a manifest without a context
|
||||
@@ -514,7 +503,7 @@ func (mfa *CLIApp) freshenManifestOperation(
|
||||
|
||||
absBase, err := filepath.Abs(basePath)
|
||||
if err != nil {
|
||||
return fmt.Errorf("freshen: invalid base path: %w", err)
|
||||
return fmt.Errorf("invalid base path: %w", err)
|
||||
}
|
||||
|
||||
// Phase 1: Scan filesystem
|
||||
@@ -606,9 +595,7 @@ func hashFile(r io.Reader, progress func(int64)) ([]byte, int64, error) {
|
||||
break
|
||||
}
|
||||
|
||||
// Returned unwrapped: the caller renders this as
|
||||
// "failed to hash <path>: <err>" and adding a second layer here
|
||||
// would change that message.
|
||||
// Returned unwrapped: a read error already names the file.
|
||||
if err != nil {
|
||||
return nil, total, err
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user