Skip to content
This repository was archived by the owner on Mar 27, 2024. It is now read-only.

Commit c1e1988

Browse files
committed
Add aptlayer analyzer
This commit implements layer analysis for single version package analyzer for images based on apt package manager
1 parent 1f50d17 commit c1e1988

File tree

3 files changed

+64
-2
lines changed

3 files changed

+64
-2
lines changed

cmd/root.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -268,7 +268,7 @@ func getExtractPathForName(name string) (string, error) {
268268

269269
func includeLayers() bool {
270270
for _, t := range types {
271-
if t == "layer" {
271+
if strings.Contains(t, "layer") {
272272
return true
273273
}
274274
}

differs/apt_diff.go

Lines changed: 62 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,9 @@ import (
2828
"github.com/sirupsen/logrus"
2929
)
3030

31+
//APT package database location
32+
const dpkgStatusFile string = "var/lib/dpkg/status"
33+
3134
type AptAnalyzer struct {
3235
}
3336

@@ -53,7 +56,7 @@ func (a AptAnalyzer) getPackages(image pkgutil.Image) (map[string]util.PackageIn
5356
// invalid image directory path
5457
return packages, err
5558
}
56-
statusFile := filepath.Join(path, "var/lib/dpkg/status")
59+
statusFile := filepath.Join(path, dpkgStatusFile)
5760
if _, err := os.Stat(statusFile); err != nil {
5861
// status file does not exist in this layer
5962
return packages, nil
@@ -120,3 +123,61 @@ func parseLine(text string, currPackage string, packages map[string]util.Package
120123
}
121124
return currPackage
122125
}
126+
127+
type AptLayerAnalyzer struct {
128+
}
129+
130+
func (a AptLayerAnalyzer) Name() string {
131+
return "AptLayerAnalyzer"
132+
}
133+
134+
// AptDiff compares the packages installed by apt-get.
135+
func (a AptLayerAnalyzer) Diff(image1, image2 pkgutil.Image) (util.Result, error) {
136+
diff, err := singleVersionLayerDiff(image1, image2, a)
137+
return diff, err
138+
}
139+
140+
func (a AptLayerAnalyzer) Analyze(image pkgutil.Image) (util.Result, error) {
141+
analysis, err := singleVersionLayerAnalysis(image, a)
142+
return analysis, err
143+
}
144+
145+
func (a AptLayerAnalyzer) getPackages(image pkgutil.Image) ([]map[string]util.PackageInfo, error) {
146+
var packages []map[string]util.PackageInfo
147+
if _, err := os.Stat(image.FSPath); err != nil {
148+
// invalid image directory path
149+
return packages, err
150+
}
151+
statusFile := filepath.Join(image.FSPath, dpkgStatusFile)
152+
if _, err := os.Stat(statusFile); err != nil {
153+
// status file does not exist in this image
154+
return packages, nil
155+
}
156+
for _, layer := range image.Layers {
157+
layerPackages := make(map[string]util.PackageInfo)
158+
if _, err := os.Stat(layer.FSPath); err != nil {
159+
// invalid layer directory path
160+
return packages, err
161+
}
162+
statusFile := filepath.Join(layer.FSPath, dpkgStatusFile)
163+
if _, err := os.Stat(statusFile); err == nil {
164+
// this layer has a package database
165+
if file, err := os.Open(statusFile); err == nil {
166+
// make sure it gets closed
167+
defer file.Close()
168+
169+
// create a new scanner and read the file line by line
170+
scanner := bufio.NewScanner(file)
171+
var currPackage string
172+
for scanner.Scan() {
173+
currPackage = parseLine(scanner.Text(), currPackage, layerPackages)
174+
}
175+
} else {
176+
return packages, err
177+
}
178+
}
179+
packages = append(packages, layerPackages)
180+
}
181+
182+
return packages, nil
183+
}

differs/differs.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ var Analyzers = map[string]Analyzer{
4747
"file": FileAnalyzer{},
4848
"layer": FileLayerAnalyzer{},
4949
"apt": AptAnalyzer{},
50+
"aptlayer": AptLayerAnalyzer{},
5051
"rpm": RPMAnalyzer{},
5152
"pip": PipAnalyzer{},
5253
"node": NodeAnalyzer{},

0 commit comments

Comments
 (0)