fix: address code review findings

- notifier: show artist display names (not internal IDs) in digest; resolve
  names from artist_settings and fall back to ID when unavailable
- notifier: skip sending an empty digest to avoid daily spam
- config: require telegram token/chat_id when enabled
- web: warn loudly when auth is disabled on a non-loopback bind; add HTTP
  server timeouts
- web: treat SetReleaseIgnored "release not found" as benign redirect (0 rows)
- musicbrainz: reject low-score/name-mismatched MBID resolutions instead of
  silently caching the wrong artist
- database: remove dead duplicate err check; harden DSN param appending
- musicbrainz: check rows.Err() after iterating existing releases
This commit is contained in:
2026-07-19 23:46:05 +03:00
parent 389d177d85
commit 7cdb473d9c
12 changed files with 189 additions and 22 deletions

View File

@@ -44,6 +44,13 @@ func NewServer(cfg *config.ServerConfig, db *database.DB, uiBaseURL string, thre
uiBaseURL: strings.TrimRight(uiBaseURL, "/"),
threshold: threshold,
}
// Warn loudly when auth is disabled but the server is reachable from outside
// the host: Basic auth is silently skipped when Username/Password are empty,
// so an operator who forgets credentials on a non-loopback bind would expose
// DB-mutating POST routes (ignore/restore/toggle) to the network.
if (cfg.Username == "" || cfg.Password == "") && cfg.Host != "localhost" && cfg.Host != "127.0.0.1" && cfg.Host != "::1" {
log.Printf("WARNING: Web UI authentication is DISABLED (server.username/password empty) and the server is bound to %q. The dashboard and its state-changing routes are exposed to the network. Set credentials or bind to localhost.", cfg.Host)
}
mux := http.NewServeMux()
mux.HandleFunc("/", s.handleDashboard)
mux.HandleFunc("/artist/{id}", s.handleArtist)
@@ -72,8 +79,12 @@ func (s *Server) Addr() string {
// due to ctx cancellation returns nil).
func (s *Server) Start(ctx context.Context) error {
srv := &http.Server{
Addr: s.Addr(),
Handler: s.Handler(),
Addr: s.Addr(),
Handler: s.Handler(),
ReadTimeout: 15 * time.Second,
ReadHeaderTimeout: 10 * time.Second,
WriteTimeout: 30 * time.Second,
IdleTimeout: 120 * time.Second,
}
go func() {