package api

import (
	"context"
	"errors"
	"net/http"

	"github.com/go-chi/chi/v5"
	"github.com/jackc/pgx/v5"

	"git.fabledsword.com/bvandeusen/minstrel/internal/apierror"
	"git.fabledsword.com/bvandeusen/minstrel/internal/coverart"
	"git.fabledsword.com/bvandeusen/minstrel/internal/db/dbq"
)

type adminCoverRefetchResp struct {
	AlbumID        string  `json:"album_id"`
	CoverArtPath   *string `json:"cover_art_path"`
	CoverArtSource *string `json:"cover_art_source"`
}

// handleAdminAlbumRefetchCover implements POST /api/admin/albums/{id}/cover/refetch.
// Synchronously clears + re-runs the enricher for one album.
func (h *handlers) handleAdminAlbumRefetchCover(w http.ResponseWriter, r *http.Request) {
	albumID, ok := parseUUID(chi.URLParam(r, "id"))
	if !ok {
		writeErr(w, apierror.BadRequest("bad_request", "invalid album id"))
		return
	}
	if err := h.coverart.RetryAlbum(r.Context(), albumID); err != nil {
		if errors.Is(err, coverart.ErrNotFound) || errors.Is(err, pgx.ErrNoRows) {
			writeErr(w, &apierror.Error{Status: http.StatusNotFound, Code: "not_found", Message: "album not found"})
			return
		}
		writeErrWithLog(w, h.logger, "admin: cover refetch failed", apierror.InternalMsg("refetch failed", err))
		return
	}
	row, err := dbq.New(h.pool).GetAlbumWithFirstTrackPath(r.Context(), albumID)
	if err != nil {
		writeErrWithLog(w, h.logger, "admin: post-refetch read failed", apierror.InternalMsg("read failed", err))
		return
	}
	writeJSON(w, http.StatusOK, adminCoverRefetchResp{
		AlbumID:        uuidToString(albumID),
		CoverArtPath:   row.CoverArtPath,
		CoverArtSource: row.CoverArtSource,
	})
}

type adminBulkRefetchResp struct {
	Started bool `json:"started"`
}

// handleAdminBulkRefetchCovers implements POST /api/admin/covers/refetch-missing.
// Returns immediately; the drain runs UNBOUNDED in a background goroutine
// (#388 — no global cap; remote providers self-throttle per provider, local
// sources run at disk speed). The count is unknowable synchronously, so the
// response just acknowledges the drain started.
func (h *handlers) handleAdminBulkRefetchCovers(w http.ResponseWriter, _ *http.Request) {
	go func() {
		bgCtx := context.Background()
		if _, err := h.coverart.EnrichRetryMissing(bgCtx, -1); err != nil {
			h.logger.Warn("admin: bulk cover refetch failed", "err", err)
		}
	}()
	writeJSON(w, http.StatusOK, adminBulkRefetchResp{Started: true})
}
