From 914bd7cd6aa14e839332a98d91c30b19865b0cf2 Mon Sep 17 00:00:00 2001 From: Paul Buetow Date: Sun, 17 May 2026 15:25:52 +0300 Subject: Restructure repo: move Go server into player-server/ --- internal/service/scan.go | 101 ----------------------------------------------- 1 file changed, 101 deletions(-) delete mode 100644 internal/service/scan.go (limited to 'internal/service/scan.go') diff --git a/internal/service/scan.go b/internal/service/scan.go deleted file mode 100644 index da5c54f..0000000 --- a/internal/service/scan.go +++ /dev/null @@ -1,101 +0,0 @@ -package service - -import ( - "context" - "errors" - "log/slog" - "sync" - "time" - - "codeberg.org/snonux/player/internal/clock" - "codeberg.org/snonux/player/internal/model" - "codeberg.org/snonux/player/internal/scanner" -) - -// scanService handles triggering and tracking media library scans. -type scanService struct { - scanner scanner.Scanner - mediaRoot string - clock clock.Clock - logger *slog.Logger - mu sync.Mutex - scanCancel context.CancelFunc - progress *model.ScanProgress - appCtx context.Context // application-level context used to propagate shutdown cancellation - doneCh chan<- struct{} -} - -// NewScanService creates a ScanService. -func NewScanService(appCtx context.Context, sc scanner.Scanner, mediaRoot string, clk clock.Clock, logger *slog.Logger) *scanService { - if logger == nil { - logger = slog.Default() - } - return &scanService{ - scanner: sc, - mediaRoot: mediaRoot, - clock: clk, - logger: logger, - appCtx: appCtx, - } -} - -func (s *scanService) TriggerRescan(ctx context.Context) error { - if s.scanner == nil { - return errors.New("scanner not configured") - } - - s.mu.Lock() - if s.scanCancel != nil { - s.scanCancel() - } - // Derive the scan context from the application-level context so that - // cancellation propagates on server exit, while still applying a 30-minute timeout. - scanCtx, cancel := context.WithTimeout(s.appCtx, 30*time.Minute) - s.scanCancel = cancel - progress := &model.ScanProgress{} - progress.Start(0) - s.progress = progress - s.mu.Unlock() - - go func() { - defer cancel() - defer s.notifyDone() - defer func() { - if err := handleWorkerPanic(s.logger, "rescan", recover()); err != nil { - progress.Done(err) - } - }() - err := s.scanner.Scan(scanCtx, s.mediaRoot, progress) - if err == nil { - err = scanCtx.Err() - } - if err != nil { - progress.Done(err) - s.logger.Error("rescan failed", "err", err) - } else { - progress.Done(nil) - s.logger.Info("rescan completed") - } - }() - return nil -} - -func (s *scanService) ScanProgress(ctx context.Context) model.ScanProgress { - s.mu.Lock() - progress := s.progress - s.mu.Unlock() - if progress == nil { - return model.ScanProgress{} - } - return progress.Copy() -} - -func (s *scanService) notifyDone() { - if s.doneCh == nil { - return - } - select { - case s.doneCh <- struct{}{}: - default: - } -} -- cgit v1.2.3