mirror of
https://github.com/anchore/syft.git
synced 2026-11-04 08:26:38 +01:00
with package id
This commit is contained in:
@@ -18,7 +18,7 @@ func init() {
|
||||
controllerInstance.add(dpkg.NewAnalyzer())
|
||||
}
|
||||
|
||||
func Analyze(s scope.Scope) (pkg.Catalog, error) {
|
||||
func Analyze(s scope.Scope) (*pkg.Catalog, error) {
|
||||
return controllerInstance.analyze(s)
|
||||
}
|
||||
|
||||
@@ -31,7 +31,7 @@ func (c *controller) add(a Analyzer) {
|
||||
c.analyzers = append(c.analyzers, a)
|
||||
}
|
||||
|
||||
func (c *controller) analyze(s scope.Scope) (pkg.Catalog, error) {
|
||||
func (c *controller) analyze(s scope.Scope) (*pkg.Catalog, error) {
|
||||
catalog := pkg.NewCatalog()
|
||||
fileSelection := make([]file.Reference, 0)
|
||||
|
||||
@@ -44,7 +44,7 @@ func (c *controller) analyze(s scope.Scope) (pkg.Catalog, error) {
|
||||
// fetch contents for requested selection by analyzers
|
||||
contents, err := s.Image.MultipleFileContentsByRef(fileSelection...)
|
||||
if err != nil {
|
||||
return pkg.Catalog{}, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// perform analysis, accumulating errors for each failed analysis
|
||||
@@ -65,7 +65,7 @@ func (c *controller) analyze(s scope.Scope) (pkg.Catalog, error) {
|
||||
}
|
||||
|
||||
if errs != nil {
|
||||
return pkg.Catalog{}, errs
|
||||
return nil, errs
|
||||
}
|
||||
|
||||
return catalog, nil
|
||||
|
||||
@@ -10,7 +10,7 @@ import (
|
||||
"github.com/mitchellh/mapstructure"
|
||||
)
|
||||
|
||||
var endOfPackages = fmt.Errorf("no more packages to read")
|
||||
var errEndOfPackages = fmt.Errorf("no more packages to read")
|
||||
|
||||
func ParseEntries(reader io.Reader) ([]pkg.DpkgMetadata, error) {
|
||||
buffedReader := bufio.NewReader(reader)
|
||||
@@ -19,7 +19,7 @@ func ParseEntries(reader io.Reader) ([]pkg.DpkgMetadata, error) {
|
||||
for {
|
||||
entry, err := parseEntry(buffedReader)
|
||||
if err != nil {
|
||||
if err == endOfPackages {
|
||||
if err == errEndOfPackages {
|
||||
break
|
||||
}
|
||||
return nil, err
|
||||
@@ -38,7 +38,7 @@ func parseEntry(reader *bufio.Reader) (entry pkg.DpkgMetadata, err error) {
|
||||
line, err := reader.ReadString('\n')
|
||||
if err != nil {
|
||||
if err == io.EOF {
|
||||
return pkg.DpkgMetadata{}, endOfPackages
|
||||
return pkg.DpkgMetadata{}, errEndOfPackages
|
||||
}
|
||||
return pkg.DpkgMetadata{}, err
|
||||
}
|
||||
|
||||
@@ -8,10 +8,10 @@ import (
|
||||
)
|
||||
|
||||
// TODO: add os detection results as return value
|
||||
func CatalogImage(img *image.Image, o scope.Option) (pkg.Catalog, error) {
|
||||
func CatalogImage(img *image.Image, o scope.Option) (*pkg.Catalog, error) {
|
||||
s, err := scope.NewScope(img, o)
|
||||
if err != nil {
|
||||
return pkg.Catalog{}, err
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// TODO: add OS detection here...
|
||||
|
||||
+55
-11
@@ -1,31 +1,75 @@
|
||||
package pkg
|
||||
|
||||
import (
|
||||
"sync"
|
||||
|
||||
"github.com/anchore/imgbom/internal/log"
|
||||
"github.com/anchore/stereoscope/pkg/file"
|
||||
)
|
||||
|
||||
// TODO: add reader methods (by type, id, fuzzy search, etc)
|
||||
|
||||
var nextPackageID int64
|
||||
|
||||
type Catalog struct {
|
||||
// TODO: catalog by package ID for potential indexing
|
||||
packages map[Type][]Package
|
||||
byID map[ID]*Package
|
||||
byType map[Type][]*Package
|
||||
byFile map[file.Reference][]*Package
|
||||
lock sync.RWMutex
|
||||
}
|
||||
|
||||
func NewCatalog() Catalog {
|
||||
return Catalog{
|
||||
packages: make(map[Type][]Package),
|
||||
func NewCatalog() *Catalog {
|
||||
return &Catalog{
|
||||
byID: make(map[ID]*Package),
|
||||
byType: make(map[Type][]*Package),
|
||||
byFile: make(map[file.Reference][]*Package),
|
||||
}
|
||||
}
|
||||
|
||||
func (c *Catalog) Package(id ID) *Package {
|
||||
return c.byID[id]
|
||||
}
|
||||
|
||||
func (c *Catalog) PackagesByFile(ref file.Reference) []*Package {
|
||||
return c.byFile[ref]
|
||||
}
|
||||
|
||||
func (c *Catalog) Add(p Package) {
|
||||
_, ok := c.packages[p.Type]
|
||||
if p.id != 0 {
|
||||
log.Errorf("package already added to catalog: %s", p)
|
||||
return
|
||||
}
|
||||
c.lock.Lock()
|
||||
defer c.lock.Unlock()
|
||||
|
||||
p.id = ID(nextPackageID)
|
||||
nextPackageID++
|
||||
|
||||
// store by package ID
|
||||
c.byID[p.id] = &p
|
||||
|
||||
// store by package type
|
||||
_, ok := c.byType[p.Type]
|
||||
if !ok {
|
||||
c.packages[p.Type] = make([]Package, 0)
|
||||
c.byType[p.Type] = make([]*Package, 0)
|
||||
}
|
||||
c.byType[p.Type] = append(c.byType[p.Type], &p)
|
||||
|
||||
// store by file references
|
||||
for _, s := range p.Source {
|
||||
_, ok := c.byFile[s]
|
||||
if !ok {
|
||||
c.byFile[s] = make([]*Package, 0)
|
||||
}
|
||||
c.byFile[s] = append(c.byFile[s], &p)
|
||||
}
|
||||
c.packages[p.Type] = append(c.packages[p.Type], p)
|
||||
}
|
||||
|
||||
func (c *Catalog) Enumerate(types ...Type) <-chan Package {
|
||||
channel := make(chan Package)
|
||||
func (c *Catalog) Enumerate(types ...Type) <-chan *Package {
|
||||
channel := make(chan *Package)
|
||||
go func() {
|
||||
defer close(channel)
|
||||
for ty, packages := range c.packages {
|
||||
for ty, packages := range c.byType {
|
||||
if len(types) != 0 {
|
||||
found := false
|
||||
typeCheck:
|
||||
|
||||
+14
-3
@@ -1,11 +1,16 @@
|
||||
package pkg
|
||||
|
||||
import "github.com/anchore/stereoscope/pkg/file"
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
// TODO: add package ID (random/incremental)
|
||||
"github.com/anchore/stereoscope/pkg/file"
|
||||
)
|
||||
|
||||
type ID int64
|
||||
|
||||
// TODO: add field to trace which analyzer detected this
|
||||
type Package struct {
|
||||
id ID
|
||||
Name string
|
||||
Version string
|
||||
Source []file.Reference
|
||||
@@ -14,4 +19,10 @@ type Package struct {
|
||||
Metadata interface{}
|
||||
}
|
||||
|
||||
// TODO: stringer...
|
||||
func (p Package) ID() ID {
|
||||
return p.id
|
||||
}
|
||||
|
||||
func (p Package) String() string {
|
||||
return fmt.Sprintf("Pkg(type=%s, name=%s, version=%s)", p.Type, p.Name, p.Version)
|
||||
}
|
||||
|
||||
+2
-2
@@ -5,7 +5,7 @@ const (
|
||||
ApkPkg
|
||||
DebPkg
|
||||
JavaPkg
|
||||
NodePkg
|
||||
JavaScriptPkg
|
||||
PacmanPkg
|
||||
PythonPkg
|
||||
RpmPkg
|
||||
@@ -19,7 +19,7 @@ var typeStr = []string{
|
||||
"apk",
|
||||
"deb",
|
||||
"java",
|
||||
"node",
|
||||
"javascript",
|
||||
"pacman",
|
||||
"python",
|
||||
"rpm",
|
||||
|
||||
@@ -49,7 +49,7 @@ type artifact struct {
|
||||
Metadata interface{} `json:"metadata"`
|
||||
}
|
||||
|
||||
func (pres *Presenter) Present(output io.Writer, img *stereoscopeImg.Image, catalog pkg.Catalog) error {
|
||||
func (pres *Presenter) Present(output io.Writer, img *stereoscopeImg.Image, catalog *pkg.Catalog) error {
|
||||
tags := make([]string, len(img.Metadata.Tags))
|
||||
for idx, tag := range img.Metadata.Tags {
|
||||
tags[idx] = tag.String()
|
||||
|
||||
@@ -16,7 +16,7 @@ var Options = []Option{
|
||||
JSONPresenter,
|
||||
}
|
||||
|
||||
type Option uint
|
||||
type Option int
|
||||
|
||||
func ParseOption(userStr string) Option {
|
||||
switch strings.ToLower(userStr) {
|
||||
@@ -28,7 +28,7 @@ func ParseOption(userStr string) Option {
|
||||
}
|
||||
|
||||
func (o Option) String() string {
|
||||
if int(o) >= len(optionStr) {
|
||||
if int(o) >= len(optionStr) || o < 0 {
|
||||
return optionStr[0]
|
||||
}
|
||||
|
||||
|
||||
@@ -9,7 +9,7 @@ import (
|
||||
)
|
||||
|
||||
type Presenter interface {
|
||||
Present(io.Writer, *image.Image, pkg.Catalog) error
|
||||
Present(io.Writer, *image.Image, *pkg.Catalog) error
|
||||
}
|
||||
|
||||
func GetPresenter(option Option) Presenter {
|
||||
|
||||
@@ -8,7 +8,7 @@ const (
|
||||
AllLayersScope
|
||||
)
|
||||
|
||||
type Option uint
|
||||
type Option int
|
||||
|
||||
var optionStr = []string{
|
||||
"UnknownScope",
|
||||
@@ -32,7 +32,7 @@ func ParseOption(userStr string) Option {
|
||||
}
|
||||
|
||||
func (o Option) String() string {
|
||||
if int(o) >= len(optionStr) {
|
||||
if int(o) >= len(optionStr) || o < 0 {
|
||||
return optionStr[0]
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user