#!/usr/bin/env python3

from datetime import timedelta
import logging
import re

from .util import is_logged_in, salt

from flask import (
    Blueprint,
    current_app,
    flash,
    redirect,
    render_template,
    request,
)
from tentacles.globals import ctx


log = logging.getLogger(__name__)
BLUEPRINT = Blueprint("user", __name__)


@BLUEPRINT.route("/")
def root():
    return (
        render_template(
            "index.html.j2",
        ),
        200,
    )


@BLUEPRINT.route("/user/login", methods=["GET", "POST"])
def login():
    if is_logged_in():
        return redirect("/")

    elif request.method == "POST":
        if sid := ctx.db.try_login(
            username := request.form["username"],
            salt(request.form["password"]),
            timedelta(days=1),
        ):
            resp = redirect("/")
            resp.set_cookie("sid", sid)
            flash(f"Welcome, {username}", category="success")
            return resp

        else:
            flash("Incorrect username/password", category="error")
            return render_template("login.html.j2")

    else:
        return render_template("login.html.j2")


@BLUEPRINT.route("/user/register", methods=["GET", "POST"])
def register():
    if is_logged_in():
        return redirect("/")

    elif request.method == "POST":
        try:
            username = request.form["username"]
            email = request.form["email"]
            group_id = None
            status_id = None

            for user_config in current_app.config.get("users", []):
                if user_config["email"] == email:
                    if "group_id" in user_config:
                        group_id = user_config["group_id"]

                    if "status_id" in user_config:
                        status_id = user_config["status_id"]

                    break

            if res := ctx.db.try_create_user(
                username, email, salt(request.form["password"]), group_id, status_id
            ):
                id, status = res
                if status == -1:
                    flash(
                        "Please check your email for a verification request",
                        category="success",
                    )
                return render_template("register.html.j2")

        except Exception as e:
            log.exception("Error encountered while registering a user...")

        flash("Unable to register that username", category="error")
        return render_template("register.html.j2")

    else:
        return render_template("register.html.j2")


@BLUEPRINT.route("/user/logout")
def logout():
    # Invalidate the user's authorization
    ctx.db.delete_key(ctx.uid, ctx.sid)
    resp = redirect("/")
    resp.set_cookie("sid", "")
    return resp


@BLUEPRINT.route("/user", methods=["GET", "POST"])
def settings():
    if not is_logged_in():
        return redirect("/")

    elif request.method == "POST":
        if request.form["action"] == "add":
            ttl_spec = request.form.get("ttl")
            if ttl_spec == "forever":
                ttl = None
            elif m := re.fullmatch(r"(\d+)d", ttl_spec):
                ttl = timedelta(days=int(m.group(1)))
            else:
                flash("Bad request", category="error")
                return render_template("user.html.j2"), 400

            ctx.db.create_key(ctx.sid, ttl, request.form.get("name"))
            flash("Key created", category="success")

        elif request.form["action"] == "revoke":
            ctx.db.delete_key(ctx.uid, request.form.get("id"))
            flash("Key revoked", category="success")

        else:
            flash("Bad request", category="error")
            return render_template("user.html.j2"), 400

    return render_template("user.html.j2")
