diff --git a/internal/factsengine/gatherers/dir_scan.go b/internal/factsengine/gatherers/dir_scan.go index 25814522..560a153f 100644 --- a/internal/factsengine/gatherers/dir_scan.go +++ b/internal/factsengine/gatherers/dir_scan.go @@ -68,32 +68,45 @@ func NewDefaultDirScanGatherer() *DirScanGatherer { return NewDirScanGatherer(afero.NewOsFs(), &cf, &cf) } -func (d *DirScanGatherer) Gather(_ context.Context, factsRequests []entities.FactRequest) ([]entities.Fact, error) { +func (d *DirScanGatherer) Gather(ctx context.Context, factsRequests []entities.FactRequest) ([]entities.Fact, error) { log.Infof("Starting %s facts gathering process", DirScanGathererName) - facts := []entities.Fact{} - for _, requestedFact := range factsRequests { - if requestedFact.Argument == "" { - log.Errorf("could not gather facts for %s gatherer, missing argument", DirScanGathererName) - facts = append(facts, entities.NewFactGatheredWithError(requestedFact, &DirScanMissingArgumentError)) - continue - } - scanResult, err := d.extractDirScanDetails(requestedFact.Argument) - if err != nil { - facts = append(facts, entities.NewFactGatheredWithError(requestedFact, DirScanScanningError.Wrap(err.Error()))) - continue - } - factValue, err := mapDirScanResultToFactValue(scanResult) - if err != nil { - facts = append(facts, entities.NewFactGatheredWithError(requestedFact, DirScanScanningError.Wrap(err.Error()))) - continue + results := make(chan []entities.Fact) + + go func() { + facts := []entities.Fact{} + for _, requestedFact := range factsRequests { + fact := d.gatherSingle(requestedFact) + facts = append(facts, fact) } - facts = append(facts, entities.NewFactGatheredWithRequest(requestedFact, factValue)) + results <- facts + }() + + select { + case <-ctx.Done(): + return nil, ctx.Err() + case facts := <-results: + log.Infof("Requested %s facts gathered", DirScanGathererName) + return facts, nil } +} - log.Infof("Requested %s facts gathered", DirScanGathererName) +func (d *DirScanGatherer) gatherSingle(requestedFact entities.FactRequest) entities.Fact { + if requestedFact.Argument == "" { + log.Errorf("could not gather facts for %s gatherer, missing argument", DirScanGathererName) + return entities.NewFactGatheredWithError(requestedFact, &DirScanMissingArgumentError) - return facts, nil + } + scanResult, err := d.extractDirScanDetails(requestedFact.Argument) + if err != nil { + return entities.NewFactGatheredWithError(requestedFact, DirScanScanningError.Wrap(err.Error())) + } + factValue, err := mapDirScanResultToFactValue(scanResult) + if err != nil { + return entities.NewFactGatheredWithError(requestedFact, DirScanScanningError.Wrap(err.Error())) + + } + return entities.NewFactGatheredWithRequest(requestedFact, factValue) } func (d *DirScanGatherer) extractDirScanDetails(dirscanPath string) (DirScanResult, error) { diff --git a/internal/factsengine/gatherers/dir_scan_test.go b/internal/factsengine/gatherers/dir_scan_test.go index cc533721..14606e54 100644 --- a/internal/factsengine/gatherers/dir_scan_test.go +++ b/internal/factsengine/gatherers/dir_scan_test.go @@ -167,3 +167,29 @@ func (s *DirScanGathererSuite) TestDirScanningSuccess() { s.NoError(err) s.EqualValues(expectedResult, result) } + +func (s *DirScanGathererSuite) TestDirScanningGathererContextCancelled() { + dirScanTestGlobPattern := "/var/test/*/ASCS*" + + groupSearcher := mocks.NewGroupSearcher(s.T()) + groupSearcher.On("GetGroupByID", mock.AnythingOfType("string")).Return("trento", nil).Maybe() + + userSearcher := mocks.NewUserSearcher(s.T()) + userSearcher.On("GetUsernameByID", mock.AnythingOfType("string")).Return("trento", nil).Maybe() + + c := gatherers.NewDirScanGatherer(s.testFS, userSearcher, groupSearcher) + factRequests := []entities.FactRequest{{ + Argument: dirScanTestGlobPattern, + CheckID: "check1", + Gatherer: "dir_scan", + Name: "dir_scan", + }} + ctx, cancel := context.WithCancel(context.Background()) + cancel() + + factResults, err := c.Gather(ctx, factRequests) + + s.Error(err) + s.Empty(factResults) + +}