From ea9ed4a28756756e24d0f06b840339e6a86ca6c4 Mon Sep 17 00:00:00 2001 From: Deluan Date: Fri, 17 Jan 2020 22:41:10 -0500 Subject: [PATCH] Fix ChangeDetector to keep the dirMap from last scan --- persistence/mediafile_repository.go | 3 +++ scanner/change_detector.go | 16 +++++++--------- scanner/change_detector_test.go | 27 +++++++++++++++------------ scanner/scanner.go | 8 ++++---- scanner/tag_scanner.go | 5 +++-- 5 files changed, 32 insertions(+), 27 deletions(-) diff --git a/persistence/mediafile_repository.go b/persistence/mediafile_repository.go index 99f3e9aeb..56599caaf 100644 --- a/persistence/mediafile_repository.go +++ b/persistence/mediafile_repository.go @@ -118,6 +118,9 @@ func (r *mediaFileRepository) DeleteByPath(path string) error { } filtered = append(filtered, mf.ID) } + if len(filtered) == 0 { + return nil + } _, err = r.newQuery(o).Filter("id__in", filtered).Delete() return err } diff --git a/scanner/change_detector.go b/scanner/change_detector.go index ee94c1481..dde337fb2 100644 --- a/scanner/change_detector.go +++ b/scanner/change_detector.go @@ -11,26 +11,24 @@ import ( type ChangeDetector struct { rootFolder string - lastUpdate time.Time dirMap map[string]time.Time } -func NewChangeDetector(rootFolder string, lastUpdate time.Time) *ChangeDetector { +func NewChangeDetector(rootFolder string) *ChangeDetector { return &ChangeDetector{ rootFolder: rootFolder, - lastUpdate: lastUpdate, dirMap: map[string]time.Time{}, } } -func (s *ChangeDetector) Scan() (changed []string, deleted []string, err error) { +func (s *ChangeDetector) Scan(lastModifiedSince time.Time) (changed []string, deleted []string, err error) { start := time.Now() newMap := make(map[string]time.Time) err = s.loadMap(s.rootFolder, newMap) if err != nil { return } - changed, deleted, err = s.checkForUpdates(s.dirMap, newMap) + changed, deleted, err = s.checkForUpdates(lastModifiedSince, newMap) if err != nil { return } @@ -95,17 +93,17 @@ func (s *ChangeDetector) getRelativePath(subfolder string) string { return dir } -func (s *ChangeDetector) checkForUpdates(oldMap map[string]time.Time, newMap map[string]time.Time) (changed []string, deleted []string, err error) { +func (s *ChangeDetector) checkForUpdates(lastModifiedSince time.Time, newMap map[string]time.Time) (changed []string, deleted []string, err error) { for dir, lastUpdated := range newMap { - oldLastUpdated, ok := oldMap[dir] + oldLastUpdated, ok := s.dirMap[dir] if !ok { - oldLastUpdated = s.lastUpdate + oldLastUpdated = lastModifiedSince } if lastUpdated.After(oldLastUpdated) { changed = append(changed, dir) } } - for dir := range oldMap { + for dir := range s.dirMap { if _, ok := newMap[dir]; !ok { deleted = append(deleted, dir) } diff --git a/scanner/change_detector_test.go b/scanner/change_detector_test.go index 623069910..2ec621fba 100644 --- a/scanner/change_detector_test.go +++ b/scanner/change_detector_test.go @@ -14,18 +14,20 @@ var _ = Describe("ChangeDetector", func() { var testFolder string var scanner *ChangeDetector + lastModifiedSince := time.Time{} + BeforeEach(func() { testFolder, _ = ioutil.TempDir("", "cloudsonic_tests") err := os.MkdirAll(testFolder, 0700) if err != nil { panic(err) } - scanner = NewChangeDetector(testFolder, time.Time{}) + scanner = NewChangeDetector(testFolder) }) It("detects changes recursively", func() { // Scan empty folder - changed, deleted, err := scanner.Scan() + changed, deleted, err := scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(ConsistOf(".")) @@ -35,7 +37,7 @@ var _ = Describe("ChangeDetector", func() { if err != nil { panic(err) } - changed, deleted, err = scanner.Scan() + changed, deleted, err = scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(ConsistOf(".", "/a")) @@ -45,13 +47,13 @@ var _ = Describe("ChangeDetector", func() { if err != nil { panic(err) } - changed, deleted, err = scanner.Scan() + changed, deleted, err = scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(ConsistOf("/a", "/a/b", "/a/b/c")) // Scan with no changes - changed, deleted, err = scanner.Scan() + changed, deleted, err = scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(BeEmpty()) @@ -61,7 +63,7 @@ var _ = Describe("ChangeDetector", func() { if err != nil { panic(err) } - changed, deleted, err = scanner.Scan() + changed, deleted, err = scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(ConsistOf("/a/b")) @@ -71,7 +73,7 @@ var _ = Describe("ChangeDetector", func() { if err != nil { panic(err) } - changed, deleted, err = scanner.Scan() + changed, deleted, err = scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(ConsistOf("/a/b")) @@ -81,21 +83,22 @@ var _ = Describe("ChangeDetector", func() { if err != nil { panic(err) } - changed, deleted, err = scanner.Scan() + changed, deleted, err = scanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(ConsistOf("/a/b/c")) Expect(changed).To(ConsistOf("/a/b")) - // Only returns changes after lastUpdate - newScanner := NewChangeDetector(testFolder, time.Now()) - changed, deleted, err = newScanner.Scan() + // Only returns changes after lastModifiedSince + lastModifiedSince = time.Now() + newScanner := NewChangeDetector(testFolder) + changed, deleted, err = newScanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(BeEmpty()) Expect(changed).To(BeEmpty()) _, err = os.Create(path.Join(testFolder, "a", "b", "new.txt")) - changed, deleted, err = newScanner.Scan() + changed, deleted, err = newScanner.Scan(lastModifiedSince) Expect(err).To(BeNil()) Expect(deleted).To(BeEmpty()) Expect(changed).To(ConsistOf("/a/b")) diff --git a/scanner/scanner.go b/scanner/scanner.go index 15099d09b..cc99a53d4 100644 --- a/scanner/scanner.go +++ b/scanner/scanner.go @@ -76,16 +76,16 @@ func (s *Scanner) RescanAll(fullRescan bool) error { func (s *Scanner) Status() []StatusInfo { return nil } -func (i *Scanner) getLastModifiedSince(folder string) time.Time { - ms, err := i.repos.property.Get(model.PropLastScan + "-" + folder) +func (s *Scanner) getLastModifiedSince(folder string) time.Time { + ms, err := s.repos.property.Get(model.PropLastScan + "-" + folder) if err != nil { return time.Time{} } if ms == "" { return time.Time{} } - s, _ := strconv.ParseInt(ms, 10, 64) - return time.Unix(0, s*int64(time.Millisecond)) + i, _ := strconv.ParseInt(ms, 10, 64) + return time.Unix(0, i*int64(time.Millisecond)) } func (s *Scanner) updateLastModifiedSince(folder string, t time.Time) { diff --git a/scanner/tag_scanner.go b/scanner/tag_scanner.go index 714738d8a..46c76898f 100644 --- a/scanner/tag_scanner.go +++ b/scanner/tag_scanner.go @@ -18,12 +18,14 @@ import ( type TagScanner struct { rootFolder string repos Repositories + detector *ChangeDetector } func NewTagScanner(rootFolder string, repos Repositories) *TagScanner { return &TagScanner{ rootFolder: rootFolder, repos: repos, + detector: NewChangeDetector(rootFolder), } } @@ -41,8 +43,7 @@ func NewTagScanner(rootFolder string, repos Repositories) *TagScanner { // Delete all empty albums, delete all empty Artists // Recreate ArtistIndex func (s *TagScanner) Scan(ctx context.Context, lastModifiedSince time.Time) error { - detector := NewChangeDetector(s.rootFolder, lastModifiedSince) - changed, deleted, err := detector.Scan() + changed, deleted, err := s.detector.Scan(lastModifiedSince) if err != nil { return err }