From ddd4a81bfabf850b28822c21b3cb3d606b41fedd Mon Sep 17 00:00:00 2001 From: Alex Goodman Date: Fri, 29 May 2020 11:31:01 -0400 Subject: [PATCH] add bleve index --- cmd/root.go | 36 +++++++++++++++++++---- imgbom/pkg/catalog.go | 66 ++++++++++++++++++++++++++++++++++++++----- 2 files changed, 90 insertions(+), 12 deletions(-) diff --git a/cmd/root.go b/cmd/root.go index c86f8e82b..f073dfcfd 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -3,9 +3,10 @@ package cmd import ( "fmt" "os" + "strconv" "github.com/anchore/imgbom/imgbom" - "github.com/anchore/imgbom/imgbom/presenter" + "github.com/anchore/imgbom/imgbom/pkg" "github.com/anchore/imgbom/internal" "github.com/anchore/stereoscope" "github.com/spf13/cobra" @@ -63,11 +64,36 @@ func doRunCmd(cmd *cobra.Command, args []string) int { } log.Info("Complete!") - err = presenter.GetPresenter(appConfig.PresenterOpt).Present(os.Stdout, img, catalog) - if err != nil { - log.Errorf("could not format catalog results: %w", err) - return 1 + // err = presenter.GetPresenter(appConfig.PresenterOpt).Present(os.Stdout, img, catalog) + // if err != nil { + // log.Errorf("could not format catalog results: %w", err) + // return 1 + // } + result := catalog.SearchName("libselinux") + fmt.Println(result) + if result != nil { + for _, hit := range result.Hits { + pkgId, err := strconv.Atoi(hit.ID) + if err != nil { + // TODO: just no... + panic(err) + } + fmt.Println(pkgId, catalog.Package(pkg.ID(pkgId)), hit.Score) + } } + fmt.Println("------------------------------------------") + result = catalog.SearchMetadata("libselinux") + fmt.Println(result) + if result != nil { + for _, hit := range result.Hits { + pkgId, err := strconv.Atoi(hit.ID) + if err != nil { + // TODO: just no... + panic(err) + } + fmt.Println(pkgId, catalog.Package(pkg.ID(pkgId)), hit.Score) + } + } return 0 } diff --git a/imgbom/pkg/catalog.go b/imgbom/pkg/catalog.go index 716133ae7..32edfc712 100644 --- a/imgbom/pkg/catalog.go +++ b/imgbom/pkg/catalog.go @@ -1,10 +1,13 @@ package pkg import ( + "fmt" "sync" "github.com/anchore/imgbom/internal/log" "github.com/anchore/stereoscope/pkg/file" + "github.com/blevesearch/bleve" + "github.com/blevesearch/bleve/mapping" ) // TODO: add reader methods (by type, id, fuzzy search, etc) @@ -12,17 +15,34 @@ import ( var nextPackageID int64 type Catalog struct { - byID map[ID]*Package - byType map[Type][]*Package - byFile map[file.Reference][]*Package - lock sync.RWMutex + byID map[ID]*Package + byType map[Type][]*Package + byFile map[file.Reference][]*Package + searchSpace mapping.IndexMapping + nameSearchIndex bleve.Index + metadataSearchIndex bleve.Index + lock sync.RWMutex } func NewCatalog() Catalog { + searchMap := bleve.NewIndexMapping() + nameIndex, err := bleve.NewMemOnly(searchMap) + if err != nil { + // TODO: log + panic(err) + } + metadataIndex, err := bleve.NewMemOnly(searchMap) + if err != nil { + // TODO: log + panic(err) + } return Catalog{ - byID: make(map[ID]*Package), - byType: make(map[Type][]*Package), - byFile: make(map[file.Reference][]*Package), + byID: make(map[ID]*Package), + byType: make(map[Type][]*Package), + byFile: make(map[file.Reference][]*Package), + searchSpace: searchMap, + nameSearchIndex: nameIndex, + metadataSearchIndex: metadataIndex, } } @@ -63,6 +83,38 @@ func (c *Catalog) Add(p Package) { } c.byFile[s] = append(c.byFile[s], &p) } + + // index the package findings + err := c.nameSearchIndex.Index(fmt.Sprintf("%d", p.id), p.Name) + if err != nil { + // TODO: just no... + panic(err) + } + err = c.metadataSearchIndex.Index(fmt.Sprintf("%d", p.id), p.Metadata) + if err != nil { + // TODO: just no... + panic(err) + } +} + +func (c *Catalog) SearchMetadata(query string) *bleve.SearchResult { + request := bleve.NewSearchRequest(bleve.NewMatchQuery(query)) + result, err := c.metadataSearchIndex.Search(request) + if err != nil { + // TODO: just no... + panic(err) + } + return result +} + +func (c *Catalog) SearchName(query string) *bleve.SearchResult { + request := bleve.NewSearchRequest(bleve.NewMatchQuery(query)) + result, err := c.nameSearchIndex.Search(request) + if err != nil { + // TODO: just no... + panic(err) + } + return result } func (c *Catalog) Enumerate(types ...Type) <-chan *Package {