# retoor <retoor@molodetz.nl>

import logging
from typing import Annotated
from fastapi import Depends, APIRouter, Request
from fastapi.responses import HTMLResponse
from devplacepy.database import get_table, get_setting, get_int_setting
from devplacepy.templating import templates
from devplacepy.utils import (
    create_session,
    get_current_user,
    register_account_async,
    cookie_secure,
)
from devplacepy.seo import base_seo_context
from devplacepy.models import SignupForm
from devplacepy.config import SECONDS_PER_DAY
from devplacepy.responses import respond, action_result, wants_json, json_error
from devplacepy.schemas import AuthPageOut
from devplacepy.services.audit import record as audit
from devplacepy.dependencies import json_or_form

logger = logging.getLogger(__name__)
router = APIRouter()

@router.get("/signup", response_class=HTMLResponse)
async def signup_page(request: Request):
    user = get_current_user(request)
    if user:
        return action_result(request, "/feed")
    seo_ctx = base_seo_context(
        request,
        title="Join DevPlace",
        description="Create your DevPlace account and start connecting with developers.",
        robots="noindex,nofollow",
    )
    registration_closed = get_setting("registration_open", "1") != "1"
    return respond(
        request,
        "signup.html",
        {
            **seo_ctx,
            "request": request,
            "page": "signup",
            "registration_closed": registration_closed,
        },
        model=AuthPageOut,
    )

@router.post("/signup")
async def signup(request: Request, data: Annotated[SignupForm, Depends(json_or_form(SignupForm))]):
    username = data.username
    email = data.email.strip().lower()
    password = data.password

    if get_setting("registration_open", "1") != "1":
        if wants_json(request):
            return json_error(403, "Registration is closed")
        seo_ctx = base_seo_context(
            request, title="Join DevPlace", robots="noindex,nofollow"
        )
        return templates.TemplateResponse(
            request,
            "signup.html",
            {**seo_ctx, "request": request, "registration_closed": True},
        )

    errors = []
    users = get_table("users")
    if users.find_one(username=username):
        errors.append("Username already taken")
    if users.find_one(email=email):
        errors.append("Email already registered")

    if errors:
        if wants_json(request):
            return json_error(400, "; ".join(errors), errors=errors)
        seo_ctx = base_seo_context(
            request, title="Join DevPlace", robots="noindex,nofollow"
        )
        return templates.TemplateResponse(
            request,
            "signup.html",
            {
                **seo_ctx,
                "request": request,
                "errors": errors,
                "username": username,
                "email": email,
            },
        )

    uid, role, is_first = await register_account_async(
        username, email, password, age_band=data.age_band, accepted_terms=True
    )

    max_age = max(1, get_int_setting("session_max_age_days", 7)) * SECONDS_PER_DAY
    token = create_session(uid, max_age)
    response = action_result(request, "/feed", data={"username": username})
    response.set_cookie(
        key="session",
        value=token,
        max_age=max_age,
        httponly=True,
        samesite="lax",
        secure=cookie_secure(request),
    )
    logger.info(f"User {username} signed up")
    audit.record(
        request,
        "auth.signup",
        user={"uid": uid, "username": username, "role": role},
        target_type="user",
        target_uid=uid,
        target_label=username,
        new_value=role,
        metadata={"first_user": is_first},
        summary=f"user {username} registered account",
        links=[audit.target("user", uid, username)],
    )
    return response
