<?php

declare(strict_types=1);

namespace apexl\Io\modules\userDisplay\controllers;

use apexl\Io\includes\RouteManager;
use apexl\Io\modules\display\components\BasicLink;
use apexl\Io\modules\display\Controllers\DisplayController;
use apexl\Io\modules\user\entities\userEntity;
use apexl\Io\modules\user\exceptions\UserAlreadyLoggedInException;
use apexl\Io\modules\user\services\CurrentUserFactory;
use apexl\Io\modules\userDisplay\FormBuilders\ForgotPasswordFormBuilder;
use apexl\Io\services\VariableManager;
use JsonException;
use Psr\Http\Message\ResponseInterface;
use Psr\Http\Message\ServerRequestInterface;

final readonly class ForgotPasswordDisplayController extends DisplayController
{
    /**
     * @throws JsonException
     */
    public function __invoke(
        RouteManager $routeManager,
        VariableManager $variableManager,
        ForgotPasswordFormBuilder $formBuilder,
        CurrentUserFactory $currentUserFactory,
        ServerRequestInterface $request,
        ResponseInterface $response
    ): ResponseInterface {
        try {
            $this->assertNotLoggedIn($currentUserFactory->get());
        } catch (UserAlreadyLoggedInException) {
            $this->output->addRedirect('user.login.redirect', '/');

            return $this->json($response);
        }

        $this->render->setActive('noUI');
        $this->render->setPageTitle('Forgotten Password');

        $components = [
            $formBuilder->build(),
            $this->component(BasicLink::class)
                ->addClass('forgottenPasswordLink')
                ->addRoute($routeManager->getRoutePattern('user.display.login'))
                ->addText($variableManager->get('user_login_return_login_text') ?? 'Return to login'),
        ];


        $this->output->addResponse($request, $this->render->build($components));

        return $this->json($response);
    }

    /**
     * @throws UserAlreadyLoggedInException
     */
    private function assertNotLoggedIn(userEntity $user): void
    {
        if ($user->isLoggedIn()) {
            throw new UserAlreadyLoggedInException($user->id);
        }
    }
}


