<?php

namespace App\Http\Controllers\Api\Parents;

use App\Http\Controllers\Api\Core\BaseApiController;
use App\Http\Requests\Parents\StoreAuthorizedUserRequest;
use App\Http\Requests\Parents\UpdateAuthorizedUserRequest;
use App\Models\AuthorizedUser;
use App\Services\Parents\AuthorizedUsersManagementService;
use Illuminate\Http\JsonResponse;
use Symfony\Component\HttpFoundation\Response;

/**
 * Parent CRUD for secondary authorized users on their account (JWT parent role).
 */
class AuthorizedUsersController extends BaseApiController
{
    public function __construct(
        private AuthorizedUsersManagementService $svc,
    ) {
        parent::__construct();
    }

    public function index(): JsonResponse
    {
        $guard = $this->guardJsonOrUnauthorized();
        if ($guard instanceof JsonResponse) {
            return $guard;
        }

        $rows = AuthorizedUser::query()
            ->where('user_id', $guard)
            ->orderBy('id')
            ->get();

        return $this->success($rows);
    }

    public function show(int $id): JsonResponse
    {
        $guard = $this->guardJsonOrUnauthorized();
        if ($guard instanceof JsonResponse) {
            return $guard;
        }

        $resolution = $this->authorizedUserForParent($id, $guard);
        if ($resolution instanceof JsonResponse) {
            return $resolution;
        }

        return $this->success($resolution);
    }

    public function store(StoreAuthorizedUserRequest $request): JsonResponse
    {
        $guard = $this->guardJsonOrUnauthorized();
        if ($guard instanceof JsonResponse) {
            return $guard;
        }

        $email = strtolower(trim((string) $request->validated('email')));
        $result = $this->svc->inviteByEmail($guard, $email);

        if (! $result['created']) {
            $message = 'If the email belongs to a registered user, a confirmation email has been sent.';

            return $this->success(['message' => $message], $message, Response::HTTP_OK);
        }

        $message = 'Authorized user added. A confirmation email has been sent.';

        return $this->success(
            ['message' => $message, 'id' => $result['record']->id],
            $message,
            Response::HTTP_CREATED
        );
    }

    public function update(UpdateAuthorizedUserRequest $request, int $id): JsonResponse
    {
        $guard = $this->guardJsonOrUnauthorized();
        if ($guard instanceof JsonResponse) {
            return $guard;
        }

        $resolution = $this->authorizedUserForParent($id, $guard);
        if ($resolution instanceof JsonResponse) {
            return $resolution;
        }

        /** @var AuthorizedUser $row */
        $row = $resolution;

        $email = $request->validated('email') ?? null;
        if (is_string($email) && trim($email) !== '') {
            try {
                $this->svc->changeEmailAndReinvite($row, $email);
            } catch (\InvalidArgumentException $e) {
                return $this->error($e->getMessage(), Response::HTTP_UNPROCESSABLE_ENTITY);
            }

            return $this->success(
                ['message' => 'Authorized user email updated. A new confirmation email has been sent.'],
                'Authorized user email updated. A new confirmation email has been sent.'
            );
        }

        return $this->success(['message' => 'Authorized user information updated.'], 'Authorized user information updated.');
    }

    public function destroy(int $id): JsonResponse
    {
        $guard = $this->guardJsonOrUnauthorized();
        if ($guard instanceof JsonResponse) {
            return $guard;
        }

        $resolution = $this->authorizedUserForParent($id, $guard);
        if ($resolution instanceof JsonResponse) {
            return $resolution;
        }

        $resolution->delete();

        return $this->success(['message' => 'Authorized user deleted successfully.'], 'Authorized user deleted successfully.');
    }

    private function guardJsonOrUnauthorized(): int|JsonResponse
    {
        $parentId = (int) (auth()->id() ?? 0);
        if ($parentId <= 0) {
            return $this->error('Authentication required.', Response::HTTP_UNAUTHORIZED);
        }

        return $parentId;
    }

    private function authorizedUserForParent(int $id, int $parentId): AuthorizedUser|JsonResponse
    {
        $row = AuthorizedUser::query()
            ->where('id', $id)
            ->where('user_id', $parentId)
            ->first();

        if (! $row) {
            return $this->error('Authorized user not found.', Response::HTTP_NOT_FOUND);
        }

        return $row;
    }
}
