from flask import Blueprint, make_response, redirect, render_template, request, url_for

from src.lib.favorites import get_favorite_artists, get_favorite_posts
from src.types.account.account import Account
from src.utils.decorators import require_login
from src.utils.utils import offset_list, parse_int, positive_or_none, restrict_value, sort_dict_list_by, step_int, take

favorites_bp = Blueprint("favorites", __name__)


@favorites_bp.route("/favorites", methods=["GET"])
@require_login
def list_favorites(user: Account):
    props = {"currentPage": "favorites"}
    base = request.args.to_dict()
    base.pop("o", None)

    fave_type = request.args.get("type", "artist")
    if fave_type == "post":
        favorites = get_favorite_posts(user.id)
        sort_field = restrict_value(request.args.get("sort"), ["faved_seq", "published"], "faved_seq")
    else:
        fave_type = "artist"
        favorites = get_favorite_artists(user.id)
        sort_field = restrict_value(
            request.args.get("sort"),
            ["faved_seq", "updated", "last_imported"],
            "updated",
        )

    limit = 50
    offset = positive_or_none(step_int(parse_int(request.args.get("o"), 0), limit))
    if offset is None:
        return redirect(url_for("favorites.list_favorites"))
    sort_asc = request.args.get("order") == "asc"
    results = sort_and_filter_favorites(favorites, offset, sort_field, sort_asc)

    props["fave_type"] = fave_type
    props["sort_field"] = sort_field
    props["sort_asc"] = sort_asc
    props["count"] = len(favorites)
    props["limit"] = limit

    response = make_response(
        render_template(
            "favorites.html",
            props=props,
            base=base,
            source="account",
            results=results,
        ),
        200,
    )
    response.headers["Cache-Control"] = "s-maxage=60"
    return response


def sort_and_filter_favorites(favorites, o, field, asc):
    favorites = sort_dict_list_by(favorites, field, not asc)
    return take(50, offset_list(o, favorites))
