refactor(scanner): don't be fancy with the clean funcs
This commit is contained in:
@@ -91,7 +91,8 @@ func New(musicPath string, db *db.DB, genreSplit string) *Scanner {
|
|||||||
// ## begin clean funcs
|
// ## begin clean funcs
|
||||||
// ## begin clean funcs
|
// ## begin clean funcs
|
||||||
|
|
||||||
func (s *Scanner) cleanTracks() (int, error) {
|
func (s *Scanner) cleanTracks() error {
|
||||||
|
start := time.Now()
|
||||||
var previous []int
|
var previous []int
|
||||||
var missing []int64
|
var missing []int64
|
||||||
err := s.db.
|
err := s.db.
|
||||||
@@ -99,7 +100,7 @@ func (s *Scanner) cleanTracks() (int, error) {
|
|||||||
Pluck("id", &previous).
|
Pluck("id", &previous).
|
||||||
Error
|
Error
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, fmt.Errorf("plucking ids: %w", err)
|
return fmt.Errorf("plucking ids: %w", err)
|
||||||
}
|
}
|
||||||
for _, prev := range previous {
|
for _, prev := range previous {
|
||||||
if _, ok := s.seenTracks[prev]; !ok {
|
if _, ok := s.seenTracks[prev]; !ok {
|
||||||
@@ -109,10 +110,15 @@ func (s *Scanner) cleanTracks() (int, error) {
|
|||||||
err = s.db.TransactionChunked(missing, func(tx *gorm.DB, chunk []int64) error {
|
err = s.db.TransactionChunked(missing, func(tx *gorm.DB, chunk []int64) error {
|
||||||
return tx.Where(chunk).Delete(&db.Track{}).Error
|
return tx.Where(chunk).Delete(&db.Track{}).Error
|
||||||
})
|
})
|
||||||
return len(missing), err
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
log.Printf("finished clean tracks in %s, %d removed", durSince(start), len(missing))
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Scanner) cleanFolders() (int, error) {
|
func (s *Scanner) cleanFolders() error {
|
||||||
|
start := time.Now()
|
||||||
var previous []int
|
var previous []int
|
||||||
var missing []int64
|
var missing []int64
|
||||||
err := s.db.
|
err := s.db.
|
||||||
@@ -120,7 +126,7 @@ func (s *Scanner) cleanFolders() (int, error) {
|
|||||||
Pluck("id", &previous).
|
Pluck("id", &previous).
|
||||||
Error
|
Error
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, fmt.Errorf("plucking ids: %w", err)
|
return fmt.Errorf("plucking ids: %w", err)
|
||||||
}
|
}
|
||||||
for _, prev := range previous {
|
for _, prev := range previous {
|
||||||
if _, ok := s.seenFolders[prev]; !ok {
|
if _, ok := s.seenFolders[prev]; !ok {
|
||||||
@@ -130,10 +136,15 @@ func (s *Scanner) cleanFolders() (int, error) {
|
|||||||
err = s.db.TransactionChunked(missing, func(tx *gorm.DB, chunk []int64) error {
|
err = s.db.TransactionChunked(missing, func(tx *gorm.DB, chunk []int64) error {
|
||||||
return tx.Where(chunk).Delete(&db.Album{}).Error
|
return tx.Where(chunk).Delete(&db.Album{}).Error
|
||||||
})
|
})
|
||||||
return len(missing), err
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
log.Printf("finished clean folders in %s, %d removed", durSince(start), len(missing))
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Scanner) cleanArtists() (int, error) {
|
func (s *Scanner) cleanArtists() error {
|
||||||
|
start := time.Now()
|
||||||
sub := s.db.
|
sub := s.db.
|
||||||
Select("artists.id").
|
Select("artists.id").
|
||||||
Model(&db.Artist{}).
|
Model(&db.Artist{}).
|
||||||
@@ -143,10 +154,15 @@ func (s *Scanner) cleanArtists() (int, error) {
|
|||||||
q := s.db.
|
q := s.db.
|
||||||
Where("artists.id IN ?", sub).
|
Where("artists.id IN ?", sub).
|
||||||
Delete(&db.Artist{})
|
Delete(&db.Artist{})
|
||||||
return int(q.RowsAffected), q.Error
|
if err := q.Error; err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
log.Printf("finished clean artists in %s, %d removed", durSince(start), q.RowsAffected)
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Scanner) cleanGenres() (int, error) {
|
func (s *Scanner) cleanGenres() error {
|
||||||
|
start := time.Now()
|
||||||
subTrack := s.db.
|
subTrack := s.db.
|
||||||
Select("genres.id").
|
Select("genres.id").
|
||||||
Model(&db.Genre{}).
|
Model(&db.Genre{}).
|
||||||
@@ -163,7 +179,8 @@ func (s *Scanner) cleanGenres() (int, error) {
|
|||||||
Where("genres.id IN ?", subTrack).
|
Where("genres.id IN ?", subTrack).
|
||||||
Or("genres.id IN ?", subAlbum).
|
Or("genres.id IN ?", subAlbum).
|
||||||
Delete(&db.Genre{})
|
Delete(&db.Genre{})
|
||||||
return int(q.RowsAffected), q.Error
|
log.Printf("finished clean genres in %s, %d removed", durSince(start), q.RowsAffected)
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// ## begin entries
|
// ## begin entries
|
||||||
@@ -182,13 +199,15 @@ func (s *Scanner) Start(opts ScanOptions) error {
|
|||||||
}
|
}
|
||||||
unSet := SetScanning()
|
unSet := SetScanning()
|
||||||
defer unSet()
|
defer unSet()
|
||||||
|
|
||||||
// reset state vars for the new scan
|
// reset state vars for the new scan
|
||||||
s.isFull = opts.IsFull
|
s.isFull = opts.IsFull
|
||||||
s.seenTracks = map[int]struct{}{}
|
s.seenTracks = map[int]struct{}{}
|
||||||
s.seenFolders = map[int]struct{}{}
|
s.seenFolders = map[int]struct{}{}
|
||||||
s.curFolders = &stack.Stack{}
|
s.curFolders = &stack.Stack{}
|
||||||
s.seenTracksNew = 0
|
s.seenTracksNew = 0
|
||||||
// ** begin being walking
|
|
||||||
|
// begin walking
|
||||||
log.Println("starting scan")
|
log.Println("starting scan")
|
||||||
var errCount int
|
var errCount int
|
||||||
start := time.Now()
|
start := time.Now()
|
||||||
@@ -212,27 +231,20 @@ func (s *Scanner) Start(opts ScanOptions) error {
|
|||||||
len(s.seenTracks),
|
len(s.seenTracks),
|
||||||
errCount,
|
errCount,
|
||||||
)
|
)
|
||||||
// ** begin cleaning
|
|
||||||
cleanFuncs := []struct {
|
if err := s.cleanTracks(); err != nil {
|
||||||
name string
|
return fmt.Errorf("clean tracks: %w", err)
|
||||||
f func() (int, error)
|
|
||||||
}{
|
|
||||||
{name: "tracks", f: s.cleanTracks},
|
|
||||||
{name: "folders", f: s.cleanFolders},
|
|
||||||
{name: "artists", f: s.cleanArtists},
|
|
||||||
{name: "genres", f: s.cleanGenres},
|
|
||||||
}
|
}
|
||||||
for _, clean := range cleanFuncs {
|
if err := s.cleanFolders(); err != nil {
|
||||||
start = time.Now()
|
return fmt.Errorf("clean folders: %w", err)
|
||||||
deleted, err := clean.f()
|
|
||||||
if err != nil {
|
|
||||||
log.Printf("finished clean %s in %s with error: %v",
|
|
||||||
clean.name, durSince(start), err)
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
log.Printf("finished clean %s in %s, %d removed",
|
|
||||||
clean.name, durSince(start), deleted)
|
|
||||||
}
|
}
|
||||||
|
if err := s.cleanArtists(); err != nil {
|
||||||
|
return fmt.Errorf("clean artists: %w", err)
|
||||||
|
}
|
||||||
|
if err := s.cleanGenres(); err != nil {
|
||||||
|
return fmt.Errorf("clean genres: %w", err)
|
||||||
|
}
|
||||||
|
|
||||||
// finish up
|
// finish up
|
||||||
strNow := strconv.FormatInt(time.Now().Unix(), 10)
|
strNow := strconv.FormatInt(time.Now().Unix(), 10)
|
||||||
s.db.SetSetting("last_scan_time", strNow)
|
s.db.SetSetting("last_scan_time", strNow)
|
||||||
@@ -392,7 +404,7 @@ func (s *Scanner) handleTrack(it *item) error {
|
|||||||
s.trTxOpen = true
|
s.trTxOpen = true
|
||||||
}
|
}
|
||||||
|
|
||||||
// ** begin set track basics
|
// set track basics
|
||||||
track := &db.Track{}
|
track := &db.Track{}
|
||||||
defer func() {
|
defer func() {
|
||||||
// folder's id will come from early return
|
// folder's id will come from early return
|
||||||
@@ -429,7 +441,7 @@ func (s *Scanner) handleTrack(it *item) error {
|
|||||||
track.Length = trTags.Length() // these two should be calculated
|
track.Length = trTags.Length() // these two should be calculated
|
||||||
track.Bitrate = trTags.Bitrate() // ...from the file instead of tags
|
track.Bitrate = trTags.Bitrate() // ...from the file instead of tags
|
||||||
|
|
||||||
// ** begin set album artist basics
|
// set album artist basics
|
||||||
artistName := firstTag("Unknown Artist", trTags.AlbumArtist, trTags.Artist)
|
artistName := firstTag("Unknown Artist", trTags.AlbumArtist, trTags.Artist)
|
||||||
artist := &db.Artist{}
|
artist := &db.Artist{}
|
||||||
s.trTx.
|
s.trTx.
|
||||||
@@ -441,7 +453,7 @@ func (s *Scanner) handleTrack(it *item) error {
|
|||||||
FirstOrCreate(artist)
|
FirstOrCreate(artist)
|
||||||
track.ArtistID = artist.ID
|
track.ArtistID = artist.ID
|
||||||
|
|
||||||
// ** begin set genre
|
// set genre
|
||||||
genreTag := firstTag("Unknown Genre", trTags.Genre)
|
genreTag := firstTag("Unknown Genre", trTags.Genre)
|
||||||
genreNames := strings.Split(genreTag, s.genreSplit)
|
genreNames := strings.Split(genreTag, s.genreSplit)
|
||||||
genreIDs := []int{}
|
genreIDs := []int{}
|
||||||
@@ -453,10 +465,10 @@ func (s *Scanner) handleTrack(it *item) error {
|
|||||||
genreIDs = append(genreIDs, genre.ID)
|
genreIDs = append(genreIDs, genre.ID)
|
||||||
}
|
}
|
||||||
|
|
||||||
// ** begin save the track
|
|
||||||
if err := s.trTx.Save(track).Error; err != nil {
|
if err := s.trTx.Save(track).Error; err != nil {
|
||||||
return fmt.Errorf("writing track table: %w", err)
|
return fmt.Errorf("writing track table: %w", err)
|
||||||
}
|
}
|
||||||
|
|
||||||
err = s.trTx.
|
err = s.trTx.
|
||||||
Where("track_id=?", track.ID).
|
Where("track_id=?", track.ID).
|
||||||
Delete(db.TrackGenre{}).
|
Delete(db.TrackGenre{}).
|
||||||
@@ -475,7 +487,7 @@ func (s *Scanner) handleTrack(it *item) error {
|
|||||||
}
|
}
|
||||||
s.seenTracksNew++
|
s.seenTracksNew++
|
||||||
|
|
||||||
// ** begin set album if this is the first track in the folder
|
// set album if this is the first track in the folder
|
||||||
folder := s.curFolders.Peek()
|
folder := s.curFolders.Peek()
|
||||||
if folder.TagTitle != "" {
|
if folder.TagTitle != "" {
|
||||||
return nil
|
return nil
|
||||||
|
|||||||
Reference in New Issue
Block a user