diff --git a/command/file.go b/command/file.go index 6b22172..f1a2445 100644 --- a/command/file.go +++ b/command/file.go @@ -2,12 +2,28 @@ package command import ( "errors" + "fmt" "os" + "os/exec" "strings" "github.com/bitrise-io/go-utils/pathutil" ) +func runCommand(name string, args ...string) error { + cmd := exec.Command(name, args...) + if out, err := cmd.CombinedOutput(); err != nil { + printableCmd := PrintableCommandArgs(false, append([]string{name}, args...)) + + var exitErr *exec.ExitError + if errors.As(err, &exitErr) { + return fmt.Errorf("command failed with exit status %d (%s): %w", exitErr.ExitCode(), printableCmd, errors.New(string(out))) + } + return fmt.Errorf("executing command failed (%s): %w", printableCmd, err) + } + return nil +} + // CopyFile ... func CopyFile(src, dst string) error { // replace with a pure Go implementation? @@ -17,10 +33,10 @@ func CopyFile(src, dst string) error { return err } if isDir { - return errors.New("Source is a directory: " + src) + return errors.New("source is a directory: " + src) } args := []string{src, dst} - return RunCommand("rsync", args...) + return runCommand("rsync", args...) } // CopyDir ... @@ -29,7 +45,7 @@ func CopyDir(src, dst string, isOnlyContent bool) error { src = src + "/" } args := []string{"-ar", src, dst} - return RunCommand("rsync", args...) + return runCommand("rsync", args...) } // RemoveDir ... diff --git a/command/file_test.go b/command/file_test.go index 7647f87..152e59e 100644 --- a/command/file_test.go +++ b/command/file_test.go @@ -12,6 +12,6 @@ func TestCopyFileErrorIfDirectory(t *testing.T) { { tmpFolder, err := pathutil.NormalizedOSTempDirPath("_tmp") require.NoError(t, err) - require.EqualError(t, CopyFile(tmpFolder, "./nothing/whatever"), "Source is a directory: "+tmpFolder) + require.EqualError(t, CopyFile(tmpFolder, "./nothing/whatever"), "source is a directory: "+tmpFolder) } }