From 47b2aabd9f52d2ced3c130ec2d9086d8861235a1 Mon Sep 17 00:00:00 2001 From: Andrew Woodlee Date: Wed, 9 Jul 2025 23:20:11 -0500 Subject: [PATCH] Improved error message for remote version package output --- docs/content/config/hosts.md | 2 +- docs/content/getting-started/config.md | 4 ++-- pkg/backy/utils.go | 9 +++++---- pkg/pkgman/apt/apt.go | 28 +++++++++++++++++--------- pkg/pkgman/dnf/dnf.go | 6 +++--- pkg/pkgman/pkgman.go | 2 +- pkg/pkgman/yum/yum.go | 6 +++--- tests/packageCommands.yml | 13 +++++++++++- 8 files changed, 45 insertions(+), 25 deletions(-) diff --git a/docs/content/config/hosts.md b/docs/content/config/hosts.md index 30a32dd..59c0398 100644 --- a/docs/content/config/hosts.md +++ b/docs/content/config/hosts.md @@ -21,4 +21,4 @@ description: > ## exec host subcommand -Backy has a subcommand `exec host`. This subcommand takes the flags of `-m host1 -m host2`. For now these hosts need to be defined in the config file. +Backy has a subcommand `exec host`. This subcommand takes the flags of `-m host1 -m host2`. The commands can also be specified by `-c command1 -c command2`. diff --git a/docs/content/getting-started/config.md b/docs/content/getting-started/config.md index 61ef7aa..88f9d3d 100644 --- a/docs/content/getting-started/config.md +++ b/docs/content/getting-started/config.md @@ -124,9 +124,9 @@ notifications: ### Logging -cmd-std-out controls whether commands output is echoed to StdOut. +`cmd-std-out` controls whether commands output is echoed to StdOut. -If logfile is not defined, the log file will be written to the config directory in the file `backy.log`. +If `logfile` is not defined, the log file will be written to the config directory in the file `backy.log`. `console-disabled` controls whether the logging messages are echoed to StdOut. Default is false. diff --git a/pkg/backy/utils.go b/pkg/backy/utils.go index d03476a..ea24994 100644 --- a/pkg/backy/utils.go +++ b/pkg/backy/utils.go @@ -333,11 +333,12 @@ func getCommandTypeAndSetCommandInfo(command *Command) *Command { func parsePackageVersion(output string, cmdCtxLogger zerolog.Logger, command *Command, cmdOutBuf bytes.Buffer) ([]string, error) { + var err error var errs []error - pkgVersionOnSystem, errs := command.pkgMan.ParseRemotePackageManagerVersionOutput(output) - if errs != nil { - cmdCtxLogger.Error().Errs("Error parsing package version output", errs).Send() - return collectOutput(&cmdOutBuf, command.Name, cmdCtxLogger, command.Output.ToLog), fmt.Errorf("error parsing package version output: %v", errs) + pkgVersionOnSystem, err := command.pkgMan.ParseRemotePackageManagerVersionOutput(output) + if err != nil { + cmdCtxLogger.Error().AnErr("Error parsing package version output", err).Send() + return collectOutput(&cmdOutBuf, command.Name, cmdCtxLogger, command.Output.ToLog), fmt.Errorf("error parsing package version output: %v", err) } for _, p := range pkgVersionOnSystem { diff --git a/pkg/pkgman/apt/apt.go b/pkg/pkgman/apt/apt.go index 9c74bb7..480af39 100644 --- a/pkg/pkgman/apt/apt.go +++ b/pkg/pkgman/apt/apt.go @@ -109,7 +109,7 @@ func (a *AptManager) SetAuthCommand(authCommand string) { } // Parse parses the apt-cache policy output to extract Installed and Candidate versions. -func (a *AptManager) ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, []error) { +func (a *AptManager) ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, error) { var ( packageName string installedString string @@ -118,11 +118,12 @@ func (a *AptManager) ParseRemotePackageManagerVersionOutput(output string) ([]pa ) // Check for error message in the output if strings.Contains(output, "Unable to locate package") { - return nil, []error{fmt.Errorf("error: %s", strings.TrimSpace(output))} + return nil, fmt.Errorf("error: %s", strings.TrimSpace(output)) } packages := []packagemanagercommon.Package{} outputBuf := bytes.NewBufferString(output) outputScan := bufio.NewScanner(outputBuf) + var packageCount uint for outputScan.Scan() { line := outputScan.Text() if !strings.HasPrefix(line, " ") && strings.HasSuffix(line, ":") { @@ -141,17 +142,24 @@ func (a *AptManager) ParseRemotePackageManagerVersionOutput(output string) ([]pa if countRelevantLines == 2 { countRelevantLines = 0 - packages = append(packages, packagemanagercommon.Package{ - Name: packageName, - VersionCheck: packagemanagercommon.PackageVersion{ - Installed: strings.TrimSpace(installedString), - Candidate: strings.TrimSpace(candidateString), - Match: installedString == candidateString, - }}, - ) + if !strings.Contains(installedString, " (none)") { + packageCount++ + packages = append(packages, packagemanagercommon.Package{ + Name: packageName, + VersionCheck: packagemanagercommon.PackageVersion{ + Installed: strings.TrimSpace(installedString), + Candidate: strings.TrimSpace(candidateString), + Match: installedString == candidateString, + }}, + ) + } } } + if packageCount == 0 { + return nil, fmt.Errorf("no packages found") + } + return packages, nil } diff --git a/pkg/pkgman/dnf/dnf.go b/pkg/pkgman/dnf/dnf.go index edc8f2e..0925dbe 100644 --- a/pkg/pkgman/dnf/dnf.go +++ b/pkg/pkgman/dnf/dnf.go @@ -92,11 +92,11 @@ func (d *DnfManager) CheckVersion(pkgs []packagemanagercommon.Package) (string, } // Parse parses the dnf info output to extract Installed and Candidate versions. -func (d DnfManager) ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, []error) { +func (d DnfManager) ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, error) { // Check for error message in the output if strings.Contains(output, "No matching packages to list") { - return nil, []error{fmt.Errorf("error: package not listed")} + return nil, fmt.Errorf("error: package not listed") } // Define regular expressions to capture installed and available versions @@ -118,7 +118,7 @@ func (d DnfManager) ParseRemotePackageManagerVersionOutput(output string) ([]pac } if installedVersion == "" && candidateVersion == "" { - return nil, []error{fmt.Errorf("failed to parse versions from dnf output")} + return nil, fmt.Errorf("failed to parse versions from dnf output") } return nil, nil diff --git a/pkg/pkgman/pkgman.go b/pkg/pkgman/pkgman.go index 82ac87a..201bc33 100644 --- a/pkg/pkgman/pkgman.go +++ b/pkg/pkgman/pkgman.go @@ -16,7 +16,7 @@ type PackageManager interface { Upgrade(pkgs []packagemanagercommon.Package) (string, []string) // Upgrade a specific package UpgradeAll() (string, []string) CheckVersion(pkgs []packagemanagercommon.Package) (string, []string) - ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, []error) + ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, error) // Configure applies functional options to customize the package manager. Configure(options ...packagemanagercommon.PackageManagerOption) } diff --git a/pkg/pkgman/yum/yum.go b/pkg/pkgman/yum/yum.go index bb3b5a9..9a445c4 100644 --- a/pkg/pkgman/yum/yum.go +++ b/pkg/pkgman/yum/yum.go @@ -90,11 +90,11 @@ func (y *YumManager) CheckVersion(pkgs []packagemanagercommon.Package) (string, } // Parse parses the dnf info output to extract Installed and Candidate versions. -func (y YumManager) ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, []error) { +func (y YumManager) ParseRemotePackageManagerVersionOutput(output string) ([]packagemanagercommon.Package, error) { // Check for error message in the output if strings.Contains(output, "No matching packages to list") { - return nil, []error{fmt.Errorf("error: package not listed")} + return nil, fmt.Errorf("error: package not listed") } // Define regular expressions to capture installed and available versions @@ -116,7 +116,7 @@ func (y YumManager) ParseRemotePackageManagerVersionOutput(output string) ([]pac } if installedVersion == "" && candidateVersion == "" { - return nil, []error{fmt.Errorf("failed to parse versions from dnf output")} + return nil, fmt.Errorf("failed to parse versions from dnf output") } return nil, nil diff --git a/tests/packageCommands.yml b/tests/packageCommands.yml index 840c01b..f5f3193 100644 --- a/tests/packageCommands.yml +++ b/tests/packageCommands.yml @@ -8,6 +8,14 @@ commands: packageManager: apt packageOperation: checkVersion + checkAptNoVersion: + type: package + shell: zsh + packages: + - name: "apt" + packageManager: apt + packageOperation: checkVersion + checkDockerPartialVersionWithoutRegex: type: package shell: zsh @@ -50,4 +58,7 @@ cmdLists: - checkDockerPartialVersionWithoutRegex - checkDockerPartialVersionWithRegex - checkDockerVersionWithInvalidRegex - - checkDockerNoVersion \ No newline at end of file + - checkDockerNoVersion + +logging: + verbose: true \ No newline at end of file