go.mondoo.com/cnquery@v0.0.0-20231005093811-59568235f6ea/providers/os/resources/packages/rpm_updates.go (about) 1 // Copyright (c) Mondoo, Inc. 2 // SPDX-License-Identifier: BUSL-1.1 3 4 package packages 5 6 import ( 7 "bufio" 8 "encoding/json" 9 "encoding/xml" 10 "io" 11 ) 12 13 func ParseRpmUpdates(input io.Reader) (map[string]PackageUpdate, error) { 14 pkgs := map[string]PackageUpdate{} 15 scanner := bufio.NewScanner(input) 16 for scanner.Scan() { 17 line := scanner.Bytes() 18 19 // we try to parse the content into the struct 20 var pkg PackageUpdate 21 err := json.Unmarshal(line, &pkg) 22 if err != nil { 23 // there are string lines that cannot be parsed 24 continue 25 } 26 pkgs[pkg.Name] = pkg 27 } 28 return pkgs, nil 29 } 30 31 type zypperUpdate struct { 32 Name string `xml:"name,attr"` 33 Kind string `xml:"kind,attr"` 34 Arch string `xml:"arch,attr"` 35 Edition string `xml:"edition,attr"` 36 OldEdition string `xml:"edition-old,attr"` 37 Status string `xml:"status,attr"` 38 Category string `xml:"category,attr"` 39 Severity string `xml:"severity,attr"` 40 PkgManager string `xml:"pkgmanager,attr"` 41 Restart string `xml:"restart,attr"` 42 Interactive string `xml:"interactive,attr"` 43 44 Summary string `xml:"summary"` 45 Description string `xml:"description"` 46 } 47 48 type zypper struct { 49 XMLNode xml.Name `xml:"stream"` 50 Updates []zypperUpdate `xml:"update-status>update-list>update"` 51 Blocked []zypperUpdate `xml:"update-status>blocked-update-list>update"` 52 } 53 54 // for Suse, updates are package updates 55 // parses the output of `zypper -n --xmlout list-updates` 56 func ParseZypperUpdates(input io.Reader) (map[string]PackageUpdate, error) { 57 pkgs := map[string]PackageUpdate{} 58 zypper, err := ParseZypper(input) 59 if err != nil { 60 return nil, err 61 } 62 63 for _, u := range zypper.Updates { 64 // filter for kind package 65 if u.Kind != "package" { 66 continue 67 } 68 pkgs[u.Name] = PackageUpdate{ 69 Name: u.Name, 70 Version: u.OldEdition, 71 Arch: u.Arch, 72 Available: u.Edition, 73 } 74 } 75 return pkgs, nil 76 } 77 78 func ParseZypper(input io.Reader) (*zypper, error) { 79 content, err := io.ReadAll(input) 80 if err != nil { 81 return nil, err 82 } 83 var patches zypper 84 err = xml.Unmarshal(content, &patches) 85 if err != nil { 86 return nil, err 87 } 88 return &patches, nil 89 }