patchman/client/zypper/packageList.go

120 lines
3.0 KiB
Go

//go:build linux
package zypper
import (
"git.jmbit.de/jmb/patchman/client/common"
"git.jmbit.de/jmb/patchman/client/utils"
"log"
"os/exec"
"strings"
"sync"
)
// GetInstalledList Because Zypper sadly can't give both the upgradeable and installed packages at the same time,
// concurrently get both a list of all installed packages and all upgradeable and merge them
func GetInstalledList() []common.ListPackage {
var allPackages []common.ListPackage
var upgradeablePackages []common.ListPackage
var wg sync.WaitGroup
wg.Add(2)
go func() {
defer wg.Done()
allPackages = getAllPackagesList()
log.Println("Got Zypper Package list")
}()
go func() {
defer wg.Done()
upgradeablePackages = getUpgradeableList()
log.Println("Got Zypper upgradable Package list")
}()
wg.Wait()
return utils.DedupAndMergePackageList(allPackages, upgradeablePackages)
}
func getAllPackagesList() []common.ListPackage {
var packageList []common.ListPackage
// List of all upgradeable packages
cmd := exec.Command("/usr/bin/zypper", "se", "-si")
out, err := cmd.Output()
if err != nil {
log.Printf("Could not get zypper packages %w", err)
}
// Convert Output into text and split it into newlines
lines := strings.Split(string(out[:]), "\n")
// Parse lines
//TODO parallelize this
for i, line := range lines {
if i < 6 {
continue
}
sections := strings.Split(line, "|")
if len(sections) != 6 {
log.Print(line)
continue
}
name := strings.TrimSpace(sections[1])
source := strings.TrimSpace(sections[5])
version := strings.TrimSpace(sections[3])
architecture := strings.TrimSpace(sections[4])
listPackage := common.ListPackage{
Name: name,
Source: source,
Version: version,
Architecture: architecture,
PackageManager: "zypper",
}
packageList = append(packageList, listPackage)
}
return packageList
}
func getUpgradeableList() []common.ListPackage {
var packageList []common.ListPackage
// List of all upgradeable packages
cmd := exec.Command("/usr/bin/zypper", "list-updates", "--all")
out, err := cmd.Output()
if err != nil {
log.Printf("Could not get zypper packages %w", err)
}
// Convert Output into text and split it into newlines
lines := strings.Split(string(out[:]), "\n")
// Parse lines
//TODO parallelize this
for i, line := range lines {
if i < 6 {
continue
}
sections := strings.Split(line, "|")
if len(sections) != 6 {
log.Print(line)
continue
}
name := strings.TrimSpace(sections[2])
source := strings.TrimSpace(sections[1])
version := strings.TrimSpace(sections[3])
upgradeableTo := strings.TrimSpace(sections[4])
architecture := strings.TrimSpace(sections[5])
listPackage := common.ListPackage{
Name: name,
Source: source,
Version: version,
Architecture: architecture,
Upgradeable: true,
UpgradeableTo: upgradeableTo,
PackageManager: "zypper",
}
packageList = append(packageList, listPackage)
}
return packageList
}