<?php

namespace App\Auth\Command;

use App\Auth\Entity\User;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\Console\Attribute\AsCommand;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Style\SymfonyStyle;
use Symfony\Component\PasswordHasher\Hasher\UserPasswordHasherInterface;

#[AsCommand(
    name: 'app:create-admin',
    description: 'Creates an admin user (ROLE_ADMIN), or promotes an existing user by mobile number',
)]
class CreateAdminCommand extends Command
{
    public function __construct(
        private readonly EntityManagerInterface $em,
        private readonly UserPasswordHasherInterface $hasher,
    ) {
        parent::__construct();
    }

    protected function configure(): void
    {
        $this
            ->addArgument('mobile', InputArgument::OPTIONAL, 'Mobile number, e.g. 09120671756')
            ->addArgument('password', InputArgument::OPTIONAL, 'Plain password (will be hashed)');
    }

    protected function execute(InputInterface $input, OutputInterface $output): int
    {
        $io = new SymfonyStyle($input, $output);

        $mobile = $input->getArgument('mobile') ?: $io->ask('Mobile number');
        $password = $input->getArgument('password') ?: $io->askHidden('Password');

        if (!$mobile || !$password) {
            $io->error('Mobile and password are required.');
            return Command::INVALID;
        }

        $repo = $this->em->getRepository(User::class);
        $user = $repo->findOneBy(['mobileNumber' => $mobile]);
        $existed = $user !== null;

        if (!$existed) {
            $user = new User($mobile);
        }

        $roles = $user->getRoles();
        if (!in_array('ROLE_ADMIN', $roles, true)) {
            $roles[] = 'ROLE_ADMIN';
            $user->setRoles($roles);
        }
        $user->setPasswordHash($this->hasher->hashPassword($user, $password));
        $user->setStatus(1);

        $this->em->persist($user);
        $this->em->flush();

        $io->success(sprintf(
            '%s admin %s (uuid=%s, roles=%s)',
            $existed ? 'Promoted' : 'Created',
            $mobile,
            $user->getUuid(),
            implode(',', $user->getRoles()),
        ));

        return Command::SUCCESS;
    }
}
