github.com/anchore/syft@v1.38.2/syft/internal/fileresolver/file.go (about)

     1  package fileresolver
     2  
     3  import (
     4  	"fmt"
     5  
     6  	"github.com/anchore/stereoscope/pkg/filetree"
     7  	"github.com/anchore/syft/syft/file"
     8  )
     9  
    10  // Compile time assurance that we meet the Resolver interface.
    11  var _ file.Resolver = (*File)(nil)
    12  
    13  // File implements path and content access for the file data source.
    14  type File struct {
    15  	FiletreeResolver
    16  	path    string
    17  	indexer *fileIndexer
    18  }
    19  
    20  // NewFromFile single file analyser
    21  // path is the filepath of the file we're creating content access for
    22  func NewFromFile(path string, pathFilters ...PathIndexVisitor) (*File, error) {
    23  	resolver, err := newFromFileWithoutIndex(path, pathFilters...)
    24  	if err != nil {
    25  		return nil, err
    26  	}
    27  
    28  	return resolver, resolver.buildIndex()
    29  }
    30  
    31  func newFromFileWithoutIndex(path string, pathFilters ...PathIndexVisitor) (*File, error) {
    32  	absParentDir, err := absoluteSymlinkFreePathToParent(path)
    33  	if err != nil {
    34  		return nil, err
    35  	}
    36  
    37  	chroot, err := NewChrootContextFromCWD(absParentDir, absParentDir)
    38  	if err != nil {
    39  		return nil, fmt.Errorf("unable to interpret chroot context: %w", err)
    40  	}
    41  
    42  	cleanBase := chroot.Base()
    43  
    44  	return &File{
    45  		path: path,
    46  		FiletreeResolver: FiletreeResolver{
    47  			Chroot: *chroot,
    48  			Tree:   filetree.New(),
    49  			Index:  filetree.NewIndex(),
    50  			Opener: nativeOSFileOpener,
    51  		},
    52  		indexer: newFileIndexer(path, cleanBase, pathFilters...),
    53  	}, nil
    54  }
    55  
    56  func (r *File) buildIndex() error {
    57  	if r.indexer == nil {
    58  		return fmt.Errorf("no file indexer configured")
    59  	}
    60  	tree, index, err := r.indexer.build()
    61  	if err != nil {
    62  		return err
    63  	}
    64  
    65  	r.Tree = tree
    66  	r.Index = index
    67  	r.SearchContext = filetree.NewSearchContext(tree, index)
    68  
    69  	return nil
    70  }
    71  
    72  // Stringer to represent a file path data source
    73  func (r *File) String() string {
    74  	return fmt.Sprintf("file:%s", r.path)
    75  }